Untitled
Anonymous
Plain Text
02/08/2026 7:50 AM
4.5 KB
10
Indexable
Never
grammar TyC;
@lexer::header {
from lexererr import *
}
@lexer::members {
def emit(self):
tk = self.type
if tk == self.UNCLOSE_STRING:
result = super().emit();
raise UncloseString(result.text);
elif tk == self.ILLEGAL_ESCAPE:
result = super().emit();
raise IllegalEscape(result.text);
elif tk == self.ERROR_CHAR:
result = super().emit();
raise ErrorToken(result.text);
else:
return super().emit();
}
options{
language=Python3;
}
// ==LEXER==
//Keywords
AUTO: 'auto';
BREAK: 'break';
CASE: 'case';
CONTINUE: 'continue';
DEFAULT: 'default';
ELSE: 'else';
FLOAT: 'float';
FOR: 'for';
IF: 'if';
INT: 'int';
RETURN: 'return';
STRING: 'string';
STRUCT: 'struct';
SWITCH: 'switch';
VOID: 'void';
WHILE: 'while';
//Operators
ADD: '+';
SUB: '-';
MUL: '*';
DIV: '/';
MOD: '%';
EQ: '==';
NEQ: '!=';
LES: '<';
GRE: '>';
LESEQ: '<=';
GREEQ: '>=';
OR: '||';
AND: '&&';
NOT: '!';
INC: '++';
DEC: '--';
ASSIGN: '=';
MEMACCESS: '.';
//Separators
LBRACE: '{';
RBRACE: '}';
LPAREN: '(';
RPAREN: ')';
SEMI: ';';
COMMA: ',';
COLON: ':';
//Identifiers
IDENTIFIER: [a-zA-Z_][a-zA-Z0-9_]*;
//Literals
INTLIT: [0-9]+;
FLOATLIT:
[0-9]+ '.' [0-9]* ([eE][+-]?[0-9]+)?
| '.' [0-9]+ ([eE][+-]?[0-9]+)?
| [0-9]+ [eE][+-]?[0-9]+
;
fragment ESC: '\\' [bfrnt"'\\];
fragment CHAR: ~["\\\r\n] | ESC;
//with tokens
ILLEGAL_ESCAPE: '"' CHAR* '\\' ~[bfrnt"'\\\r\n] {
self.text = self.text[1:]
};
UNCLOSE_STRING: '"' CHAR* ([\r\n] | EOF) {
self.text = self.text[1:]
};
STRINGLIT: '"' CHAR* '"' {
self.text = self.text[1:-1]
};
WS: [ \t\r\n\f]+ -> skip;
BLOCK_COMMENT: '/*' .*? '*/' -> skip;
LINE_COMMENT: '//' ~[\r\n]* -> skip;
ERROR_CHAR: .;
//==PARSER==
// TODO: Define grammar rules here
program: (structDec1 | funcDec1)* EOF;
structDec1: STRUCT IDENTIFIER LBRACE memberDec1* RBRACE SEMI;
memberDec1: type IDENTIFIER SEMI;
funcDec1: (type | VOID)? IDENTIFIER LPAREN paramList? RPAREN block;
paramList: param (COMMA param)*;
param: type IDENTIFIER;
type: primitiveType | IDENTIFIER;
primitiveType: INT | FLOAT | STRING;
block: LBRACE stmt* RBRACE;
stmt:
varDec1Stmt
| assignStmt SEMI
| ifStmt
| whileStmt
| forStmt
| switchStmt
| returnStmt SEMI
| breakStmt SEMI
| continueStmt SEMI
| callStmt SEMI
| expr SEMI
| block
;
//Vari declaration
varDec1Stmt: (AUTO | type) IDENTIFIER (ASSIGN expr)? SEMI;
//Assign
assignStmt: lhs ASSIGN expr;
lhs: IDENTIFIER | expr MEMACCESS IDENTIFIER;
//Control
ifStmt: IF LPAREN expr RPAREN stmt (ELSE stmt)?;
whileStmt: WHILE LPAREN expr RPAREN stmt;
forStmt: FOR LPAREN forInit SEMI expr? SEMI forUpdate? RPAREN stmt;
forInit: (AUTO IDENTIFIER (ASSIGN expr)? | type IDENTIFIER (ASSIGN expr)? | assignStmt)?;
forUpdate: assignStmt | incDecExpr;
//Switch
switchStmt: SWITCH LPAREN expr RPAREN LBRACE switchCase* RBRACE;
switchCase: CASE expr COLON stmt* | DEFAULT COLON stmt*;
//Others
breakStmt: BREAK;
continueStmt: CONTINUE;
returnStmt: RETURN expr?;
//callStmt: IDENTIFIER LPAREN argList? RPAREN;
expr1:
literal
| IDENTIFIER
| LPAREN expr RPAREN
| IDENTIFIER LPAREN argList? RPAREN
| expr1 MEMACCESS IDENTIFIER
;
//Literals
literal: INTLIT | FLOATLIT | STRINGLIT | structLiteral;
structLiteral: LBRACE exprList? RBRACE;
incDecExpr: (INC | DEC) expr1 | expr1 (INC | DEC);
argList: expr (COMMA expr)*;
exprList: expr (COMMA expr)*;
expr2: expr1 (INC | DEC)?;
expr3: (SUB | NOT | INC | DEC) expr3 | expr2;
expr4: expr3 ((MUL | DIV | MOD) expr3)*;
expr5: expr4 ((ADD | SUB) expr4)*;
expr6: expr5 ((LES | GRE | LESEQ | GREEQ) expr5)*;
expr7: expr6 ((EQ | NEQ) expr6)*;
expr8: expr7 (AND expr7)*;
expr9: expr8 (OR expr8)*;
expr:
expr9
| expr ASSIGN expr
;Editor is loading...
Leave a Comment