logo

Select Sidearea

Populate the sidearea with useful widgets. Itโ€™s simple to add images, categories, latest post, social media icon links, tag clouds, and more.
[email protected]
+1234567890
 

Subroutine Division for 8051 Microcontroller

;=============================================================== ; subroutine DIV8 ; 8-Bit / 8-Bit to 8-Bit Quotient & Remainder signed Divide ; 2’s Complement Format ; ; input: r0 = Dividend X ; r1 = Divisor Y ; ; output: r0 = quotient Q of division Q = X / Y ; r1 = remainder ; ; calls: Cr0, Cr1, Mr0-> See previous subroutine ; alters: acc, C, Bits 21H & 22H ;===============================================================

DIV8:      anl PSW, #0E7H ; Register Bank 0           acall Cr0 ; 2's comp -> Mag/Sign           acall Cr1 ; 2's comp -> Mag/Sign           acall UDIV8           acall Mr0 ; Mag/Sign -> 2's Comp           ret
;===============================================================; subroutine UDIV8; 8-Bit / 8-Bit to 8-Bit Quotient & Remainder Unsigned Divide;; input: r0 = Dividend X; r1 = Divisor Y;; output: r0 = quotient Q of division Q = X / Y; r1 = remainder ; ;; alters: acc, C;===============================================================
UDIV8:     push b           mov a, r0 ; read X and ...           mov b, r1 ; ... Y           div ab ; divide X and Y           mov r0, a ; save result quotient           mov r1, b ; save remainder           pop b           ret
;====================================================================           ; subroutine DIV16           ; 16-Bit / 16-Bit to 16-Bit Quotient & remainder signed Divide           ; 2's Complement Format           ;           ; input: r1, r0 = Dividend X           ; r3, r2 = Divisor Y           ;           ; output: r1, r0 = quotient Q of division Q = X / Y           ; r3, r2 = remainder            ; Carry C is set if Y = 0, i.e. divide by 0 attempted           ;           ; calls: UDIV16, Cr0r1, Cr2r3, Mr0r1           ;           ; alters: acc, r4, r5, r6, r7, flags, Bits 21H & 22H;====================================================================
DIV16: anl PSW, #0E7H ; Register Bank 0           mov a, r3 ; get divisor high byte           orl a, r2 ; OR with low byte           jnz div_OK ; divisor OK if not 0           setb C ; else, overflow           ret
div_OK: push dpl           push dph           push b           acall Cr0r1 ; 2's comp -> Mag/Sign           acall Cr2r3 ; 2's comp -> Mag/Sign           acall UDIV16           acall Mr0r1 ; Mag/Sign -> 2's Comp           clr C           pop b           pop dph           pop dpl           ret ; done
;====================================================================           ; subroutine UDIV16           ; 16-Bit / 16-Bit to 16-Bit Quotient & Remainder Unsigned Divide           ;           ; input: r1, r0 = Dividend X           ; r3, r2 = Divisor Y           ;           ; output: r1, r0 = quotient Q of division Q = X / Y           ; r3, r2 = remainder            ;           ; alters: acc, B, dpl, dph, r4, r5, r6, r7, flags;====================================================================
UDIV16: mov r7, #0 ; clear partial remainder           mov r6, #0           mov B, #16 ; set loop count
div_loop: clr C ; clear carry flag           mov a, r0 ; shift the highest bit of           rlc a ; the dividend into...           mov r0, a           mov a, r1           rlc a           mov r1, a           mov a, r6 ; ... the lowest bit of the           rlc a ; partial remainder           mov r6, a           mov a, r7           rlc a           mov r7, a           mov a, r6 ; trial subtract divisor           clr C ; from partial remainder           subb a, r2           mov dpl, a           mov a, r7           subb a, r3           mov dph, a           cpl C ; complement external borrow           jnc div_1 ; update partial remainder if           ; borrow           mov r7, dph ; update partial remainder           mov r6, dpl           div_1: mov a, r4 ; shift result bit into partial           rlc a ; quotient           mov r4, a           mov a, r5           rlc a           mov r5, a           djnz B, div_loop           mov a, r5 ; put quotient in r0, and r1           mov r1, a           mov a, r4           mov r0, a           mov a, r7 ; get remainder, saved before the           mov r3, a ; last subtraction           mov a, r6           mov r2, a           ret
;====================================================================           ; subroutine DIV32           ; 32-Bit / 16-Bit to 32-Bit Quotient & remainder signed Divide           ; 2's Complement Format           ;           ; input: r3, r2, r1, r0 = Dividend X           ; r5, r4 = Divisor Y           ;           ; output: r3, r2, r1, r0 = quotient Q of division Q = X / Y           ; r7, r6, r5, r4 = remainder           ; Carry C is set if Y = 0, i.e. divide by 0 attempted           ;           ; calls: UDIV32, Cr0r3, Cr4r5, Mr0r3           ;           ; alters: acc, flags, Bits 21H & 22H;====================================================================
DIV32: anl PSW, #0E7H ; Register Bank 0           mov a, r4 ; get divisor high byte           orl a, r5 ; OR with low byte           jnz div32_OK ; divisor OK if not 0           setb C ; else, overflow           ret
div32_OK: acall Cr0r3 ; 2's comp -> Mag/Sign           acall Cr4r5 ; 2's comp -> Mag/Sign           acall UDIV32           acall Mr0r3 ; Mag/Sign -> 2's Comp           clr C ; divisor is not 0           ret ; done
;====================================================================           ; subroutine UDIV32           ; 32-Bit / 16-Bit to 32-Bit Quotient & Remainder Unsigned Divide           ;           ; input: r3, r2, r1, r0 = Dividend X           ; r5, r4 = Divisor Y           ;           ; output: r3, r2, r1, r0 = quotient Q of division Q = X / Y           ; r7, r6, r5, r4 = remainder           ;;           ; alters: acc, flags;====================================================================
UDIV32: push 08 ; Save Register Bank 1           push 09           push 0AH           push 0BH           push 0CH           push 0DH           push 0EH           push 0FH           push dpl           push dph           push B           setb RS0 ; Select Register Bank 1           mov r7, #0 ; clear partial remainder           mov r6, #0           mov r5, #0            mov r4, #0           mov B, #32 ; set loop count
div_lp32: clr RS0 ; Select Register Bank 0           clr C ; clear carry flag           mov a, r0 ; shift the highest bit of the           rlc a ; dividend into...           mov r0, a           mov a, r1           rlc a           mov r1, a           mov a, r2           rlc a           mov r2, a           mov a, r3           rlc a           mov r3, a           setb RS0 ; Select Register Bank 1           mov a, r4 ; ... the lowest bit of the           rlc a ; partial remainder           mov r4, a           mov a, r5           rlc a           mov r5, a           mov a, r6           rlc a           mov r6, a           mov a, r7           rlc a           mov r7, a           mov a, r4 ; trial subtract divisor from           clr C ; partial remainder           subb a, 04           mov dpl, a           mov a, r5           subb a, 05           mov dph, a           mov a, r6           subb a, #0           mov 06, a           mov a, r7           subb a, #0           mov 07, a           cpl C ; complement external borrow           jnc div_321 ; update partial remainder if           ; borrow           mov r7, 07 ; update partial remainder           mov r6, 06           mov r5, dph           mov r4, dpl           div_321: mov a, r0 ; shift result bit into partial           rlc a ; quotient           mov r0, a           mov a, r1           rlc a           mov r1, a           mov a, r2           rlc a           mov r2, a           mov a, r3           rlc a           mov r3, a           djnz B, div_lp32
 mov 07, r7 ; put remainder, saved before the           mov 06, r6 ; last subtraction, in bank 0           mov 05, r5           mov 04, r4           mov 03, r3 ; put quotient in bank 0           mov 02, r2           mov 01, r1           mov 00, r0           clr RS0           pop B           pop dph           pop dpl           pop 0FH ; Retrieve Register Bank 1           pop 0EH           pop 0DH           pop 0CH           pop 0BH           pop 0AH           pop 09           pop 08           ret