AWL syntax chart
/*
--------------------------------------------------------------
Syntax root
--------------------------------------------------------------
*/
/* Sequence of root statements */
ROOT_STMT_SEQ:
| ROOT_STMT
| ROOT_STMT ';' ROOT_STMT_SEQ
| SYNTAX_ERR ROOT_STMT_SEQ /* syntax error recovery */
;
ROOT_STMT: STMT /* root statement -> execute */
;
SYNTAX_ERR: error ';' /* syntax error */
;
/*
--------------------------------------------------------------
Rules for statements
--------------------------------------------------------------
*/
/* Single statement */
STMT:
EXPR /* any expression is statement */
| FC_DEF /* functor/class definition */
| S_DEF /* scope definition */
| /* module locals */
LOCAL_DEF
;
/* Functor/class definition */
FC_DEF:
F_DEF /* functor definition */
| F_GROUP_DEF
| C_DEF /* class definition */
/* Probably, make group definition for classes? */
| V_DEF /* virtual definition */
;
/* Statement sequence: statements, separated with ';' */
O_STMT:
| STMT
;
/*
--------------------------------------------------------------
Functor && class definitions
--------------------------------------------------------------
*/
/* Parameter or local */
LOCAL: L_IDENT
;
/* Parameter evaluation flag: '@', if lazy passing */
PARAM_FLAG:
| '@'
;
/* Parameter default initialiser */
PARAM_INIT:
| '=' C_EXPR
;
/* Parameter list */
PARAM_LIST:
| PARAM_FLAG LOCAL PARAM_INIT PARAM_LIST
;
/* Optional parameters list */
O_PARAM_LIST:
| '(' PARAM_LIST ')'
;
/* Locals list (no return value) */
LOCAL_LIST:
| LOCAL LOCAL_LIST
;
LOCAL_DEF:
':' '[' LOCAL_LIST ']'
;
/* Optional locals list (no return value) */
O_LOCAL_LIST:
| LOCAL_DEF
;
/* Functor definition header:
([optional] parameters + [optional] locals).
Returns parameters list. */
F_DEF_HEAD:
O_PARAM_LIST O_LOCAL_LIST
;
/* Functor id */
F_NAME: L_IDENT
;
/* Functor id list */
F_NAME_LIST:
F_NAME
| F_NAME F_NAME_LIST
;
/* Functor definition */
F_DEF: '!' F_NAME
/* functor header & body */
F_DEF_HEAD '=' EXPR
;
/* Functor group definition */
F_GROUP_DEF: '!'
'{' F_NAME_LIST '}'
'='
'{' F_GROUP_SEQ '}'
;
/* Functor group node */
F_GROUP_NODE:
F_DEF_HEAD '=' EXPR
;
/* Functor group sequence */
F_GROUP_SEQ:
F_GROUP_NODE
| F_GROUP_SEQ ',' F_GROUP_NODE
;
/* Virtual definition */
V_DEF: '!' '#' PREFIX
F_DEF_HEAD '=' EXPR
;
/* List of definitions */
FC_LIST:
FC_DEF
| FC_LIST ',' FC_DEF
;
/* List of definitions (optional) */
O_FC_LIST:
| '{' FC_LIST '}'
;
/* Optional superclass */
O_SUPER:
| '[' PREFIX ']'
;
/* Optional constructor */
O_CTOR:
| '=' C_EXPR
;
/* Optional destructor */
O_DTOR:
| '~' C_EXPR
;
/* Optional new virtuals list */
O_VIRTUALS:
| '#'
'{' VIRT_LIST '}'
;
/* Virtuals list */
VIRT_LIST:
| VIRT_LIST L_IDENT
;
/* Class definition */
C_DEF: /* class header */
'!!' O_SUPER L_IDENT
/* optional parameter list */
O_PARAM_LIST
/* optional locals list */
O_LOCAL_LIST
/* optional constructor */
O_CTOR
/* optional destructor */
O_DTOR
/* optional virtuals */
O_VIRTUALS
/* (virtuals binding must be done BEFORE local defs!) */
/* local functors/classes/virtuals definitions */
O_FC_LIST
;
/* Scope definition -- reserved */
S_DEF: '!' '%' L_IDENT
'{' ROOT_STMT_SEQ '}'
;
/*
--------------------------------------------------------------
Rules for expressions
--------------------------------------------------------------
*/
/* Scalar literal */
L_LIT:
/* fixed point literal */
L_FIXED
/* floating point literal */
| L_FLOAT
/* string literal */
| L_STRING
;
/* Prefix reference */
PREFIX: L_IDENT
;
/* Variable reference */
VARIABLE: L_IDENT
;
/* List of any expressions (comma-separated) */
XP_SEQ:
| EXPR
| EXPR ',' XP_SEQ
;
/* List of closed expressions (not separated) */
CXP_SEQP:
C_EXPR
| C_EXPR CXP_SEQP
;
/* List of closed expressions (with termination) */
CXP_SEQT:
':'
| C_EXPR CXP_SEQT
;
CXP_SEQ:
| CXP_SEQP
| CXP_SEQT
;
/* Closed expression (allowed with prefix) */
C_EXPR_PFX:
L_LIT /* literal */
| VARIABLE /* variable reference */
| '(' XP_SEQ ')' /* list of any expressions */
;
BLOCK: O_STMT
| STMT ';' BLOCK
;
/* Closed expression */
C_EXPR:
C_EXPR_PFX
| '[' CXP_SEQ ']' /* list of closed expressions */
| '{' BLOCK '}' /* block */
| '!' '.' /* current class */
;
XP_ATERM: C_EXPR /* (closed expression) */
/* prefixed expression */
| PREFIX C_EXPR_PFX → $1:($2)
/* prefixed expression (alternate) */
| PREFIX '^' XP_ATERM → $1:($3)
/* list compose */
| C_EXPR '::' XP_ATERM → ($1, $3)
/* prefixed with list compose */
| PREFIX C_EXPR_PFX '::' XP_ATERM → $1:($2, $4)
;
/* Expression: terminal (postfix) */
XP_TERM:
XP_ATERM
/* item of list */
| XP_TERM '[' EXPR ']' → l_item($3, $1)
/* element of array */
| XP_TERM '{' XP_SEQ '}' → a_elem($1, $3)
/* tail of list */
| XP_TERM '[>]' → l_tail($1)
;
XP_NTERM: XP_TERM
| XP_TERM '.' XP_NTERM → with($1, $3)
| XP_TERM '!' XP_NTERM → apply($1, $3)
| PREFIX '!!' → $1 . $4
XP_NTERM
| PREFIX '#' PREFIX
;
/* Expression: terminal (prefix) */
XP_PTERM: XP_NTERM
/* head of list */
| '[<]' XP_PTERM → l_head($2)
;
/* Expression: unary postfix */
XP_POST:
XP_PTERM
/* (post increment/decrement) */
| XP_POST '++' → inc_p($1)
| XP_POST '--' → dec_p($1)
/* (string slice) */
| XP_POST '$' '[' EXPR ']' → s_slice($4, $1)
;
/* Expression: anonimous functor definition */
F_LAMBDA: '!'
/* functor header & body */
F_DEF_HEAD '=' C_EXPR
;
/* Expression: unary prefix */
XP_PRE:
XP_POST
/* (preincrement) */
| '++' XP_PRE → inc($2)
/* (predecrement) */
| '--' XP_PRE → dec($2)
/* (absolute value) */
| '+' XP_PRE → abs($2)
/* (negation) */
| '-' XP_PRE → neg($2)
/* (bitwise complement) */
| '~' XP_PRE → not($2)
/* (sign) */
| '<?>' XP_PRE → sgn($2)
/* (string length) */
| '#' '$' XP_PRE → s_len($3)
/* (list length) */
| '#' XP_PRE → l_len($2)
/* (list reverse) */
| '[~]' XP_PRE → l_rev($2)
/* (devaluator) */
| '@' XP_PRE → deval($2)
/* (revaluator) */
| '^' XP_PRE → reval($2)
/* (prefix reference) */
| '!' PREFIX
/* (anonimous functor def) */
| F_LAMBDA
;
/* Expression: multiplicative */
XP_MUL:
XP_PRE
/* (multiplication) */
| XP_MUL '*' XP_PRE → mul($1, $3)
/* (division) */
| XP_MUL '/' XP_PRE → div($1, $3)
/* (integer division) */
| XP_MUL '%' XP_PRE → idiv($1, $3)
/* (integer remainder) */
| XP_MUL '%%' XP_PRE → irem($1, $3)
/* (bit shift left) */
| XP_MUL '<<' XP_PRE → shl($1, $3)
/* (bit shift right) */
| XP_MUL '>>' XP_PRE → shr($1, $3)
/* (string replication) */
| XP_MUL '*' '$' XP_PRE → s_rep($1, $4)
/* (list replication) */
| XP_MUL '[*]' XP_PRE → l_rep($3, $1)
/* (string search backward) */
| XP_MUL '<<' '$' XP_PRE → s_findlast($1, $4)
/* (string search forward) */
| XP_MUL '>>' '$' XP_PRE → s_findfirst($1, $4)
;
/* Expression: additive */
XP_ADD:
XP_MUL
/* (addition) */
| XP_ADD '+' XP_MUL → add($1, $3)
/* (subtraction) */
| XP_ADD '-' XP_MUL → sub($1, $3)
/* (string concatenation) */
| XP_ADD '+' '$' XP_MUL → s_cat($1, $4)
/* (list concatenation) */
| XP_ADD '[+]' XP_MUL → l_cat($1, $3)
;
/* Expression: maximum/minimum */
XP_MUM:
XP_ADD
/* (minimum) */
| XP_MUM '?<' XP_ADD → min($1, $3)
/* (maximum) */
| XP_MUM '?>' XP_ADD → max($1, $3)
/* (string minimum) */
| XP_MUM '?<' '$' XP_ADD → s_min($1, $4)
/* (string maximum) */
| XP_MUM '?>' '$' XP_ADD → s_max($1, $4)
;
/* Expression: comparative */
XP_CMP:
XP_MUM
/* (less than) */
| XP_MUM '<' XP_MUM → lt($1, $3)
/* (less than or equal) */
| XP_MUM '~>' XP_MUM → le($1, $3)
/* (greater than) */
| XP_MUM '>' XP_MUM → gt($1, $3)
/* (greater than or equal) */
| XP_MUM '~<' XP_MUM → ge($1, $3)
/* (equality) */
| XP_MUM '==' XP_MUM → eq($1, $3)
/* (inequality) */
| XP_MUM '~=' XP_MUM → ne($1, $3)
/* (compare) */
| XP_MUM '<?>' XP_MUM → cmp($1, $3)
/* (string less than) */
| XP_MUM '<' '$' XP_MUM → s_lt($1, $4)
/* (string less than or equal) */
| XP_MUM '~>' '$' XP_MUM → s_le($1, $4)
/* (string greater than) */
| XP_MUM '>' '$' XP_MUM → s_gt($1, $4)
/* (string greater than or equal) */
| XP_MUM '~<' '$' XP_MUM → s_ge($1, $4)
/* (string equality) */
| XP_MUM '==' '$' XP_MUM → s_eq($1, $4)
/* (string inequality) */
| XP_MUM '~=' '$' XP_MUM → s_ne($1, $4)
/* (string compare) */
| XP_MUM '<?>' '$' XP_MUM → s_cmp($1, $4)
/* (object equality) */
| XP_MUM '[==]' XP_MUM → ident($1, $3)
/* (object inequality) */
| XP_MUM '[<>]' XP_MUM → differ($1, $3)
;
/* Expression: logical/bitwise */
XP_BIT:
XP_CMP
/* (bitwise AND) */
| XP_BIT '&' XP_CMP → and($1, $3)
/* (bitwise OR) */
| XP_BIT '|' XP_CMP → or($1, $3)
/* (bitwise XOR) */
| XP_BIT '~' XP_CMP → xor($1, $3)
;
/* (optional bit expression */
O_XP_BIT:
| XP_BIT
;
/* Expression: conditional/iterative */
XP_CND:
XP_BIT
/* (range list) */
| O_XP_BIT '..' O_XP_BIT → ($1, $3)
/* (conditional AND clause) */
| XP_BIT '&&' XP_CND → c_and($1, $3)
/* (conditional OR clause) */
| XP_BIT '||' XP_CND → c_or($1, $3)
/* (conditional IF clause) */
| XP_BIT '?' XP_CND ':' → if($1, $3)
/* (conditional UNLESS clause) */
| XP_BIT '~' '?' XP_CND ':' → unless($1, $4)
/* (conditional IF clause) */
| XP_BIT '?' XP_CND ':' XP_CND → if($1, $3, $5)
/* (conditional UNLESS clause) */
| XP_BIT '~' '?' XP_CND ':' XP_CND → unless($1, $4, $6)
/* (loop WHILE clause / precondition) */
| XP_BIT '??' XP_CND → while($1, $3)
/* (loop WHILE clause / postcondition) */
| '??' C_EXPR XP_BIT → do_while($3, $2)
/* (loop UNTIL clause / precondition) */
| XP_BIT '~' '??' XP_CND → until($1, $4)
/* (loop UNTIL clause / postcondition) */
| '~' '??' C_EXPR XP_BIT → do_until($4, $3)
;
/* Unary ops (for combined assignment) */
OPC_UN:
'+' → abs
| '-' → neg
| '~' → not
;
/* Binary ops (for combined assignment / reduction) */
OPC_BIN:
'+' → add
| '-' → sub
| '*' → mul
| '/' → div
| '%' → idiv
| '%%' → irem
| '?<' → min
| '?>' → max
| '<<' → shl
| '>>' → shr
| '&' → and
| '|' → or
| '~' → xor
| '+' '$' → s_cat
| '*' '$' → s_rep
| '?<' '$' → s_min
| '?>' '$' → s_max
;
/* Expression: assignment/exchange */
XP_EXX:
XP_CND
| XP_PTERM '=' XP_EXX → set($1, $3)
| '=' XP_PTERM ':' XP_EXX → set_a($2, $4)
| XP_PTERM '=' ':' OPC_UN → comb ($4:($1))
| '=' XP_PTERM ':' OPC_UN → comb_a ($4:($2))
| '[=]' OPC_BIN XP_PTERM → reduce ($2:($3))
| XP_PTERM '=' OPC_BIN ':' XP_EXX → comb ($3:($1, $5)
| '=' XP_PTERM OPC_BIN ':' XP_EXX → comb_a ($3:($2, $5)
| XP_PTERM ':=' XP_EXX → let($1, $3)
| XP_PTERM ':=' ':' XP_PTERM → swap($1, $4)
| XP_PTERM ':>' XP_EXX → f_get($1, $3)
| XP_PTERM '<:' XP_EXX → f_put($1, $3)
| ':>' XP_PRE → f_get((), $2)
| '<:' XP_PRE → f_put((), $2)
| XP_PTERM '[<-]' XP_EXX → l_push($1, $3)
| XP_PTERM '[->]' XP_EXX → l_pop($1, $3)
;
/* Expression: root */
EXPR: XP_EXX
;