X-Git-Url: https://gitweb.ps.run/toc/blobdiff_plain/8aeae09e74b46ca52866f22b48f55fecdf27b849..dbc4a22d3c8c4189459f0361cb9da06415ec2dc9:/Toc.g4 diff --git a/Toc.g4 b/Toc.g4 index afe4209..336b7b0 100644 --- a/Toc.g4 +++ b/Toc.g4 @@ -5,28 +5,34 @@ prog: (decl)+ EOF; decl: varDecl ';' | funcDecl | structDecl + | namespaceDecl ; +namespaceDecl: 'namespace' typeName '{' decl* '}'; + varDecl: 'var' var; var: varName (':' type) ('=' expr)?; varInit: varName (':' type) ('=' expr); -type: typeName (typeModifier)*; +type: namespaceSpecifier* typeName (typeModifier)*; typeModifier: '*' | ('[' (INT_LIT)? ']'); +namespaceSpecifier: typeName '::'; funcDecl: 'func' func; -func: funcName '(' parameter ')' (':' type) body; +func: funcName genericDecl? '(' parameter ')' (':' type) body; parameter: (var (',' var)*)?; body: '{' stmt* '}'; -structDecl: 'struct' structName '{' structMember* '}'; -structMember: structVar | structMethod; +structDecl: 'struct' structName genericDecl? '{' structMember* '}'; +structMember: privateDecl? structVar | structMethod; structVar: var ';'; structMethod: func; +privateDecl: 'private'; +genericDecl: '<' typeName (',' typeName)* '>'; stmt: varDecl ';' | ifStmt @@ -41,55 +47,32 @@ ifStmt: 'if' expr body elseIfStmt* elseStmt?; elseIfStmt: 'else' 'if' expr body; elseStmt: 'else' body; -switchStmt: 'switch' identifierExpr switchBody; +switchStmt: 'switch' expr switchBody; switchBody: '{' switchCase* '}'; switchCase: 'case' expr body; -forStmt: 'for' (varInit | assignStmt) ',' expr ',' expr body; +forStmt: 'for' varInit ',' expr ',' expr body; whileStmt: 'while' expr body; -assignStmt: identifierExpr '=' expr; +assignStmt: expr '=' expr; returnStmt: 'return' expr; -expr: funcExpr - | litExpr - | identifierExpr - | parenExpr - | accessExpr - | opExpr; - -/* op */ -nonOpExpr: funcExpr - | litExpr - | identifierExpr - | parenExpr - | accessExpr; - -/* lit access op */ -nonAccessExpr: funcExpr - | identifierExpr - | parenExpr; - -funcExpr: funcName '(' (expr (',' expr)*)? ')'; - -opExpr: binaryOp | prefixOp | postfixOp | ternaryOp; -binaryOp: nonOpExpr binary_op nonOpExpr (binary_op nonOpExpr)*; -prefixOp: prefix_op nonOpExpr; -postfixOp: nonOpExpr postfix_op; -ternaryOp: nonOpExpr '?' expr ':' expr; - -identifierExpr: varName; - -litExpr: INT_LIT | DECIMAL_LIT | STRING_LIT | BOOL_LIT; - -accessExpr: nonAccessExpr (accessSubExpr)+; -accessSubExpr: accessMember | accessBrackets; -accessMember: ('.' | '->') identifierExpr; -accessBrackets: '[' expr ']'; +expr: namespaceSpecifier* funcName '(' (expr (',' expr)*)? ')' #funcExpr + | expr '.' funcName '(' (expr (',' expr)*)? ')' #methodExpr + | literal #litExpr + | '(' expr ')' #parenExpr + | expr '.' varName #dotExpr + | prefix_op expr #prefixOpExpr + | expr postfix_op #postfixOpExpr + | expr binary_op expr #binaryOpExpr + | expr '?' expr ':' expr #ternaryOpExpr + | expr '[' expr ']' #bracketExpr + | namespaceSpecifier* varName #identifierExpr + ; -parenExpr: '(' expr ')'; +literal: INT_LIT | DECIMAL_LIT | STRING_LIT | BOOL_LIT; funcName: NAME; varName: NAME;