mirror of
https://gitlab.com/camelot/kickc.git
synced 2024-09-29 03:56:15 +00:00
98 lines
1.6 KiB
NASM
98 lines
1.6 KiB
NASM
// Program where loop-head optimization produces wrong return value
|
|
// Reported by Richard-William Loerakker
|
|
.pc = $801 "Basic"
|
|
:BasicUpstart(main)
|
|
.pc = $80d "Program"
|
|
.label BORDER_COLOR = $d020
|
|
.label BG_COLOR = $d021
|
|
main: {
|
|
.label result = 2
|
|
.label kaputt = $a
|
|
// mul16u(4,123)
|
|
jsr mul16u
|
|
// mul16u(4,123)
|
|
// result = mul16u(4,123)
|
|
// kaputt = <result
|
|
lda.z result
|
|
sta.z kaputt
|
|
lda.z result+1
|
|
sta.z kaputt+1
|
|
// <kaputt
|
|
lda.z kaputt
|
|
// *BORDER_COLOR = <kaputt
|
|
sta BORDER_COLOR
|
|
// >kaputt
|
|
lda.z kaputt+1
|
|
// *BG_COLOR = >kaputt
|
|
sta BG_COLOR
|
|
// }
|
|
rts
|
|
}
|
|
// Perform binary multiplication of two unsigned 16-bit unsigned ints into a 32-bit unsigned long
|
|
// mul16u(word zp($a) a)
|
|
mul16u: {
|
|
.const b = $7b
|
|
.label a = $a
|
|
.label mb = 6
|
|
.label res = 2
|
|
.label return = 2
|
|
lda #<b
|
|
sta.z mb
|
|
lda #>b
|
|
sta.z mb+1
|
|
lda #<b>>$10
|
|
sta.z mb+2
|
|
lda #>b>>$10
|
|
sta.z mb+3
|
|
lda #<0
|
|
sta.z res
|
|
sta.z res+1
|
|
lda #<0>>$10
|
|
sta.z res+2
|
|
lda #>0>>$10
|
|
sta.z res+3
|
|
lda #<4
|
|
sta.z a
|
|
lda #>4
|
|
sta.z a+1
|
|
__b1:
|
|
// while(a!=0)
|
|
lda.z a
|
|
bne __b2
|
|
lda.z a+1
|
|
bne __b2
|
|
// }
|
|
rts
|
|
__b2:
|
|
// a&1
|
|
lda #1
|
|
and.z a
|
|
// if( (a&1) != 0)
|
|
cmp #0
|
|
beq __b3
|
|
// res = res + mb
|
|
lda.z res
|
|
clc
|
|
adc.z mb
|
|
sta.z res
|
|
lda.z res+1
|
|
adc.z mb+1
|
|
sta.z res+1
|
|
lda.z res+2
|
|
adc.z mb+2
|
|
sta.z res+2
|
|
lda.z res+3
|
|
adc.z mb+3
|
|
sta.z res+3
|
|
__b3:
|
|
// a = a>>1
|
|
lsr.z a+1
|
|
ror.z a
|
|
// mb = mb<<1
|
|
asl.z mb
|
|
rol.z mb+1
|
|
rol.z mb+2
|
|
rol.z mb+3
|
|
jmp __b1
|
|
}
|