;Division of 16bit by 8 bit with a result in Q16.16 form
;
; X_Int.X_Frac = X_Int / Y
;
; RAM - 6 bytes (1 temp):
; X_Int = X_IntH:X_IntL 16 bit input/ output integer part
; X_Frac = X_FracH:X_FracL 16 bit output fractional part
; Y divisor / temporary
; Counter counter
;
; Size = 39 instructions
; Execution time = 6+16*15-2+3+16*15-2+3+3(return)
; = 491 instruction cycles
;
; 8-July-2000 by Nikolai Golovchenko
; 16-February-2001 fixed, reduced execution time and temporaries
Div16by8to16_16
clr X_FracL
clr X_FracH
mov W, #16
mov Counter, W
mov W, Y ;keep Y value in accumulator
clr Y ;and use Y register as temporary
;Find integer part
Div16by8to16_16a
rl X_IntL ;shift next msb into temporary
rl X_IntH
rl Y
rl Counter ;carry has 9th bit of temporary
;copy carry to counter
sub Y, W ;substract Y (in w) from temporary
snc ;if no borrow, set Counter.0
setb Counter.0
sb Counter.0 ;if Counter.0 clear (borrow) restore temporary
add Y, W
clc ;restore counter
rr Counter
;at this point carry is the next bit of result
decsz Counter ;repeat 16 times to find integer part
jmp Div16by8to16_16a
;shift last integer bit
rl X_IntL
rl X_IntH
;Find fractional part
setb Counter.4 ;Counter = 16
Div16by8to16_16b
;Shift zero bit into temporary
rl X_FracL
rl X_FracH
rl Y
rl Counter ;carry has 9th bit of temporary
;copy carry to counter
sub Y, W ;substract Y(in w) from temporary
snc ;if no borrow, set Counter.0
setb Counter.0
sb Counter.0 ;if Counter.0 clear (borrow) restore temporary
add Y, W
clc ;restore counter
rr Counter
decsz Counter ;repeat 16 times
jmp Div16by8to16_16b
;shift last fractional bit
rl X_FracL
rl X_FracH
mov Y, W ;restore divisor
retp
Interested: