RPGHacker / asar

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

defining a label on the same line as an `if` statement is sometimes broken #280

Open gizaha opened 1 year ago

gizaha commented 1 year ago

The "+" sublabel position breaks the code. Asar 1.81

macro testmacro()
    !index = 1
    !frames_done = 0

while !frames_done < 8
    print "run #!index"

;***IF YOU PUT THE + SUBLABEL ONE POSITION UP, CODE WORKS PERFECT, I CANNOT FIGURE WHY
;(PROBABLY BECAUSE "IF LOOP" WITHIN "WHILE LOOP"?)

+               if getfilestatus("C:/folder/!index.pic") = 0 
                !frames_done #= !frames_done+1 
                print "file is available"
                endif   
;there is a folder that has 8 files with names 1.pic, 2.pic, 4.pic, 5.pic, 7.pic, 8.pic, 9.pic, 10.pic
;and I want to search which are available and which ones are missing.
;normally 10 runs needed to detect these 8 files and exit the while loop with !index=11

    print "flag"        
    print "found !frames_done files from 8 total"
    print ""    ;new line
    !index #= !index+1
endif

    print "exit from loop, index=!index MUST BE 11"
endmacro

%testmacro()
randomdude999 commented 6 months ago

reduced test case to

if 0
  lbl: if 1
  endif
endif

labels at the start of the line are only parsed if numif==numtrue, which means asar doesn't see the if 1 and thinks there's one endif too many.

also, i have a feeling that trying to put a label right before a while or for will lead to weird bugs where said label will be added multiple times.

i think the easiest fix is to just ban labels before if/while/for/etc and tell people to move the labels one line up or something.

randomdude999 commented 6 months ago
if 1
  lbl: if 1
  endif
endif

now gives

<input>:3: error: (Elabel_before_if): Labels are not allowed before "if" commands. Suggestion: move the label to a separate line.
    in block: [lbl: if 1]
<input>:5: error: (Emisplaced_endif): Misplaced endif.
    in block: [endif]

while i couldn't get rid of that misplaced endif error easily, at least it should give a hint as to what's wrong. unfortunately changing the first if 1 to if 0 still gives the old error, that'd take a fair bit more effort to fix... it shouldn't be a problem with while loops, as the error is given every time the if condition is true, which for while loops is at least once i hope.

i'm not exactly happy with this fix, but if nobody volunteers to make a better one then i'll consider this good enough

randomdude999 commented 6 months ago

you just can't win with asar, can you

i tried implementing a different fix that would actually allow labels in this position. this involves making addlabel() be called even on false if branches, and making sure it doesn't error in that case, just return whether the first word is a valid label. however, this breaks if the label definition contains a define, in fact it's impossible to tell whether the first word is a label or not without fully expanding defines there, which we also don't want to do for untaken if branches.

so basically the choice is between banning all labels here, or allowing most labels but still giving the cryptic error in complicated cases. i'm not sure which one i like better