From 18d58e66d58e1174dcd99bccaae5e96e664c54ad Mon Sep 17 00:00:00 2001 From: Rob Landley Date: Tue, 31 May 2022 13:13:43 -0500 Subject: [PATCH] Fix case/esac getting confused by nested flow control blocks. --- tests/sh.test | 2 ++ toys/pending/sh.c | 7 +++---- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/tests/sh.test b/tests/sh.test index 330cbdaa..b3f32ec1 100644 --- a/tests/sh.test +++ b/tests/sh.test @@ -247,6 +247,8 @@ testing 'case;;&' 'case wow in w?w) echo ok;;& wow) echo no; esac' 'ok\nno\n' \ testing "case newlines" \ $'case i\n\nin\n\na) echo one\n\n;;\n\ni)\n\necho two\n\n;;\n\nesac' \ "two\n" "" "" +testing "case block" \ + $'case X in\n X) printf %s "X" || { echo potato;} ;;\nesac' 'X' '' '' testing 'loop in && ||' \ 'false && for i in a b c; do echo $i; done || echo no' 'no\n' '' '' testing "continue" 'for i in a b c; do for j in d e f; do echo $i $j; continue 2; done; done' \ diff --git a/toys/pending/sh.c b/toys/pending/sh.c index 0832b355..ce9b5e18 100644 --- a/toys/pending/sh.c +++ b/toys/pending/sh.c @@ -2861,7 +2861,7 @@ funky: } // type 0 means just got ;; so start new type 2 - if (!pl->type) { + if (!pl->type || pl->type==3) { // catch "echo | ;;" errors if (arg->v && arg->v[arg->c] && strcmp(arg->v[arg->c], "&")) goto flush; if (!arg->c) { @@ -3790,9 +3790,8 @@ is_binary: more = parse_line(new ? : " ", &pl, &expect); free(new); if (more==1) { - if (!new) { - if (!ff) syntax_err("unexpected end of file"); - } else continue; + if (!new) syntax_err("unexpected end of file"); + else continue; } else if (!more && pl) { TT.ff->pl = pl; run_lines(); -- 2.39.2