| author | |
| committer | |
| log | e054442e2371b0176c14ff740d78607d078ca9fb |
| tree | 5469c4564c8d4b0a020b3cc444affb64fdd66022 |
| parent | 203e8279539220db84823bb79671c5c6c7d1065f |
| signature |
Currently the grammar doesn't forbid chained compare ops, see the new
test case which now passes.3 files changed, 16 insertions(+), 13 deletions(-)
doc/langref/grammar.peg+1-1| ... | ... | @@ -126,7 +126,7 @@ BoolOrExpr <- BoolAndExpr (OrOp BoolAndExpr)* !OrOp |
| 126 | 126 | |
| 127 | 127 | BoolAndExpr <- CompareExpr (AndOp CompareExpr)* !AndOp |
| 128 | 128 | |
| 129 | CompareExpr <- BitwiseExpr (CompareOp BitwiseExpr / !CompareOp) | |
| 129 | CompareExpr <- BitwiseExpr (CompareOp BitwiseExpr)? !CompareOp | |
| 130 | 130 | |
| 131 | 131 | BitwiseExpr <- BitShiftExpr (BitwiseOp BitShiftExpr)* !BitwiseOp |
| 132 | 132 |
lib/std/zig/parser_fuzz.zig+5| ... | ... | @@ -140,6 +140,11 @@ test "bin op at end of file" { |
| 140 | 140 | ); |
| 141 | 141 | } |
| 142 | 142 | |
| 143 | // Found using AFL++ | |
| 144 | test "resume block chained compare ops" { | |
| 145 | try checkAgainstOracle("test{resume{0 > 0;} > 0 > 0;}"); | |
| 146 | } | |
| 147 | ||
| 143 | 148 | fn checkAgainstOracle(source: [:0]const u8) !void { |
| 144 | 149 | var fba_buf: [1 << 18]u8 = undefined; |
| 145 | 150 | var fba: std.heap.FixedBufferAllocator = .init(&fba_buf); |
lib/std/zig/parser_generated_oracle.zig+10-12| ... | ... | @@ -639,18 +639,16 @@ const Parser = struct { |
| 639 | 639 | pub fn parseCompareExpr(p: *Parser) Error!bool { |
| 640 | 640 | return blk_0: { |
| 641 | 641 | const pos_0 = p.i; |
| 642 | if (try p.parseBitwiseExpr() and blk_2: { | |
| 643 | const pos_2 = p.i; | |
| 644 | if (try p.parseCompareOp() and try p.parseBitwiseExpr()) break :blk_2 true; | |
| 645 | p.i = pos_2; | |
| 646 | if (blk_3: { | |
| 647 | const pos_3 = p.i; | |
| 648 | const match_3 = try p.parseCompareOp(); | |
| 649 | p.i = pos_3; | |
| 650 | break :blk_3 !match_3; | |
| 651 | }) break :blk_2 true; | |
| 652 | p.i = pos_2; | |
| 653 | break :blk_2 false; | |
| 642 | if (try p.parseBitwiseExpr() and (blk_3: { | |
| 643 | const pos_3 = p.i; | |
| 644 | if (try p.parseCompareOp() and try p.parseBitwiseExpr()) break :blk_3 true; | |
| 645 | p.i = pos_3; | |
| 646 | break :blk_3 false; | |
| 647 | } or true) and blk_1: { | |
| 648 | const pos_1 = p.i; | |
| 649 | const match_1 = try p.parseCompareOp(); | |
| 650 | p.i = pos_1; | |
| 651 | break :blk_1 !match_1; | |
| 654 | 652 | }) break :blk_0 true; |
| 655 | 653 | p.i = pos_0; |
| 656 | 654 | break :blk_0 false; |