mult_32x32_uns - Demonstrate unsigned 32 bit multiplicationΒΆ
.include "p24Hxxxx.inc"
.global __reset ;The label for the first line of code.
.data ;unitialized data section
.bss
;;These start at location 0x0800 because 0-0x07FF reserved for SFRs
u16_k: .space 2 ;Allocating space (in bytes) to variable.
u8_j: .space 1 ;Allocating space (in bytes) to variable.
.text ;Start of Code section
__reset: ; first instruction located at __reset label
mov #__SP_init, w15 ;Initalize the Stack Pointer
mov #__SPLIM_init,W0
mov W0, SPLIM ;Initialize the stack limit register
rcall main ;call main()
reset ;start over
;__SP_init set by linker to be after allocated data
main:
mov #0xFFFF,W0 ;
mov #0xFFFF,W1 ; s = W1:W0 = 4294967295
mov #0xFFFF,W2 ;
mov #0xFFFF,W3 ; r = W3:W2 = 4294967295
call mult32x32_uns
;;W3:W2:W1:W0 = 0xFFFFFFFE00000001 = 18446744065119617025
done: ;do not return
bra done
p = s * r, where: W1:W0 = s
sL = W0
sH = W1
W3:W2 = r
rL = W2
rH = W3
Use W4-W11 to store low and high words of partial products 0-3
pp0L = W4
pp0H = W5
pp1L = W6
pp1H = W7
pp2L = W8
pp2H = W9
pp3L = W10
pp3H = W11
64-bit result in p = W3:W2:W1:W0 (p3:p2:p1:p0)
p0 = W0
p1 = W1
p2 = W2
p3 = W3
mult32x32_uns:
push W8
push W9
push W10
push W11
mul.uu sL,rL,pp0L ;sL*rL = pp0
mul.uu sL,rH,pp1L ;sL*rH = pp1
mul.uu sH,rL,pp2L ;sH*rL = pp2
mul.uu sH,rH,pp3L ;sH*rH = pp3
mov pp0L,p0 ;p0 = pp0L
add pp0H,pp1L,p1 ;p1 = pp0H + pp1L
;;now propagate carry all the way up to p3 word
addc pp1H,pp2H,p2 ;p2 = pp1H + pp2H + cout(pp0H + pp1L)
addc pp3H,#0,p3 ;p3 = pp3H + 0 + cout(previous sum)
;;next sum
add p1,pp2L,p1 ;p1 = pp2L + (p1=pp0H + pp1L)
;;now propagate carry all the way up to p3 word
addc p2,pp3L,p2 ;p2 = pp3L + (p2=pp1H+pp2H) + cout(previous_sum)
addc p3,#0,p3 ;p3 = p3 + 0 + cout(previous_sum)
;;64-bit result p3:p2:p1:p0
pop W11
pop W10
pop W9
pop W8
return
.end