diff options
Diffstat (limited to 'parsing')
-rw-r--r-- | parsing/parse.sh | 140 |
1 files changed, 114 insertions, 26 deletions
diff --git a/parsing/parse.sh b/parsing/parse.sh index 6f3018e..eff6d66 100644 --- a/parsing/parse.sh +++ b/parsing/parse.sh @@ -6,12 +6,44 @@ US="$(printf '\037.')"; US="${US%.}" dbg() { dbg=true - #dbg=false + dbg=false if ${dbg}; then printf 'DEBUG: %s\n' "${@}" >&2 fi } +ptrace=false + +ptrace_begn() +{ + local fn="${1}" + shift 1 + + if ${ptrace}; then + printf 'TRACE: BEGN %s()\n' "${fn}" >&2 + fi +} + +ptrace_pass() +{ + local fn="${1}" + shift 1 + + if ${ptrace}; then + printf 'TRACE: PASS %s()\n' "${fn}" >&2 + fi +} + +ptrace_fail() +{ + local fn="${1}" + shift 1 + + if ${ptrace}; then + printf 'TRACE: FAIL %s()\n' "${fn}" >&2 + fi +} + . ./tokens.sh . ./lexer.sh @@ -27,146 +59,177 @@ complete_command() list() { - dbg 'list()' + ptrace_begn list if and_or; then while separator && and_or; do : done + ptrace_pass list return 0 fi + ptrace_fail list return 1 } and_or() { - dbg 'and_or()' + ptrace_begn and_or if pipeline; then while accept T_AND_IF || accept T_OR_IF; do if ! linebreak || ! pipeline; then + ptrace_fail and_or return 1 fi done + ptrace_pass and_or return 0 fi + ptrace_fail and_or return 1 } pipeline() { - dbg 'pipeline()' + ptrace_begn pipeline accept T_BANG if pipe_sequence; then + ptrace_pass pipeline return 0 fi + ptrace_fail pipeline return 1 } pipe_sequence() { - dbg 'pipe_sequence()' + ptrace_begn pipe_sequence if command; then while accept T_PIPE; do if ! linebreak || ! command; then + ptrace_fail pipe_sequence return 1 fi done + ptrace_pass pipe_sequence return 0 fi + ptrace_fail pipe_sequence return 1 } command() { - dbg 'command()' + ptrace_begn command if simple_command; then + ptrace_pass command return 0 elif compound_command; then redirect_list + ptrace_pass command return 0 fi + ptrace_fail command return 1 } compound_command() { - dbg 'compound_command()' + ptrace_begn compound_command if brace_group; then + ptrace_pass compound_command return 0 elif subshell; then + ptrace_pass compound_command return 0 elif for_clause; then + ptrace_pass compound_command return 0 elif case_clause; then + ptrace_pass compound_command return 0 elif if_clause; then + ptrace_pass compound_command return 0 elif while_clause; then + ptrace_pass compound_command return 0 elif until_clause; then + ptrace_pass compound_command return 0 fi + ptrace_fail compound_command return 1 } subshell() { - dbg 'subshell()' + ptrace_begn subshell if accept T_LPAREN && compound_list && expect T_RPAREN; then + ptrace_pass subshell return 0 fi + ptrace_fail subshell return 1 } compound_list() { - dbg 'compound_list()' + ptrace_begn compound_list newline_list if term; then - dbg FOUND TERM separator + ptrace_pass compound_list return 0 fi + ptrace_fail compound_list return 1 } term() { - dbg 'term()' + ptrace_begn term if and_or; then while separator; do and_or done + ptrace_pass term return 0 fi + ptrace_fail term return 1 } for_clause() { - dbg 'for_clause()' + ptrace_begn for_clause if accept T_FOR; then if expect T_NAME && linebreak; then if accept T_IN; then wordlist if ! sequential_sep; then + ptrace_fail for_clause return 1 fi fi if do_group; then + ptrace_pass for_clause return 0 fi fi fi + ptrace_fail for_clause return 1 } wordlist() { - dbg 'wordlist()' + ptrace_begn wordlist if accept T_WORD; then while accept T_WORD; do :; done + ptrace_pass wordlist return 0 fi + ptrace_fail wordlist return 1 } @@ -289,118 +352,140 @@ until_clause() function_body() { - dbg 'function_body()' + ptrace_begn function_body if compound_command; then redirect_list fi + ptrace_fail function_body return 1 } brace_group() { - dbg 'brace_group()' + ptrace_begn brace_group if accept T_LBRACE && compound_list && expect T_RBRACE; then + ptrace_pass brace_group return 0 fi + ptrace_fail brace_group return 1 } do_group() { - dbg 'do_group()' + ptrace_begn do_group if accept T_DO && compound_list && expect T_DONE; then + ptrace_pass do_group return 0 fi + ptrace_fail do_group return 1 } simple_command() { - dbg 'simple_command()' + ptrace_begn simple_command if cmd_prefix; then if cmd_word; then cmd_suffix fi + ptrace_pass simple_command return 0 elif accept T_FNAME; then if accept T_LPAREN; then expect T_RPAREN if linebreak && function_body; then + ptrace_pass simple_command return 0 fi else cmd_suffix + ptrace_pass simple_command return 0 fi elif cmd_name; then cmd_suffix + ptrace_pass simple_command return 0 fi + ptrace_fail simple_command return 1 } cmd_name() { - dbg 'cmd_name()' + ptrace_begn cmd_name # TODO: Assignment if accept T_CMDNAME; then + ptrace_pass cmd_name return 0 fi + ptrace_fail cmd_name return 1 } cmd_word() { - dbg 'cmd_word()' + ptrace_begn cmd_word # TODO: Assignment if accept T_WORD; then + ptrace_pass cmd_word return 0 fi + ptrace_fail cmd_word return 1 } cmd_prefix() { - dbg 'cmd_prefix()' + ptrace_begn cmd_prefix if io_redirect || accept T_ASSIGNMENT_WORD; then while io_redirect || accept T_ASSIGNMENT_WORD; do : done + ptrace_pass cmd_prefix return 0 fi + ptrace_fail cmd_prefix return 1 } cmd_suffix() { - dbg 'cmd_suffix()' + ptrace_begn cmd_suffix if io_redirect || accept T_WORD; then while io_redirect || accept T_WORD; do : done + ptrace_pass cmd_suffix return 0 fi + ptrace_fail cmd_suffix return 1 } redirect_list() { - dbg 'redirect_list()' + ptrace_begn redirect_list if io_redirect; then while io_redirect; do : done + ptrace_pass redirect_list return 0 fi + ptrace_fail redirect_list return 1 } io_redirect() { - dbg 'io_redirect()' + ptrace_begn io_redirect if io_file || io_here; then + ptrace_pass io_redirect return 0 fi + ptrace_fail io_redirect return 1 } @@ -479,14 +564,17 @@ separator() sequential_sep() { - dbg 'sequential_sep()' + ptrace_begn sequential_sep if accept T_SEMI; then if linebreak; then + ptrace_pass sequential_sep return 0 fi elif newline_list; then + ptrace_pass sequential_sep return 0 fi + ptrace_fail sequential_sep return 1 } @@ -548,6 +636,6 @@ try() #try 'if ; then ; fi' #try 'while foo; do bar; done' #try 'while ; do ; done' -#try 'foo(){ bar; }' +try 'foo(){ bar; }' #try 'case foo in bar) baz;; (qux) quux;; quux);; esac' -try 'foo bar ( baz )' +#try 'foo bar ( baz )' |