dnl vim:mps+=\: dnl dnl DO NOT EDIT! This file is generated automatically! dnl divert(-1)changequote(,) __AUTHOR(⟦Josef Kubin⟧, ⟦2021,01,30⟧, ⟦https://github.com/jkubin/m4root⟧) ___DESCR(⟦the most general (root) rules for all scripts⟧) __REASON(⟦script decomposition; NO repeated information anywhere else⟧) ___USAGE(⟦m4 root.m4 stem.m4 branch.m4 sub_branch.m4 leaf.m4 data.mc > output.file⟧) # prerequisites for understanding M4 # # https://en.wikipedia.org/wiki/Automata_theory # https://en.wikipedia.org/wiki/Formal_grammar # # Formal Grammar (Chomsky type) # G = (N, Σ, P, S) # N: nonempty finite set of non-terminal symbols # Σ: finite set of terminal symbols # N ∩ Σ = ø # P: finite set of production rules # (N ∪ Σ)* N (N ∪ Σ)* → (N ∪ Σ)* # S: is the start symbol # S ∈ N # # https://en.wikipedia.org/wiki/Context-free_grammar # # production rules in Context-free grammar (type 2) # P: A → β # A ∈ N # β ∈ (N ∪ Σ)* # # production rules in M4 # A → β # define(A, β) # # A → ε # define(A, ) # define(A) # adds LOUD alert for unsuspecting users define(DONTE, ifelse($#, 0, $0, DO NOT EDIT! This file is generated automatically!)) # adds an unpaired quote symbol Left/Right: # LL() →  # RR() →  # define(LL, ifelse($#, 0, $0, changequotednl changequote(,))) define(RR, ifelse($#, 0, $0, changequote`'dnl changequote(,))) # expands n-th argument (use Vim shortcuts Ctrl-a or Ctrl-x to change ARGn) define(ARG1, $1) define(ARG2, $2) define(ARG3, $3) define(ARG4, $4) define(ARG5, $5) define(ARG6, $6) define(ARG7, $7) define(ARG8, $8) define(ARG9, $9) # selects n-th argument define(SARG1, $1) define(SARG2, $2) define(SARG3, $3) define(SARG4, $4) define(SARG5, $5) define(SARG6, $6) define(SARG7, $7) define(SARG8, $8) define(SARG9, $9) # adds number of arguments (used for loops) define(NAR, $#) # adds another universal pair of symbols that protects unwanted expansion # (`paYr' is not a word from the dictionary) define(PAYR, $@) # expands the last argument # A($1, $2, …, $n) → $$# → $n → β define(EXPAND_LAST_ARG, define(#, $$#)indir(#, $@)) # selects the last argument # A($1, $2, …, $n) → $$# → $n define(SELECT_LAST_ARG, define(#, $$#)indir(#, $@)) # expands the last but one (there must be at least two arguments) # A($1, $2, …, $n) → $decr($#) → $(n-1) → β define(EXPAND_LAST_BUT_ONE, define(#, $decr($#))indir(#, $@)) # selects the last but one (there must be at least two arguments) # A($1, $2, …, $n) → $decr($#) → $(n-1) define(SELECT_LAST_BUT_ONE, define(#, LL()$decr($#)RR())indir(#, $@)) # prints an informative message to stderr define(ROOT_INFO, errprint(__file__:__line__: info: $1 )) # prints a warning message to stderr if something is strange define(ROOT_WARNING, errprint(__file__:__line__: warning: $1 )) # aborts a script if something goes wrong and prints the reason to stderr define(ROOT_ERROR, errprint(__file__:__line__: error: $1 )m4exit(1))