RPGHacker / asar

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

Hoisting? #237

Open GhbSmwc opened 2 years ago

GhbSmwc commented 2 years ago

Was wondering how asar processes the defines in order:

!define1 = !define2

!define2 = 5

print "testing ", dec(!define1)

And I am not sure if this is documented in the help section. The above code does not error out saying define2 is not defined (yet) since the first line define1 was being set by define2 before that was being defined.

However this does error out:

print "testing ", dec(!define1)

!define1 = !define2

!define2 = 5
Asar 1.81, originally developed by Alcaro, maintained by Asar devs.
Source code: https://github.com/RPGHacker/asar

Enter patch name: "C:\Users\RedBro\Desktop\smw romhacking\Submission\ExtendedSpriteDespawn\test.asm"
Enter ROM name: "C:\Users\RedBro\Desktop\smw romhacking\Submission\ExtendedSpriteDespawn\a.smc"
c:/users/redbro/desktop/smw romhacking/submission/extendedspritedespawn/test.asm:1: error: (E5088): Define 'define1' wasn't found.
Errors were detected while assembling the patch. Assembling aborted. Your ROM has not been modified.
Press any key to continue . . .

So it seems like the print command does not "look ahead" on the code and evaluate things orderly, but defines themselves when a value isn't given will look ahead to find that define on what its being set to.

Alcaro commented 2 years ago

Those two code snippets are identical. You copypasted something incorrectly.

GhbSmwc commented 2 years ago

Oops, thanks. Fixed.

RPGHacker commented 2 years ago

I do think this behavior is documented in the manual. Specifically, I think it's documented that defining with = does not evaluate a define immediately, while defining with := does. Considering this, I'd say the behavior here is exactly what one would expect.

GhbSmwc commented 2 years ago

Looking at the manuel:

equal to the standard =, but resolves all defines in the text to assign before actually assigning it. This makes recursive defines possible.

So it is indirectly mentioned. Also this is backwards, = is the one that resolves the entire document before assigning it, := is the one that does not look ahead in the document when assigning to a define that isn't defined yet.

randomdude999 commented 2 years ago

= does not "resolve the entire document" before assigning. for example, this doesn't work:

!a = !b
print "!a"
!b = 2

= simply sets the contents of the define equal to exactly what you specify, which may contain more defines. the value of !a in that example literally is "!b", not "2". using a define recursively evaluates all defines in it, so in this example:

!a = 2
!b = !a
print "!b"

print "!b" gets expanded to print "!a", which then gets expanded to print "2".

on the other hand, := replaces all defines in the right-hand side at the time of definition, so in this example:

!a = 2
!b := !a
!a = 3

in the 2nd line, the value of !a is still 2, so !b becomes 2, (literally the number 2, not "!a"), and modifying !a after that won't affect !b.

GhbSmwc commented 2 years ago

@randomdude999 Thanks for the info. I sould take the time to explore more on the document.