aboutsummaryrefslogtreecommitdiffstats
path: root/cparser/pre_parser.mly
diff options
context:
space:
mode:
authorFrançois Pottier <francois.pottier@inria.fr>2015-10-07 10:49:42 +0200
committerFrançois Pottier <francois.pottier@inria.fr>2015-10-07 10:49:42 +0200
commit09527e66514edcfa20a0341acd75c1fe6fd77363 (patch)
treec0983f011758c1d8cbe3ad748a3f157a89bf6d6d /cparser/pre_parser.mly
parentc1937e330a3ca6c19ef648e2dcfe4871fc3c2219 (diff)
downloadcompcert-kvx-09527e66514edcfa20a0341acd75c1fe6fd77363.tar.gz
compcert-kvx-09527e66514edcfa20a0341acd75c1fe6fd77363.zip
Introduced optional(X, Y), which means X? Y, and used it in array declarators and FOR loops.
This leads to fewer automaton states, and potentially better error messages.
Diffstat (limited to 'cparser/pre_parser.mly')
-rw-r--r--cparser/pre_parser.mly16
1 files changed, 12 insertions, 4 deletions
diff --git a/cparser/pre_parser.mly b/cparser/pre_parser.mly
index 497851bf..62a57618 100644
--- a/cparser/pre_parser.mly
+++ b/cparser/pre_parser.mly
@@ -97,6 +97,14 @@ option(X):
| x = X
{ Some x }
+(* [optional(X, Y)] is equivalent to [X? Y]. However, by inlining
+ the two possibilies -- either [X Y] or just [Y] -- we are able
+ to give more meaningful syntax error messages. [optional(X, Y)]
+ itself is usually NOT inlined, as that would cause a useless
+ explosion of cases. *)
+optional(X, Y):
+ ioption(X) Y {}
+
%inline fst(X):
| x = X
{ fst x }
@@ -537,7 +545,7 @@ direct_declarator:
| i = general_identifier
{ set_id_type i VarId; (i, None) }
| LPAREN x = declarator RPAREN
-| x = direct_declarator LBRACK type_qualifier_list? assignment_expression? RBRACK
+| x = direct_declarator LBRACK type_qualifier_list? optional(assignment_expression, RBRACK)
{ x }
| x = direct_declarator LPAREN
open_context parameter_type_list? restore_fun = save_contexts_stk
@@ -583,7 +591,7 @@ abstract_declarator:
direct_abstract_declarator:
| LPAREN abstract_declarator RPAREN
-| option(direct_abstract_declarator) LBRACK type_qualifier_list? assignment_expression? RBRACK
+| option(direct_abstract_declarator) LBRACK type_qualifier_list? optional(assignment_expression, RBRACK)
| ioption(direct_abstract_declarator) LPAREN in_context(parameter_type_list?) RPAREN
{}
@@ -764,8 +772,8 @@ iteration_statement(openc,last_statement):
| WHILE openc LPAREN expression RPAREN last_statement
| DO open_context statement_finish_close WHILE
openc LPAREN expression RPAREN close_context SEMICOLON
-| FOR openc LPAREN expression? SEMICOLON expression? SEMICOLON expression? RPAREN last_statement
-| FOR openc LPAREN declaration expression? SEMICOLON expression? RPAREN last_statement
+| FOR openc LPAREN optional(expression, SEMICOLON) optional(expression, SEMICOLON) optional(expression, RPAREN) last_statement
+| FOR openc LPAREN declaration optional(expression, SEMICOLON) optional(expression, RPAREN) last_statement
{}
asm_attributes: