7 PARSER_BEGIN(ExpressParser)
\r
8 package org.simantics.express.parser;
\r
9 import org.simantics.express.ast.types.*;
\r
10 import org.simantics.express.ast.expressions.*;
\r
11 import java.util.List;
\r
12 import java.util.ArrayList;
\r
14 public class ExpressParser {
\r
16 PARSER_END(ExpressParser)
\r
21 { <WHITESPACE: " " | "\n" | "\r" | "\t" >
\r
22 | <COMMENT1: "(*" (~["*"] | "*" ~[")"])* "*)" >
\r
23 | <COMMENT2: "--" (~["\n"])* >
\r
27 { ";" | "(" | ")" | "\\" | "?" | "[" | "]"
\r
28 | "{" | "}" | "|" | "&" | ":" | ":=" | ":=:"
\r
29 | ":<>:" | "," | "." | "=" | "<" | ">"
\r
30 | "<=" | ">=" | "/" | "+" | "-" | "*" | "@"
\r
31 | "<*" | "<>" | "**" | "||"
\r
32 | <ENTITY:"ENTITY">
\r
33 | <END_ENTITY:"END_ENTITY">
\r
34 | <SCHEMA:"SCHEMA">
\r
35 | <END_SCHEMA:"END_SCHEMA">
\r
36 | <CONSTANT:"CONSTANT">
\r
37 | <END_CONSTANT:"END_CONSTANT">
\r
38 | <FUNCTION:"FUNCTION">
\r
39 | <END_FUNCTION:"END_FUNCTION">
\r
40 | <PROCEDURE:"PROCEDURE">
\r
41 | <END_PROCEDURE:"END_PROCEDURE">
\r
43 | <END_RULE:"END_RULE">
\r
45 | <END_TYPE:"END_TYPE">
\r
46 | <SUBTYPE_CONSTRAINT:"SUBTYPE_CONSTRAINT">
\r
47 | <END_SUBTYPE_CONSTRAINT:"END_SUBTYPE_CONSTRAINT">
\r
49 | <END_LOCAL:"END_LOCAL">
\r
51 | <ABSTRACT:"ABSTRACT">
\r
52 | <EXTENSIBLE:"EXTENSIBLE">
\r
53 | <GENERIC_ENTITY:"GENERIC_ENTITY">
\r
54 | <BASED_ON:"BASED_ON">
\r
56 | <SUBTYPE:"SUBTYPE">
\r
57 | <SUPERTYPE:"SUPERTYPE">
\r
64 | <REFERENCE:"REFERENCE">
\r
68 | <INVERSE:"INVERSE">
\r
69 | <OPTIONAL:"OPTIONAL">
\r
84 | <RENAMED:"RENAMED">
\r
86 | <STRING_:"STRING">
\r
87 | <INTEGER:"INTEGER">
\r
90 | <BOOLEAN:"BOOLEAN">
\r
91 | <LOGICAL:"LOGICAL">
\r
98 | <ENUMERATION:"ENUMERATION">
\r
99 | <GENERIC:"GENERIC">
\r
100 | <AGGREGATE:"AGGREGATE">
\r
103 | <RETURN: "RETURN">
\r
105 | <END_IF: "END_IF">
\r
108 | <REPEAT: "REPEAT">
\r
109 | <END_REPEAT: "END_REPEAT">
\r
115 | <END_CASE: "END_CASE">
\r
118 | <ESCAPE: "ESCAPE">
\r
122 | <STRING: "'" (~["'"])* "'">
\r
123 | <IDENT: ["a"-"z","A"-"Z"] (["a"-"z","A"-"Z","_","0"-"9"])* >
\r
124 | <INT: (["0"-"9"])+ >
\r
125 | <FLOAT: <INT> "." (<INT>)? (("e"|"E") ("+"|"-")? <INT>)? >
\r
130 void document() : {}
\r
131 { (schema())* <EOF>
\r
135 { <SCHEMA> <IDENT> ";"
\r
142 void interface_() : {}
\r
143 { <USE> <FROM> <IDENT> ( "(" references() ")" )? ";"
\r
144 | <REFERENCE> <FROM> <IDENT> ( "(" references() ")" )? ";"
\r
147 void references() : {}
\r
148 { reference() ("," reference())*
\r
151 void reference() : {}
\r
152 { <IDENT> (<AS> <IDENT>)?
\r
155 void constDecl() : {}
\r
156 { <CONSTANT> (<IDENT> ":" typeB() ":=" exp() ";")+ <END_CONSTANT> ";"
\r
164 void ruleDecl() : {}
\r
165 { <RULE> <IDENT> <FOR> "(" idents() ")" ";"
\r
177 | subtypeConstraintDecl()
\r
180 void entityDecl() : {}
\r
181 { <ENTITY> <IDENT> (supertype())? (subtype())? ";"
\r
182 (attributes() ":" (<OPTIONAL>)? typeB() ";")*
\r
183 (<DERIVE> (attribute() ":" typeB() ":=" exp() ";")+ )?
\r
184 (<INVERSE> (attribute() ":" typeI() <FOR> attribute() ";")+ )?
\r
185 (<UNIQUE> ( ( LOOKAHEAD(2) <IDENT> ":")? attributes() ";")+ )?
\r
190 void localDecls() : {}
\r
193 (<LOCAL> ( idents() ":" typeP() (":=" exp())* ";")+ <END_LOCAL> ";")?
\r
196 void functionDecl() : {}
\r
197 { <FUNCTION> <IDENT> ("(" parameter() (";" parameter())* ")")? ":" typeP() ";"
\r
203 void procedureDecl() : {}
\r
204 { <PROCEDURE> <IDENT> ("(" parameterP() (";" parameterP())* ")")? ";"
\r
207 <END_PROCEDURE> ";"
\r
210 void typeDecl() : {}
\r
211 { <TYPE> <IDENT> "=" typeU() ";" (where())? <END_TYPE> ";"
\r
214 void subtypeConstraintDecl() : {}
\r
215 { <SUBTYPE_CONSTRAINT> <IDENT> <FOR> <IDENT> ";"
\r
216 (<ABSTRACT> <SUPERTYPE> ";")?
\r
217 (supertypeExpression() ";")?
\r
218 <END_SUBTYPE_CONSTRAINT> ";"
\r
222 { <WHERE> ( ( LOOKAHEAD(2) <IDENT> ":")? exp() ";")+
\r
225 void parameter() : {}
\r
226 { idents() ":" typeP()
\r
229 void parameterP() : {}
\r
231 | <VAR> parameterP()
\r
234 void supertype() : {}
\r
235 { <SUPERTYPE> <OF> "(" supertypeExpression() ")"
\r
236 | <ABSTRACT> <SUPERTYPE> (<OF> "(" supertypeExpression() ")")?
\r
239 void supertypeExpression() : {}
\r
240 { supertypeExpression2() (<ANDOR> supertypeExpression2())*
\r
243 void supertypeExpression2() : {}
\r
244 { supertypeExpression3() (<AND> supertypeExpression3())*
\r
247 void subtype() : {}
\r
248 { <SUBTYPE> <OF> "(" idents() ")"
\r
251 void supertypeExpression3() : {}
\r
253 | <ONEOF> "(" supertypeExpression() ("," supertypeExpression())* ")"
\r
254 | "(" supertypeExpression() ")"
\r
257 void attribute() : {}
\r
259 | <SELF> "\\" <IDENT> "." <IDENT> (<RENAMED> <IDENT>)?
\r
262 void attributes() : {}
\r
263 { attribute() ("," attribute())*
\r
266 ExpType typeBI() : {}
\r
267 { <BOOLEAN> { return ExpBoolean.INSTANCE; }
\r
268 | <REAL> /* */ { return ExpReal.INSTANCE; }
\r
269 | <NUMBER> { return ExpNumber.INSTANCE; }
\r
270 | <BINARY> ( "(" exp1() ")")? ( <FIXED> )? { return ExpBinary.INSTANCE; }
\r
271 | <LOGICAL> { return ExpLogical.INSTANCE; }
\r
272 | <STRING_> ( "(" exp1() ")")? ( <FIXED> )? { return ExpString.INSTANCE; }
\r
273 | <INTEGER> { return ExpInteger.INSTANCE; }
\r
276 ExpType typeB() : { ExpType type; }
\r
277 { type=typeN() { return type; }
\r
278 | type=typeBI() { return type; }
\r
279 | type=typeA() { return type; }
\r
282 ExpType typeA() : { ExpType type; }
\r
283 { <BAG> bound() <OF> type=typeB() { return new ExpBag(type); }
\r
284 | <ARRAY> bound() <OF> (<OPTIONAL>)? (<UNIQUE>)? type=typeB() { return new ExpArray(type); }
\r
285 | <LIST> bound() <OF> (<UNIQUE>)? type=typeB() { return new ExpList(type); }
\r
286 | <SET> bound() <OF> type=typeB() { return new ExpSet(type); }
\r
289 ExpType typeI() : { ExpType type; }
\r
290 { type=typeN() { return type; }
\r
291 | <BAG> bound() <OF> type=typeN() { return new ExpBag(type); }
\r
292 | <SET> bound() <OF> type=typeN() { return new ExpSet(type); }
\r
295 ExpType typeN() : { Token tt; }
\r
296 { tt=<IDENT> { return new ExpTypeName(tt.image); }
\r
299 ExpType typeP() : { ExpType type; }
\r
300 { type=typeBI() { return type; }
\r
301 | type=typeN(){ return type; }
\r
302 | <BAG> bound() <OF> type=typeP() { return new ExpBag(type); }
\r
303 | <ARRAY> bound() <OF> (<OPTIONAL>)? (<UNIQUE>)? type=typeP() { return new ExpArray(type); }
\r
304 | <LIST> bound() <OF> (<UNIQUE>)? type=typeP() { return new ExpList(type); }
\r
305 | <SET> bound() <OF> type=typeP() { return new ExpSet(type); }
\r
306 | <GENERIC> (":" <IDENT>)? { return ExpGeneric.INSTANCE; }
\r
307 | <GENERIC_ENTITY> { return ExpGenericEntity.INSTANCE; }
\r
308 | <AGGREGATE> (":" <IDENT>)? <OF> type=typeP() { return new ExpAggregate(type); }
\r
311 ExpType typeU() : {}
\r
312 { { ExpType type; } type=typeB() { return type; }
\r
313 | LOOKAHEAD(3) (<EXTENSIBLE>)? (<GENERIC_ENTITY>)? <SELECT>
\r
314 (<BASED_ON> <IDENT> (<WITH> "(" idents() ")")?
\r
316 )? { return new ExpSelect(); }
\r
317 | LOOKAHEAD(3) (<EXTENSIBLE>)? (<GENERIC_ENTITY>)? <ENUMERATION>
\r
318 (<BASED_ON> <IDENT> (<WITH> "(" idents() ")")?
\r
319 | <OF> "(" idents() ")"
\r
320 )? { return new ExpEnumeration(); }
\r
324 { ("[" exp1() ":" exp1() "]")?
\r
327 ExpExpression exp() : { ExpExpression exp; }
\r
329 ( {ExpExpression exp2; String op;} op=op0() exp2=exp1()
\r
330 { exp = new ExpBinaryExpression(exp, op, exp2); } )?
\r
335 { ">" { return ">"; }
\r
336 | "<" { return "<"; }
\r
337 | ">=" { return ">="; }
\r
338 | "<=" { return "<="; }
\r
339 | ":=:" { return ":=:"; }
\r
340 | ":<>:" { return ":<>:"; }
\r
341 | "=" { return "="; }
\r
342 | "<>" { return "<>"; }
\r
343 | <LIKE> { return "like"; }
\r
344 | <IN> { return "in"; }
\r
347 ExpExpression exp1() : { ExpExpression exp; }
\r
349 ( {ExpExpression exp2; String op;} op=op1() exp2=exp2()
\r
350 { exp = new ExpBinaryExpression(exp, op, exp2); }
\r
356 { <OR> { return "or"; }
\r
357 | <XOR> { return "xor"; }
\r
358 | "+" { return "+"; }
\r
359 | "-" { return "-"; }
\r
362 ExpExpression exp2() : { ExpExpression exp; }
\r
364 ( {ExpExpression exp2; String op;} op=op2() exp2=exp3()
\r
365 { exp = new ExpBinaryExpression(exp, op, exp2); }
\r
371 { <AND> { return "and"; }
\r
372 | <MOD> { return "mod"; }
\r
373 | <DIV> { return "div"; }
\r
374 | "*" { return "*"; }
\r
375 | "/" { return "/"; }
\r
376 | "||" { return "||"; }
\r
379 ExpExpression exp3() : { ExpExpression exp; }
\r
381 ( {ExpExpression exp2;} "**" exp2=exp4()
\r
382 { exp = new ExpBinaryExpression(exp, "**", exp2); }
\r
387 ExpExpression exp4() : { ExpExpression exp; }
\r
388 { "[" (exp() (":" exp())? ("," exp() (":" exp())?)* )? "]" { return null; }
\r
389 | <QUERY> "(" <IDENT> "<*" exp1() "|" exp() ")" { return null; }
\r
390 | "{" exp1() ("<" | "<=") exp1() ("<" | "<=") exp1() "}" { return null; }
\r
391 | "+" exp=exp5() { return new ExpUnaryExpression(exp, "+"); }
\r
392 | "-" exp=exp5() { return new ExpUnaryExpression(exp, "-"); }
\r
393 | <NOT> exp=exp5() { return new ExpUnaryExpression(exp, "not"); }
\r
394 | exp=exp5() { return exp; }
\r
397 ExpExpression exp5() : { Token tt; ExpExpression exp; }
\r
398 { tt=<INT> { return new ExpIntegerLiteral(tt.image); }
\r
399 | "(" exp=exp() ")" { return exp; }
\r
400 | "?" { return ExpQuestionMark.INSTANCE; }
\r
401 | <SELF> exp=quals(ExpQuestionMark.INSTANCE) { return exp; }
\r
402 | <IDENT> ("(" (exp() ("," exp())*)? ")")? quals(null) { return null; }
\r
403 | tt=<STRING> { return new ExpStringLiteral(tt.image.substring(1, tt.image.length()-1)); }
\r
404 | tt=<FLOAT> { return new ExpFloatLiteral(tt.image); }
\r
405 | <TRUE> { return ExpBooleanLiteral.TRUE; }
\r
406 | <FALSE> { return ExpBooleanLiteral.FALSE; }
\r
410 ExpExpression quals(ExpExpression base) : {}
\r
413 | "[" exp() (":" exp1())? "]"
\r
414 )* { return base; }
\r
417 void statement() : {}
\r
418 { <RETURN> (exp1())? ";"
\r
419 | <IF> exp() <THEN> (statement())+ (<ELSE> (statement())+)? <END_IF> ";"
\r
420 | LOOKAHEAD(2) <IDENT> quals(null) ":=" exp() ";"
\r
422 (<IDENT> ":=" exp1() <TO> exp1() (<BY> exp2())?)?
\r
424 (<UNTIL> exp())? ";"
\r
425 (statement())+ <END_REPEAT> ";"
\r
426 | <CASE> exp() <OF> ( exp() ("," exp())* ":" statement() )* <END_CASE> ";"
\r
427 | <BEGIN> (statement())+ <END> ";"
\r
430 | LOOKAHEAD(2) <IDENT> "(" (exp() ("," exp())*)? ")" ";"
\r
435 String[] idents() : { List<String> idents = new ArrayList<String>(2); Token tt; }
\r
436 { tt=<IDENT> { idents.add(tt.image); } ("," tt=<IDENT> { idents.add(tt.image); })*
\r
437 { return idents.toArray(new String[idents.size()]); }
\r