RPGHacker / asar

(Now) official repository of the SNES assembler Asar, originally created by Alcaro
Other
195 stars 42 forks source link

datasize fails when used in assert or print before label is defined #274

Closed spooonsss closed 6 months ago

spooonsss commented 1 year ago
!rb as4
print hex(end-Pointers)
Pointers:
db 1
end:

randombot999
<print> 1
01

!rb as4
print hex(datasize(Pointers))
Pointers:
db 1
end:

randombot999
Errors occurred while assembling.
exodustx0 commented 1 year ago

Came across this today, and I got some additional information:

!rb as3
org $008000
ldy #datasize(Data)
Data: db 0
_Data_End:

This produces A0 01 00 00 as expected. However:

!rb as3
org $008000
arch spc700
mov Y, #datasize(Data)
Data: db 0
_Data_End:

This produces:

Errors occurred while assembling.
: error: (Ephantom_error): A phantom error occurred. This is an Asar bug, please report it: https://github.com/RPGHacker/asar/issues
Alcaro commented 1 year ago

I think that's a different issue.

<Sir Walrus> .rb as3
arch spc700
org $008000

mov Y, #1/(x-y)

x:
nop
y:
<randombot999> Errors occurred while assembling.
: error: (Ephantom_error): A phantom error occurred. This is an Asar bug, please report it: https://github.com/RPGHacker/asar/issues
exodustx0 commented 1 year ago

I don't think so, but even if it is, I think you've pointed out a different issue yourself. You tried dividing 1 by -1; was that your intention? Either way, mov Y, #x-y correctly produces 8D FF 00 00, but I assume you meant mov Y, #y-x, which works equally fine.

Alcaro commented 1 year ago

No, I intended to divide by the difference between two labels.

On the first pass, Asar assumes all unknown labels are forward labels and returns some constant (I don't know which, but it's same for all). 1/(val-val) is 1/0, which is an error. However, math errors are not reported on the first pass, it just sets the 'there was an error' flag and expects that the same error will show up on the third pass.

On the second and third passes, labels have their actual values, and 1/($8002-$8003) is just -1.

For the one you posted, I believe that Data is not defined yet, and datasize(Data) is an error. But, like the 1/(val-val) example, it only sets the error flag, it doesn't actually print anything.

In both cases, the root cause is spc700 opcodes trying to evaluate math on first pass. The 65816 opcodes don't, and spc700 shouldn't either.

We should remove the 'unknown labels are fine on first pass' thing; it does nothing useful (it did in earlier Asar versions, but apparently I never cleaned that out when it became obsolete), it just hides errors.

exodustx0 commented 1 year ago

For the one you posted, I believe that Data is not defined yet, and datasize(Data) is an error.

The Asar manual gives this as example codeblock for datasize() usage:

org $008000
main:

lda #datasize(my_table)     ;3
lda #datasize(other_label)  ;0x7FF3 (last label, throws a warning. calculated as $FFFFFF-$00800C)
lda #datasize(main)     ;9

my_table:
    db $00, $00, $02
other_label:

So, based on what you said that I quoted, would that mean that the manual sports erroneous usage of it too? It's using datasize(my_table) while my_table is not defined yet, as far as I can see. Or there's a nuanced difference between this excerpt and mine that I'm not getting.

Alcaro commented 1 year ago

We're talking about Asar bugs, so yes, there is a nuanced difference. 65816 lda #n is correctly implemented, spc700 mov y,#n is not.

randomdude999 commented 6 months ago

the spc700 mov thing was fixed earlier already, and just fixed the print() phantom error too.