From c587587f49226a4b9a21c17c243cfecf7b9fa927 Mon Sep 17 00:00:00 2001 From: Olaf Seibert Date: Sat, 23 Jan 2021 20:05:50 +0100 Subject: [PATCH] Fix/work around a bug in parse_expr(). There was an obscure bug in parse_expr(), used to evaluate 'if df', where it could skip past the end of the line marker. If this happened inside an expanded macro, then after that was the next line... In other cases it might be worse. Now that this is fixed, another check for line end junk can be enabled. --- assemble.c | 2 +- parse.c | 6 ++++-- tests/test-float.lst.ok | 6 +++--- tests/test-prec.lst.ok | 41 ++++++++++++++++++++++++++++++++++++----- tests/test-prec.mac | 23 +++++++++++++++++++++++ 5 files changed, 67 insertions(+), 11 deletions(-) diff --git a/assemble.c b/assemble.c index 0c1e0f5..53ba3cb 100644 --- a/assemble.c +++ b/assemble.c @@ -932,7 +932,7 @@ static int assemble( suppressed until .ENDC */ } - return 1; /* TODO: CHECK_EOL */ + return CHECK_EOL; case P_IFF: if (last_cond < 0) { diff --git a/parse.c b/parse.c index 2ac13d2..2e9f406 100644 --- a/parse.c +++ b/parse.c @@ -64,7 +64,7 @@ int check_eol( return 1; } - report(stack->top, "Junk at end of line ('%s')\n", cp); + report(stack->top, "Junk at end of line ('%.20s')\n", cp); return 0; } @@ -1072,7 +1072,9 @@ EX_TREE *parse_unary( get_symbol a second time. */ if (!(label = get_symbol(cp, &cp, &local))) { - cp++; /*JH: eat first char of illegal label, else endless loop on implied .WORD */ + if (!EOL(*cp)) { + cp++; /*JH: eat first char of illegal label, else endless loop on implied .WORD */ + } tp = ex_err(NULL, cp); /* Not a valid label. */ return tp; } diff --git a/tests/test-float.lst.ok b/tests/test-float.lst.ok index 99af982..ec5a5b0 100644 --- a/tests/test-float.lst.ok +++ b/tests/test-float.lst.ok @@ -143,11 +143,11 @@ 120 000420 172127 140263 addd #-1.4,ac1 ; as float 121 122 ; TODO: let parser check for junk at end of line -test-float.mac:123: ***ERROR Junk at end of line ('5') +test-float.mac:123: ***ERROR Junk at end of line ('5 ; bad: ') 123 000424 170627 000002 absf #2.5 ; bad: operand is destination -test-float.mac:124: ***ERROR Junk at end of line ('5') +test-float.mac:124: ***ERROR Junk at end of line ('5 ; bad: ') 124 000430 170527 000002 tstd #2.5 ; bad: operand is considered FDST by the arch handbook -test-float.mac:125: ***ERROR Junk at end of line ('5') +test-float.mac:125: ***ERROR Junk at end of line ('5 ; bad: junk') 125 000434 174027 000002 stf ac0,#2.5 ; bad: junk at end of line 126 000440 174027 000002 stf ac0,#2 ; doesn't makes sense but MACRO11 allows it 127 diff --git a/tests/test-prec.lst.ok b/tests/test-prec.lst.ok index c8676d1..ffa188e 100644 --- a/tests/test-prec.lst.ok +++ b/tests/test-prec.lst.ok @@ -56,17 +56,48 @@ 56 000114 000007 .word 1 + ^/ 2 * 3 / ; 1 + 6 = 7 57 000116 000007 .word 1 + ^$ 2 * 3 $ ; 1 + 6 = 7 test-prec.mac:58: ***ERROR Invalid expression - 58 000120 000003 000000 000000G .word 1 + ^* 2 * 3 * ; Invalid expression - 000126 000000G - 58 + 58 000120 000003 000000 .word 1 + ^* 2 * 3 * ; Invalid expression + 59 + 60 ;;;;; + 61 ; + 62 ; There was an obscure bug in parse_expr(), used to evaluate 'if df', + 63 ; where it could skip past the end of the line marker. + 64 ; + 65 ; If this happened inside an expanded macro, then after that was the + 66 ; next line... + 67 ; In other cases it might be worse. + 68 ; + 69 .macro dirdef name, flags, cond + 70 .rad50 /.'name/ + 71 .byte flags+0, 0 + 72 .if df cond + 73 .globl opcerr + 74 .word opcerr + 75 .iff + 76 .globl name + 77 .word name + 78 .endc + 79 .endm + 80 + 81 000124 dirdef name + 1 000124 130461 051010 .rad50 /.name/ + 2 000130 000 000 .byte +0, 0 + 3 .if df + 4 .globl opcerr + 5 .word opcerr + 6 .iff + 7 .globl name + 8 000132 000000G .word name + 9 .endc + 81 Symbol table -. ******R 001 EXPRES= ****** GX INVALI= ****** GX +. ******R 001 NAME = ****** G Program sections: . ABS. 000000 000 (RW,I,GBL,ABS,OVR,NOSAV) - 000130 001 (RW,I,LCL,REL,CON,NOSAV) + 000134 001 (RW,I,LCL,REL,CON,NOSAV) diff --git a/tests/test-prec.mac b/tests/test-prec.mac index 52083e5..a8e253b 100644 --- a/tests/test-prec.mac +++ b/tests/test-prec.mac @@ -56,3 +56,26 @@ .word 1 + ^/ 2 * 3 / ; 1 + 6 = 7 .word 1 + ^$ 2 * 3 $ ; 1 + 6 = 7 .word 1 + ^* 2 * 3 * ; Invalid expression + +;;;;; +; +; There was an obscure bug in parse_expr(), used to evaluate 'if df', +; where it could skip past the end of the line marker. +; +; If this happened inside an expanded macro, then after that was the +; next line... +; In other cases it might be worse. +; + .macro dirdef name, flags, cond + .rad50 /.'name/ + .byte flags+0, 0 + .if df cond + .globl opcerr + .word opcerr + .iff + .globl name + .word name + .endc + .endm + + dirdef name