Release coccinelle-0.2.0rc1
[bpt/coccinelle.git] / parsing_cocci / parser_cocci.mly
CommitLineData
34e49164
C
1%{
2
3(* Not clear how to allow function declarations to specify a return type
4and how to allow both to be specified as static, because they are in
5different rules. The rules seem to have to be combined, which would allow
6functions to be declared as local variables *)
7
8(* Not clear how to let a function have a parameter of type void. At the
9moment, void is allowed to be the type of a variable, which is wrong, and a
10parameter needs both a type and an identifier *)
11
12module Ast0 = Ast0_cocci
13module Ast = Ast_cocci
14
faf9a90c
C
15(*let warning s v =
16 if !Flag.verbose_parsing
34e49164
C
17 then Common.warning s v
18 else v*)
19
20let make_info line logical_line =
21 { Ast.line = line; Ast.logical_line = logical_line }
22
23let clt2info (_,line,logical_line) = make_info line logical_line
24
25let clt2mcode str = function
26 (Data.MINUS,line,lline) ->
27 (str,Ast0.NONE,
28 (Ast.MINUS({Ast.line=line;Ast.logical_line=lline},ref[])))
29 | (Data.OPTMINUS,line,lline) ->
30 (str,Ast0.OPT,
31 (Ast.MINUS({Ast.line=line;Ast.logical_line=lline},ref[])))
32 | (Data.UNIQUEMINUS,line,lline) ->
33 (str,Ast0.UNIQUE,
34 (Ast.MINUS({Ast.line=line;Ast.logical_line=lline},ref[])))
35 | (Data.MULTIMINUS,line,lline) ->
36 (str,Ast0.MULTI,
37 (Ast.MINUS({Ast.line=line;Ast.logical_line=lline},ref[])))
38 | (Data.PLUS,line,lline) ->
39 (str,Ast0.NONE,Ast.PLUS({Ast.line=line;Ast.logical_line=lline}))
40 | (Data.CONTEXT,line,lline) ->
41 (str,Ast0.NONE,
42 Ast.CONTEXT({Ast.line=line;Ast.logical_line=lline},ref Ast.NOTHING))
43 | (Data.OPT,line,lline) ->
44 (str,Ast0.OPT,
45 Ast.CONTEXT({Ast.line=line;Ast.logical_line=lline},ref Ast.NOTHING))
46 | (Data.UNIQUE,line,lline) ->
47 (str,Ast0.UNIQUE,
48 Ast.CONTEXT({Ast.line=line;Ast.logical_line=lline},ref Ast.NOTHING))
49 | (Data.MULTI,line,lline) ->
50 (str,Ast0.MULTI,
51 Ast.CONTEXT({Ast.line=line;Ast.logical_line=lline},ref Ast.NOTHING))
52
53let id2name (name, clt) = name
54let id2clt (name, clt) = clt
55let id2info (name, clt) = clt2info clt
56let id2mcode (name, clt) = clt2mcode name clt
57
58let arith_op ast_op left op right =
59 Ast0.Binary(left, clt2mcode (Ast.Arith ast_op) op, right)
60
61let logic_op ast_op left op right =
62 Ast0.Binary(left, clt2mcode (Ast.Logical ast_op) op, right)
63
64let top_dots l =
65 if List.exists (function Ast0.Circles(_) -> true | _ -> false) l
66 then Ast0.CIRCLES(l)
67 else if List.exists (function Ast0.Stars(_) -> true | _ -> false) l
68 then Ast0.STARS(l)
69 else Ast0.DOTS(l)
70
71%}
72
73
74%token EOF
75
76%token TIdentifier TExpression TStatement TFunction TLocal TType TParameter
77%token TWhy0 TPlus0 TBang0 Tlist TFresh TConstant TError TWords
78
79%token<Data.line_type * int * int> Tchar Tshort Tint Tdouble Tfloat Tlong Tvoid
80%token<Data.line_type * int * int> Tstruct Tunion
81%token<Data.line_type * int * int> Tunsigned Tsigned
82
83%token<Data.line_type * int * int> Tstatic Tconst Tvolatile
84
85%token <Data.line_type * int * int> TIf TElse TWhile TFor TDo TReturn
86%token <string * (Data.line_type * int * int)> TIdent TFunName TMetaFunName
87%token <string * (Data.line_type * int * int)> TMetaId TMetaType TMetaErr
88%token <string * (Data.line_type * int * int)> TMetaParam TMetaParamList
89%token <string * (Data.line_type * int * int)> TMetaStm TMetaStmList TMetaFunc
90%token <string * (Data.line_type * int * int)> TMetaLocalFunc TMetaExpList
91%token <string * Ast0_cocci.fullType list option * (Data.line_type*int*int)>
92TMetaExp TMetaConst
93%token TArobArob
94
95%token <Data.line_type * int * int> TEllipsis TOEllipsis TCEllipsis
96%token <Data.line_type * int * int> TWhen
97%token TLineEnd
98%token <Data.line_type * int * int> TCircles TOCircles TCCircles
99%token <Data.line_type * int * int> TStars TOStars TCStars
100
101%token <Data.line_type * int * int> TWhy TDotDot TBang TOPar TOPar0 TMid
102%token <Data.line_type * int * int> TMid0 TCPar TCPar0
103
104%token <string * (Data.line_type * int * int)> TInclude TMinusFile TPlusFile
105
106%token <Data.line_type * int * int> TInc TDec
107
108%token <string * (Data.line_type * int * int)> TString TChar TFloat TInt
109
110%token <Data.line_type * int * int> TOrLog
111%token <Data.line_type * int * int> TAndLog
112%token <Data.line_type * int * int> TOr
113%token <Data.line_type * int * int> TXor
faf9a90c 114%token <Data.line_type * int * int> TAnd
34e49164 115%token <Data.line_type * int * int> TEqEq TNotEq
faf9a90c 116%token <Data.line_type * int * int> TInf TSup TInfEq TSupEq
34e49164
C
117%token <Data.line_type * int * int> TShl TShr
118%token <Data.line_type * int * int> TPlus TMinus
faf9a90c 119%token <Data.line_type * int * int> TMul TDiv TMod
34e49164
C
120
121%token <Data.line_type * int * int> TOBrace TCBrace
122%token <Data.line_type * int * int> TOCro TCCro
123
124%token <Data.line_type * int * int> TPtrOp
125
126%token <Data.line_type * int * int> TEq TDot TComma TPtVirg
127%token <Ast_cocci.assignOp * (Data.line_type * int * int)> TAssign
128
129/* operator precedence */
130%nonassoc TIf
131%nonassoc TElse
132
133%left TOrLog
134%left TAndLog
135%left TOr
136%left TXor
faf9a90c 137%left TAnd
34e49164 138%left TEqEq TNotEq
faf9a90c 139%left TInf TSup TInfEq TSupEq
34e49164
C
140%left TShl TShr
141%left TPlus TMinus
faf9a90c 142%left TMul TDiv TMod
34e49164 143
faf9a90c 144%start main
34e49164
C
145%type <Ast0_cocci.rule> main
146
147%start meta_main
148%type <Ast_cocci.metavar list> meta_main
149
150
151
152%%
153
154main: body EOF { $1 } | body TArobArob { $1 }
155meta_main: meta_var_list_opt TArobArob { $1 }
156
157/*****************************************************************************
158*
159*
160*****************************************************************************/
161
162meta_var:
163 arity TIdentifier pure_ident_or_meta_ident_list TPtVirg
164 { List.map
165 (function name ->
166 !Data.add_id_meta name;
167 Ast.MetaIdDecl($1,name))
168 $3 }
169| arity TFresh TIdentifier pure_ident_or_meta_ident_list TPtVirg
170 { List.map
171 (function name ->
172 !Data.add_id_meta name;
173 Ast.MetaFreshIdDecl($1,name))
174 $4 }
175| arity TType pure_ident_or_meta_ident_list TPtVirg
176 { List.map
177 (function name ->
178 !Data.add_type_meta name;
179 Ast.MetaTypeDecl($1,name))
faf9a90c 180 $3 }
34e49164
C
181| arity TParameter pure_ident_or_meta_ident_list TPtVirg
182 { List.map
183 (function name ->
184 !Data.add_param_meta name;
185 Ast.MetaParamDecl($1,name))
faf9a90c 186 $3 }
34e49164
C
187| arity TParameter Tlist pure_ident_or_meta_ident_list TPtVirg
188 { List.map
189 (function name ->
190 !Data.add_paramlist_meta name;
191 Ast.MetaParamListDecl($1,name))
faf9a90c 192 $4 }
34e49164
C
193| arity TError pure_ident_or_meta_ident_list TPtVirg
194 { List.map
195 (function name ->
196 !Data.add_err_meta name;
197 Ast.MetaErrDecl($1,name))
198 $3 }
199| arity TExpression pure_ident_or_meta_ident_list TPtVirg
200 { List.map
201 (function name ->
202 !Data.add_exp_meta None name;
203 Ast.MetaExpDecl($1,name))
204 $3 }
205| arity TExpression Tlist pure_ident_or_meta_ident_list TPtVirg
206 { List.map
207 (function name ->
208 !Data.add_explist_meta name;
209 Ast.MetaExpListDecl($1,name))
210 $4 }
211| arity TStatement pure_ident_or_meta_ident_list TPtVirg
212 { List.map
213 (function name ->
214 !Data.add_stm_meta name;
215 Ast.MetaStmDecl($1,name))
216 $3 }
217| arity TStatement Tlist pure_ident_or_meta_ident_list TPtVirg
218 { List.map
219 (function name ->
220 !Data.add_stmlist_meta name;
221 Ast.MetaStmListDecl($1,name))
222 $4 }
223| arity TFunction pure_ident_or_meta_ident_list TPtVirg
224 { List.map
225 (function name ->
226 !Data.add_func_meta name;
227 Ast.MetaFuncDecl($1,name))
228 $3 }
229| arity TLocal TFunction pure_ident_or_meta_ident_list TPtVirg
230 { List.map
231 (function name ->
232 !Data.add_local_func_meta name;
233 Ast.MetaLocalFuncDecl($1,name))
234 $4 }
235| arity meta_exp_type pure_ident_or_meta_ident_list TPtVirg
236 { List.map
237 (function name ->
238 !Data.add_exp_meta (Some $2) name;
239 Ast.MetaExpDecl($1,name))
240 $3 }
241| arity TConstant meta_exp_type pure_ident_or_meta_ident_list TPtVirg
242 { List.map
243 (function name ->
244 !Data.add_const_meta (Some $3) name;
245 Ast.MetaConstDecl($1,name))
246 $4 }
247| arity TConstant pure_ident_or_meta_ident_list TPtVirg
248 { List.map
249 (function name ->
250 !Data.add_const_meta None name;
251 Ast.MetaConstDecl($1,name))
252 $3 }
253
254meta_exp_type:
255 ctype { [$1] }
256| TOBrace ctype_list TCBrace { $2 }
257
258arity: TBang0 { Ast.UNIQUE }
259 | TWhy0 { Ast.OPT }
260 | TPlus0 { Ast.MULTI }
261 | /* empty */ { Ast.NONE }
262
263ctype: Tvoid
264 { Ast0.BaseType(clt2mcode Ast.VoidType $1, None) }
265 | ctype_qualif Tchar
266 { Ast0.BaseType(clt2mcode Ast.CharType $2, $1) }
267 | ctype_qualif Tshort
268 { Ast0.BaseType(clt2mcode Ast.ShortType $2, $1) }
269 | ctype_qualif Tint
270 { Ast0.BaseType(clt2mcode Ast.IntType $2, $1) }
271 | Tdouble
272 { Ast0.BaseType(clt2mcode Ast.DoubleType $1, None) }
273 | Tfloat
274 { Ast0.BaseType(clt2mcode Ast.FloatType $1, None) }
275 | ctype_qualif Tlong
276 { Ast0.BaseType(clt2mcode Ast.LongType $2, $1) }
277 | Tstruct pure_ident
278 { Ast0.StructUnionName(id2mcode $2,clt2mcode Ast.Struct $1) }
279 | Tunion pure_ident
280 { Ast0.StructUnionName(id2mcode $2,clt2mcode Ast.Union $1) }
281 | ctype TMul
282 { Ast0.Pointer($1,clt2mcode "*" $2) }
283 | TMetaType
284 { let (nm,clt) = $1 in Ast0.MetaType(clt2mcode nm clt) }
285
286ctype_qualif:
287 Tunsigned
288 { Some (clt2mcode Ast.Unsigned $1) }
289 | Tsigned
290 { Some (clt2mcode Ast.Signed $1) }
291 | /* empty */ { None }
292
293param_ctype:
294 Tvoid
295 { Ast0.BaseType(clt2mcode Ast.VoidType $1, None) }
296 | ctype_qualif Tchar
297 { Ast0.BaseType(clt2mcode Ast.CharType $2, $1) }
298 | ctype_qualif Tshort
299 { Ast0.BaseType(clt2mcode Ast.ShortType $2, $1) }
300 | ctype_qualif Tint
301 { Ast0.BaseType(clt2mcode Ast.IntType $2, $1) }
302 | Tdouble
303 { Ast0.BaseType(clt2mcode Ast.DoubleType $1, None) }
304 | Tfloat
305 { Ast0.BaseType(clt2mcode Ast.FloatType $1, None) }
306 | ctype_qualif Tlong
307 { Ast0.BaseType(clt2mcode Ast.LongType $2, $1) }
308 | Tstruct pure_ident
309 { Ast0.StructUnionName(id2mcode $2,clt2mcode Ast.Struct $1) }
310 | Tunion pure_ident
311 { Ast0.StructUnionName(id2mcode $2,clt2mcode Ast.Union $1) }
312 | pure_ident { Ast0.TypeName(id2mcode $1) }
313 | param_ctype TMul { Ast0.Pointer($1,clt2mcode "*" $2) }
314 | TMetaType
315 { let (nm,clt) = $1 in Ast0.MetaType(clt2mcode nm clt) }
316
317/*****************************************************************************/
318
319/* have to inline everything to avoid conflicts? switch to proper
320declarations, statements, and expressions for the subterms */
321
322body: function_decl_statement_or_expression { Top_level.top_level $1 }
323 | /* empty */ { [] }
324
325/*****************************************************************************/
326
327fundecl:
328 storage TFunName TOPar decl_list TCPar
329 TOBrace pre_post_decl_statement_and_expression_opt TCBrace
330 { Ast0.FunDecl($1, Ast0.Id(id2mcode $2), clt2mcode "(" $3, $4,
331 clt2mcode ")" $5, clt2mcode "{" $6, $7,
332 clt2mcode "}" $8) }
333| storage TMetaFunName TOPar decl_list TCPar
334 TOBrace pre_post_decl_statement_and_expression_opt TCBrace
335 { Ast0.FunDecl($1, Ast0.MetaFunc(id2mcode $2), clt2mcode "(" $3, $4,
336 clt2mcode ")" $5, clt2mcode "{" $6, $7,
337 clt2mcode "}" $8) }
338
339storage: Tstatic { Some (clt2mcode Ast.Static $1) }
340 | /* empty */ { None }
341
342decl: decl_qualif param_ctype ident
343 { Ast0.Param($3, $1, $2) }
344 | TMetaParam
345 { let (nm,clt) = $1 in Ast0.MetaParam(clt2mcode nm clt) }
346
347decl_qualif:
348 Tconst { Some (clt2mcode Ast.Const $1) }
349 | Tvolatile { Some (clt2mcode Ast.Volatile $1) }
350 | /* empty */ { None }
351
352/*****************************************************************************/
353
354statement:
355 TMetaStm
356 { let (nm,clt) = $1 in Ast0.MetaStmt(clt2mcode nm clt) }
357| expr TPtVirg
358 { Ast0.ExprStatement ($1, clt2mcode ";" $2) }
359| TIf TOPar eexpr TCPar single_statement %prec TIf
360 { Ast0.IfThen(clt2mcode "if" $1,
361 clt2mcode "(" $2,$3,clt2mcode ")" $4,$5) }
362| TIf TOPar eexpr TCPar single_statement TElse single_statement
363 { Ast0.IfThenElse(clt2mcode "if" $1,
364 clt2mcode "(" $2,$3,clt2mcode ")" $4,$5,
365 clt2mcode "else" $6,$7) }
366| TFor TOPar eexpr_opt TPtVirg eexpr_opt TPtVirg eexpr_opt TCPar
367 single_statement
368 { Ast0.For(clt2mcode "for" $1,clt2mcode "(" $2,$3,
369 clt2mcode ";" $4,$5,clt2mcode ";" $6,$7,clt2mcode ")" $8,$9) }
370| TWhile TOPar eexpr TCPar single_statement
371 { Ast0.While(clt2mcode "while" $1,
372 clt2mcode "(" $2,$3,clt2mcode ")" $4,$5) }
373| TDo single_statement TWhile TOPar eexpr TCPar TPtVirg
374 { Ast0.Do(clt2mcode "do" $1,$2,clt2mcode "while" $3,
375 clt2mcode "(" $4,$5,clt2mcode ")" $6, clt2mcode ";" $7) }
376| TReturn eexpr TPtVirg
377 { Ast0.ReturnExpr(clt2mcode "return" $1,$2,clt2mcode ";" $3) }
378| TReturn TPtVirg
379 { Ast0.Return(clt2mcode "return" $1,clt2mcode ";" $2) }
380| TOBrace pre_post_decl_statement_and_expression_opt TCBrace
381 { Ast0.Seq(clt2mcode "{" $1,$2,clt2mcode "}" $3) }
382| TOEllipsis decl_statement_or_expression_dots TCEllipsis
383 { Ast0.Nest(Ast0.DOTS($2)) }
384| TOCircles decl_statement_or_expression_circles TCCircles
385 { Ast0.Nest(Ast0.CIRCLES($2)) }
386| TOStars decl_statement_or_expression_stars TCStars
387 { Ast0.Nest(Ast0.STARS($2)) }
388
389/* In the following, an identifier as a type is not fully supported. Indeed,
390the language is ambiguous: what is foo * bar; */
391decl_var: ctype d_ident_list TPtVirg
392 { (List.map
393 (function (id,fn) -> Ast0.UnInit(fn $1,id,clt2mcode ";" $3))
394 $2) }
395 | ctype d_ident TEq eexpr TPtVirg
396 { let (id,fn) = $2 in
397 [Ast0.Init(fn $1,id,clt2mcode "=" $3,$4,clt2mcode ";" $5)] }
398 | pure_ident d_ident TPtVirg
399 { let (id,fn) = $2 in
400 [Ast0.UnInit(fn (Ast0.TypeName(id2mcode $1)),id,clt2mcode ";" $3)] }
401 | pure_ident d_ident TEq eexpr TPtVirg
402 { let (id,fn) = $2 in
403 [Ast0.Init(fn(Ast0.TypeName(id2mcode $1)),id,
404 clt2mcode "=" $3,$4,clt2mcode ";" $5)] }
405
406d_ident:
407 ident
408 { ($1,function x -> x) }
409 | ident TOCro eexpr_opt TCCro
410 { ($1,function x -> Ast0.Array(x,clt2mcode "[" $2,$3,clt2mcode "]" $4)) }
411
412/* a statement on its own */
413single_statement:
414 statement { $1 }
415 | TOPar0 statement_mid TCPar0
416 { Ast0.Disj($2) }
417
418/* a statement that is part of a list */
419decl_statement:
420 TMetaStmList
421 { let (nm,clt) = $1 in [Ast0.MetaStmt(clt2mcode nm clt)] }
422 | decl_var
423 { List.map (function x -> Ast0.Decl(x)) $1 }
424 | statement { [$1] }
425 | TOPar0 pre_post_decl_statement_and_expression_opt_mid TCPar0
426 { if List.for_all (function Ast0.DOTS([]) -> true | _ -> false) $2
427 then []
428 else [Ast0.Disj($2)] }
429
430/*****************************************************************************/
431
432
433/*****************************************************************************/
434/* The following cannot contain <... ...> at the top level. This can only
435be allowed as an expression when the expression is delimited on both sides
436by expression-specific markers. In that case, the rule eexpr is used, which
437allows <... ...> anywhere. Hopefully, this will not be too much of a problem
438in practice. */
439
440expr: assign_expr { $1 }
441
442assign_expr:
443 cond_expr { $1 }
444 | unary_expr TAssign assign_expr
445 { let (op,clt) = $2 in Ast0.Assignment($1,clt2mcode op clt,$3) }
446 | unary_expr TEq assign_expr
447 { Ast0.Assignment($1,clt2mcode Ast.SimpleAssign $2,$3) }
448
449cond_expr: arith_expr { $1 }
450 | arith_expr TWhy eexpr_opt TDotDot cond_expr
451 { Ast0.CondExpr ($1, clt2mcode "?" $2, $3, clt2mcode "?" $4, $5) }
452
453arith_expr: cast_expr { $1 }
454 | arith_expr TMul arith_expr { arith_op Ast.Mul $1 $2 $3 }
455 | arith_expr TDiv arith_expr { arith_op Ast.Div $1 $2 $3 }
456 | arith_expr TMod arith_expr { arith_op Ast.Mod $1 $2 $3 }
457 | arith_expr TPlus arith_expr { arith_op Ast.Plus $1 $2 $3 }
458 | arith_expr TMinus arith_expr { arith_op Ast.Minus $1 $2 $3 }
459 | arith_expr TShl arith_expr { arith_op Ast.DecLeft $1 $2 $3 }
460 | arith_expr TShr arith_expr { arith_op Ast.DecRight $1 $2 $3 }
461 | arith_expr TInf arith_expr { logic_op Ast.Inf $1 $2 $3 }
462 | arith_expr TSup arith_expr { logic_op Ast.Sup $1 $2 $3 }
463 | arith_expr TInfEq arith_expr { logic_op Ast.InfEq $1 $2 $3 }
464 | arith_expr TSupEq arith_expr { logic_op Ast.SupEq $1 $2 $3 }
465 | arith_expr TEqEq arith_expr { logic_op Ast.Eq $1 $2 $3 }
466 | arith_expr TNotEq arith_expr { logic_op Ast.NotEq $1 $2 $3 }
467 | arith_expr TAnd arith_expr { arith_op Ast.And $1 $2 $3 }
468 | arith_expr TOr arith_expr { arith_op Ast.Or $1 $2 $3 }
469 | arith_expr TXor arith_expr { arith_op Ast.Xor $1 $2 $3 }
470 | arith_expr TAndLog arith_expr { logic_op Ast.AndLog $1 $2 $3 }
471 | arith_expr TOrLog arith_expr { logic_op Ast.OrLog $1 $2 $3 }
472
473cast_expr: unary_expr { $1 }
474 | TOPar ctype TCPar cast_expr
475 { Ast0.Cast (clt2mcode "(" $1, $2, clt2mcode ")" $3, $4) }
476
477unary_expr: postfix_expr { $1 }
478 | TInc unary_expr
479 { Ast0.Infix ($2, clt2mcode Ast.Inc $1) }
480 | TDec unary_expr
481 { Ast0.Infix ($2, clt2mcode Ast.Dec $1) }
482 | unary_op unary_expr
483 { let mcode = $1 in Ast0.Unary($2, mcode) }
484
485unary_op: TAnd { clt2mcode Ast.GetRef $1 }
486 | TMul { clt2mcode Ast.DeRef $1 }
487 | TPlus { clt2mcode Ast.UnPlus $1 }
488 | TMinus { clt2mcode Ast.UnMinus $1 }
489 | TBang { clt2mcode Ast.Not $1 }
490
491postfix_expr: primary_expr { $1 }
492 | postfix_expr TOCro eexpr TCCro
493 { Ast0.ArrayAccess ($1,clt2mcode "[" $2,$3,clt2mcode "]" $4) }
494 | postfix_expr TDot ident
495 { Ast0.RecordAccess($1, clt2mcode "." $2, $3) }
496 | postfix_expr TPtrOp ident
497 { Ast0.RecordPtAccess($1, clt2mcode "->" $2, $3) }
498 | postfix_expr TInc
499 { Ast0.Postfix ($1, clt2mcode Ast.Inc $2) }
500 | postfix_expr TDec
501 { Ast0.Postfix ($1, clt2mcode Ast.Dec $2) }
502 | postfix_expr TOPar eexpr_list_opt TCPar
503 { Ast0.FunCall($1,clt2mcode "(" $2,$3,clt2mcode ")" $4) }
504
505primary_expr: ident { Ast0.Ident($1) }
506 | TInt
507 { let (x,clt) = $1 in
508 Ast0.Constant (clt2mcode (Ast.Int x) clt) }
509 | TFloat
510 { let (x,clt) = $1 in
511 Ast0.Constant (clt2mcode (Ast.Float x) clt) }
512 | TString
513 { let (x,clt) = $1 in
514 Ast0.Constant (clt2mcode (Ast.String x) clt) }
515 | TChar
516 { let (x,clt) = $1 in
517 Ast0.Constant (clt2mcode (Ast.Char x) clt) }
518 | TMetaConst
519 { let (nm,ty,clt) = $1 in Ast0.MetaConst(clt2mcode nm clt,ty) }
520 | TMetaErr
521 { let (nm,clt) = $1 in Ast0.MetaErr(clt2mcode nm clt) }
522 | TMetaExp
523 { let (nm,ty,clt) = $1 in Ast0.MetaExpr(clt2mcode nm clt,ty) }
524 | TOPar eexpr TCPar
525 { Ast0.Paren(clt2mcode "(" $1,$2,clt2mcode ")" $3) }
526 | TOPar0 expr_mid TCPar0 { Ast0.DisjExpr($2) }
527
528/*****************************************************************************/
529
530eexpr: eassign_expr { $1 }
531
532eassign_expr: econd_expr { $1 }
533 | eunary_expr TAssign eassign_expr
534 { let (op,clt) = $2 in
535 Ast0.Assignment($1,clt2mcode op clt,$3) }
536 | eunary_expr TEq eassign_expr
537 { Ast0.Assignment($1,clt2mcode Ast.SimpleAssign $2,$3) }
538
faf9a90c 539econd_expr: earith_expr { $1 }
34e49164
C
540 | earith_expr TWhy eexpr_opt TDotDot econd_expr
541 { Ast0.CondExpr ($1, clt2mcode "?" $2, $3, clt2mcode "?" $4, $5) }
542
543earith_expr: ecast_expr { $1 }
544 | earith_expr TMul earith_expr { arith_op Ast.Mul $1 $2 $3 }
545 | earith_expr TDiv earith_expr { arith_op Ast.Div $1 $2 $3 }
546 | earith_expr TMod earith_expr { arith_op Ast.Mod $1 $2 $3 }
547 | earith_expr TPlus earith_expr { arith_op Ast.Plus $1 $2 $3 }
548 | earith_expr TMinus earith_expr { arith_op Ast.Minus $1 $2 $3 }
549 | earith_expr TShl earith_expr { arith_op Ast.DecLeft $1 $2 $3 }
550 | earith_expr TShr earith_expr { arith_op Ast.DecRight $1 $2 $3 }
551 | earith_expr TInf earith_expr { logic_op Ast.Inf $1 $2 $3 }
552 | earith_expr TSup earith_expr { logic_op Ast.Sup $1 $2 $3 }
553 | earith_expr TInfEq earith_expr { logic_op Ast.InfEq $1 $2 $3 }
554 | earith_expr TSupEq earith_expr { logic_op Ast.SupEq $1 $2 $3 }
555 | earith_expr TEqEq earith_expr { logic_op Ast.Eq $1 $2 $3 }
556 | earith_expr TNotEq earith_expr { logic_op Ast.NotEq $1 $2 $3 }
557 | earith_expr TAnd earith_expr { arith_op Ast.And $1 $2 $3 }
558 | earith_expr TOr earith_expr { arith_op Ast.Or $1 $2 $3 }
559 | earith_expr TXor earith_expr { arith_op Ast.Xor $1 $2 $3 }
560 | earith_expr TAndLog earith_expr { logic_op Ast.AndLog $1 $2 $3 }
561 | earith_expr TOrLog earith_expr { logic_op Ast.OrLog $1 $2 $3 }
562
563ecast_expr: eunary_expr { $1 }
564 | TOPar ctype TCPar ecast_expr
565 { Ast0.Cast (clt2mcode "(" $1, $2, clt2mcode ")" $3, $4) }
566
567eunary_expr: epostfix_expr { $1 }
568 | TInc eunary_expr
569 { Ast0.Infix ($2, clt2mcode Ast.Inc $1) }
570 | TDec eunary_expr
571 { Ast0.Infix ($2, clt2mcode Ast.Dec $1) }
572 | unary_op eunary_expr
573 { let mcode = $1 in Ast0.Unary($2, mcode) }
574
575epostfix_expr: eprimary_expr { $1 }
576 | epostfix_expr TOCro eexpr TCCro
577 { Ast0.ArrayAccess ($1,clt2mcode "[" $2,$3,clt2mcode "]" $4) }
578 | epostfix_expr TDot ident
579 { Ast0.RecordAccess($1, clt2mcode "." $2, $3) }
580 | epostfix_expr TPtrOp ident
581 { Ast0.RecordPtAccess($1, clt2mcode "->" $2, $3) }
582 | epostfix_expr TInc
583 { Ast0.Postfix ($1, clt2mcode Ast.Inc $2) }
584 | epostfix_expr TDec
585 { Ast0.Postfix ($1, clt2mcode Ast.Dec $2) }
586 | epostfix_expr TOPar eexpr_list_opt TCPar
587 { Ast0.FunCall($1,clt2mcode "(" $2,$3,clt2mcode ")" $4) }
588
589eprimary_expr: ident { Ast0.Ident($1) }
590 | TEllipsis { Ast0.Edots(clt2mcode "..." $1,None) }
591 | TInt
592 { let (x,clt) = $1 in
593 Ast0.Constant (clt2mcode (Ast.Int x) clt) }
594 | TFloat
595 { let (x,clt) = $1 in
596 Ast0.Constant (clt2mcode (Ast.Float x) clt) }
597 | TString
598 { let (x,clt) = $1 in
599 Ast0.Constant (clt2mcode (Ast.String x) clt) }
600 | TChar
601 { let (x,clt) = $1 in
602 Ast0.Constant (clt2mcode (Ast.Char x) clt) }
603 | TMetaConst
604 { let (nm,ty,clt) = $1 in Ast0.MetaConst(clt2mcode nm clt,ty) }
605 | TMetaErr
606 { let (nm,clt) = $1 in Ast0.MetaErr(clt2mcode nm clt) }
607 | TMetaExp
608 { let (nm,ty,clt) = $1 in Ast0.MetaExpr(clt2mcode nm clt,ty) }
609 | TOPar eexpr TCPar
610 { Ast0.Paren(clt2mcode "(" $1,$2,clt2mcode ")" $3) }
611 | TOPar0 eexpr_mid TCPar0
612 { Ast0.DisjExpr($2) }
613 | TOEllipsis expr_dots TCEllipsis
614 { Ast0.NestExpr(Ast0.DOTS($2)) }
615 | TOCircles expr_circles TCCircles
616 { Ast0.NestExpr(Ast0.CIRCLES($2)) }
617 | TOStars expr_stars TCStars
618 { Ast0.NestExpr(Ast0.STARS($2)) }
619
620/*****************************************************************************/
621
622dexpr: dassign_expr { $1 }
623
624dassign_expr: dcond_expr { $1 }
625 | dunary_expr TAssign dassign_expr
626 { let (op,clt) = $2 in
627 Ast0.Assignment($1,clt2mcode op clt,$3) }
628 | dunary_expr TEq dassign_expr
629 { Ast0.Assignment($1,clt2mcode Ast.SimpleAssign $2,$3) }
630
faf9a90c 631dcond_expr: darith_expr { $1 }
34e49164
C
632 | darith_expr TWhy eexpr_opt TDotDot dcond_expr
633 { Ast0.CondExpr ($1, clt2mcode "?" $2, $3, clt2mcode "?" $4, $5) }
634
635darith_expr: dcast_expr { $1 }
636 | darith_expr TMul darith_expr { arith_op Ast.Mul $1 $2 $3 }
637 | darith_expr TDiv darith_expr { arith_op Ast.Div $1 $2 $3 }
638 | darith_expr TMod darith_expr { arith_op Ast.Mod $1 $2 $3 }
639 | darith_expr TPlus darith_expr { arith_op Ast.Plus $1 $2 $3 }
640 | darith_expr TMinus darith_expr { arith_op Ast.Minus $1 $2 $3 }
641 | darith_expr TShl darith_expr { arith_op Ast.DecLeft $1 $2 $3 }
642 | darith_expr TShr darith_expr { arith_op Ast.DecRight $1 $2 $3 }
643 | darith_expr TInf darith_expr { logic_op Ast.Inf $1 $2 $3 }
644 | darith_expr TSup darith_expr { logic_op Ast.Sup $1 $2 $3 }
645 | darith_expr TInfEq darith_expr { logic_op Ast.InfEq $1 $2 $3 }
646 | darith_expr TSupEq darith_expr { logic_op Ast.SupEq $1 $2 $3 }
647 | darith_expr TEqEq darith_expr { logic_op Ast.Eq $1 $2 $3 }
648 | darith_expr TNotEq darith_expr { logic_op Ast.NotEq $1 $2 $3 }
649 | darith_expr TAnd darith_expr { arith_op Ast.And $1 $2 $3 }
650 | darith_expr TOr darith_expr { arith_op Ast.Or $1 $2 $3 }
651 | darith_expr TXor darith_expr { arith_op Ast.Xor $1 $2 $3 }
652 | darith_expr TAndLog darith_expr { logic_op Ast.AndLog $1 $2 $3 }
653 | darith_expr TOrLog darith_expr { logic_op Ast.OrLog $1 $2 $3 }
654
655dcast_expr: dunary_expr { $1 }
656 | TOPar ctype TCPar dcast_expr
657 { Ast0.Cast (clt2mcode "(" $1, $2, clt2mcode ")" $3, $4) }
658
659dunary_expr: dpostfix_expr { $1 }
660 | TInc dunary_expr
661 { Ast0.Infix ($2, clt2mcode Ast.Inc $1) }
662 | TDec dunary_expr
663 { Ast0.Infix ($2, clt2mcode Ast.Dec $1) }
664 | unary_op dunary_expr
665 { let mcode = $1 in Ast0.Unary($2, mcode) }
666
667dpostfix_expr: dprimary_expr { $1 }
668 | dpostfix_expr TOCro eexpr TCCro
669 { Ast0.ArrayAccess ($1,clt2mcode "[" $2,$3,clt2mcode "]" $4) }
670 | dpostfix_expr TDot ident
671 { Ast0.RecordAccess($1, clt2mcode "." $2, $3) }
672 | dpostfix_expr TPtrOp ident
673 { Ast0.RecordPtAccess($1, clt2mcode "->" $2, $3) }
674 | dpostfix_expr TInc
675 { Ast0.Postfix ($1, clt2mcode Ast.Inc $2) }
676 | dpostfix_expr TDec
677 { Ast0.Postfix ($1, clt2mcode Ast.Dec $2) }
678 | dpostfix_expr TOPar eexpr_list_opt TCPar
679 { Ast0.FunCall($1,clt2mcode "(" $2,$3,clt2mcode ")" $4) }
680
681dprimary_expr: ident { Ast0.Ident($1) }
682 | TInt
683 { let (x,clt) = $1 in
684 Ast0.Constant (clt2mcode (Ast.Int x) clt) }
685 | TFloat
686 { let (x,clt) = $1 in
687 Ast0.Constant (clt2mcode (Ast.Float x) clt) }
688 | TString
689 { let (x,clt) = $1 in
690 Ast0.Constant (clt2mcode (Ast.String x) clt) }
691 | TChar
692 { let (x,clt) = $1 in
693 Ast0.Constant (clt2mcode (Ast.Char x) clt) }
694 | TMetaConst
695 { let (nm,ty,clt) = $1 in Ast0.MetaConst(clt2mcode nm clt,ty) }
696 | TMetaErr
697 { let (nm,clt) = $1 in Ast0.MetaErr(clt2mcode nm clt) }
698 | TMetaExp
699 { let (nm,ty,clt) = $1 in Ast0.MetaExpr(clt2mcode nm clt,ty) }
700 | TOPar eexpr TCPar
701 { Ast0.Paren(clt2mcode "(" $1,$2,clt2mcode ")" $3) }
702 | TOPar0 eexpr_mid TCPar0
703 { Ast0.DisjExpr($2) }
704 | TOEllipsis expr_dots TCEllipsis
705 { Ast0.NestExpr(Ast0.DOTS($2)) }
706 | TOCircles expr_circles TCCircles
707 { Ast0.NestExpr(Ast0.CIRCLES($2)) }
708 | TOStars expr_stars TCStars
709 { Ast0.NestExpr(Ast0.STARS($2)) }
710
711expr_dots:
712 dexpr { [$1] }
713 | dexpr TEllipsis expr_dots
714 { $1 :: Ast0.Edots(clt2mcode "..." $2,None) :: $3 }
715 | dexpr TEllipsis TWhen TNotEq eexpr TLineEnd expr_dots
716 { $1 :: Ast0.Edots(clt2mcode "..." $2,Some $5) :: $7 }
717
718expr_circles:
719 dexpr { [$1] }
720 | dexpr TCircles expr_circles
721 { $1 :: Ast0.Ecircles(clt2mcode "ooo" $2,None) :: $3 }
722 | dexpr TCircles TWhen TNotEq eexpr TLineEnd expr_dots
723 { $1 :: Ast0.Ecircles(clt2mcode "ooo" $2,Some $5) :: $7 }
724
725expr_stars:
726 dexpr { [$1] }
727 | dexpr TStars expr_stars
728 { $1 :: Ast0.Estars(clt2mcode "***" $2,None) :: $3 }
729 | dexpr TStars TWhen TNotEq eexpr TLineEnd expr_dots
730 { $1 :: Ast0.Estars(clt2mcode "***" $2,Some $5) :: $7 }
731
732/*****************************************************************************/
733
734pure_ident: TIdent { $1 }
735
736/* allows redeclaring metavariables. used in @@ @@ */
737pure_ident_or_meta_ident:
738 TIdent { $1 }
739 | TMetaId { $1 }
740 | TMetaType { $1 }
741 | TMetaParam { $1 }
742 | TMetaParamList { $1 }
743 | TMetaStm { $1 }
744 | TMetaStmList { $1 }
745 | TMetaFunc { $1 }
746 | TMetaLocalFunc { $1 }
747 | TMetaExpList { $1 }
748 | TMetaConst { let (name,_,info) = $1 in (name,info) }
749 | TMetaExp { let (name,_,info) = $1 in (name,info) }
750 | TMetaErr { $1 }
751
752ident: TIdent { Ast0.Id(id2mcode $1) }
753 | TMetaId { Ast0.MetaId(id2mcode $1) }
754 | TMetaFunc { Ast0.MetaFunc(id2mcode $1) }
755 | TMetaLocalFunc { Ast0.MetaLocalFunc(id2mcode $1) }
756
757/*****************************************************************************/
758
759meta_var_list: meta_var { $1 }
760 | meta_var meta_var_list { $1@$2 }
761
762meta_var_list_opt: meta_var_list { $1 }
763 | /* empty */ { [] }
764
765d_ident_list: d_ident { [$1] }
766 | d_ident TComma d_ident_list { $1::$3 }
767
768ctype_list: ctype { [$1] }
769 | ctype TComma ctype_list { $1::$3 }
770
771pure_ident_or_meta_ident_list:
772 pure_ident_or_meta_ident
773 { [id2name $1] }
774 | pure_ident_or_meta_ident TComma pure_ident_or_meta_ident_list
775 { (id2name $1)::$3 }
776
777decl_list:
778 decl_list_start
779 { if List.exists (function Ast0.Pcircles(_) -> true | _ -> false) $1
780 then Ast0.CIRCLES($1)
781 else Ast0.DOTS($1) }
782
783decl_list_start:
784 decl { [$1] }
785 | TMetaParamList
786 { let (nm,clt) = $1 in [Ast0.MetaParamList(clt2mcode nm clt)] }
787 | TEllipsis
788 { [Ast0.Pdots(clt2mcode "..." $1)] }
789 | TCircles
790 { [Ast0.Pcircles(clt2mcode "ooo" $1)] }
791 | decl TComma decl_list_start
792 { $1::Ast0.PComma(clt2mcode "," $2)::$3 }
793 | TMetaParamList TComma decl_list_start
794 { let (nm,clt) = $1 in
795 Ast0.MetaParamList(clt2mcode nm clt)::
796 Ast0.PComma(clt2mcode "," $2)::$3 }
797 | TEllipsis TComma decl_list_dots
798 { Ast0.Pdots(clt2mcode "..." $1)::
799 Ast0.PComma(clt2mcode "," $2)::
800 $3 }
801 | TCircles TComma decl_list_circles
802 { Ast0.Pcircles(clt2mcode "ooo" $1)::
803 Ast0.PComma(clt2mcode "," $2)::
804 $3 }
805
806decl_list_dots:
807 decl { [$1] }
808 | TMetaParamList
809 { let (nm,clt) = $1 in [Ast0.MetaParamList(clt2mcode nm clt)] }
810 | TEllipsis
811 { [Ast0.Pdots(clt2mcode "..." $1)] }
812 | decl TComma decl_list_dots
813 { $1::Ast0.PComma(clt2mcode "," $2)::$3 }
814 | TMetaParamList TComma decl_list_dots
815 { let (nm,clt) = $1 in
816 Ast0.MetaParamList(clt2mcode nm clt)::
817 Ast0.PComma(clt2mcode "," $2)::$3 }
818 | TEllipsis TComma decl_list_dots
819 { Ast0.Pdots(clt2mcode "..." $1)::Ast0.PComma(clt2mcode "," $2)::
820 $3 }
821
822decl_list_circles:
823 decl { [$1] }
824 | TMetaParamList
825 { let (nm,clt) = $1 in [Ast0.MetaParamList(clt2mcode nm clt)] }
826 | TCircles
827 { [Ast0.Pcircles(clt2mcode "ooo" $1)] }
828 | decl TComma decl_list_circles
829 { $1::Ast0.PComma(clt2mcode "," $2)::$3 }
830 | TMetaParamList TComma decl_list_circles
831 { let (nm,clt) = $1 in
832 Ast0.MetaParamList(clt2mcode nm clt)::
833 Ast0.PComma(clt2mcode "," $2)::$3 }
834 | TCircles TComma decl_list_circles
835 { Ast0.Pcircles(clt2mcode "ooo" $1)::
836 Ast0.PComma(clt2mcode "," $2)::
837 $3 }
838
839/* must be a single statement */
840statement_mid:
841 statement { [Ast0.DOTS([$1])] }
842 | statement TMid0 statement_mid { Ast0.DOTS([$1])::$3 }
843
844/* must be a list of declarations or statements, with no ... or expressions
845for "and" case */
846pure_decl_statement_list:
847 decl_statement { $1 }
848 | decl_statement pure_decl_statement_list { $1@$2 }
849
850/* as above, but allows a single expression - for "or" case */
851exp_decl_statement_list:
852 expr { [Ast0.Exp($1)] }
853 | decl_statement { $1 }
854 | decl_statement pure_decl_statement_list { $1@$2 }
855
856fun_exp_decl_statement_list:
857 expr
858 { [Ast0.OTHER(Ast0.Exp($1))] }
859 | decl_statement
860 { List.map (function x -> Ast0.OTHER x) $1 }
861 | fundecl
862 { [Ast0.FUNCTION($1)] }
863 | TInclude
864 { [Ast0.INCLUDE(clt2mcode "#include" (id2clt $1),id2mcode $1)] }
865 | TMinusFile TPlusFile
866 { [Ast0.FILEINFO(id2mcode $1,id2mcode $2)] }
867 | decl_statement fun_exp_decl_statement_list
868 { (List.map (function x -> Ast0.OTHER x) $1)@$2 }
869 | fundecl fun_exp_decl_statement_list
870 { Ast0.FUNCTION($1)::$2 }
871 | TInclude fun_exp_decl_statement_list
872 { Ast0.INCLUDE(clt2mcode "#include" (id2clt $1),id2mcode $1)::$2 }
873 | TMinusFile TPlusFile fun_exp_decl_statement_list
874 { Ast0.FILEINFO(id2mcode $1,id2mcode $2)::$3 }
875
876/* ---------------------------------------------------------------------- */
877
878error_words:
879 TError TWords TEq TOCro dotless_eexpr_list TCCro
880 { Ast0.ERRORWORDS($5) }
881
882/* ---------------------------------------------------------------------- */
883/* sequences of statements and expressions */
884
885/* a mix of declarations, statements and expressions. an expression may
886appear by itself. always nonempty and cannot just be dots. */
887
888function_decl_statement_or_expression:
889 error_words /* only at the end */
890 { [$1] }
891 | fun_exp_decl_statement_list
892 { $1 }
893 | fun_exp_decl_statement_list TEllipsis
894 function_decl_statement_or_expression_dots
895 { $1@Ast0.OTHER(Ast0.Dots(clt2mcode "..." $2,None))::$3 }
896 | TEllipsis function_decl_statement_or_expression_dots
897 { Ast0.OTHER(Ast0.Dots(clt2mcode "..." $1,None))::$2 }
898 | fun_exp_decl_statement_list TEllipsis
899 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
900 function_decl_statement_or_expression_dots
901 { $1@Ast0.OTHER(Ast0.Dots(clt2mcode "..." $2,Some $5))::$7 }
902 | TEllipsis TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
903 function_decl_statement_or_expression_dots
904 { Ast0.OTHER(Ast0.Dots(clt2mcode "..." $2,Some $4))::$6 }
905 | fun_exp_decl_statement_list TCircles
906 function_decl_statement_or_expression_circles
907 { $1@Ast0.OTHER(Ast0.Circles(clt2mcode "ooo" $2,None))::$3 }
908 | TCircles function_decl_statement_or_expression_circles
909 { Ast0.OTHER(Ast0.Circles(clt2mcode "ooo" $1,None))::$2 }
910 | fun_exp_decl_statement_list TCircles
911 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
912 function_decl_statement_or_expression_circles
913 { $1@Ast0.OTHER(Ast0.Circles(clt2mcode "ooo" $2,Some $5))::$7 }
914 | TCircles TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
915 function_decl_statement_or_expression_circles
916 { Ast0.OTHER(Ast0.Circles(clt2mcode "ooo" $1,Some $4))::$6 }
917 | fun_exp_decl_statement_list TStars
918 function_decl_statement_or_expression_stars
919 { $1@Ast0.OTHER(Ast0.Stars(clt2mcode "***" $2,None))::$3 }
920 | TStars function_decl_statement_or_expression_stars
921 { Ast0.OTHER(Ast0.Stars(clt2mcode "***" $1,None))::$2 }
922 | fun_exp_decl_statement_list TStars
923 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
924 function_decl_statement_or_expression_stars
925 { $1@Ast0.OTHER(Ast0.Stars(clt2mcode "***" $2,Some $5))::$7 }
926 | TStars TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
927 function_decl_statement_or_expression_stars
928 { Ast0.OTHER(Ast0.Stars(clt2mcode "***" $1,Some $4))::$6 }
929
930function_decl_statement_or_expression_dots:
931 /* empty */ { [] }
932 | fun_exp_decl_statement_list
933 { $1 }
934 | fun_exp_decl_statement_list TEllipsis
935 function_decl_statement_or_expression_dots
936 { $1@Ast0.OTHER(Ast0.Dots(clt2mcode "..." $2,None))::$3 }
937 | fun_exp_decl_statement_list TEllipsis
938 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
939 function_decl_statement_or_expression_dots
940 { $1@Ast0.OTHER(Ast0.Dots(clt2mcode "..." $2,Some $5))::$7 }
941
942function_decl_statement_or_expression_circles:
943 /* empty */ { [] }
944 | fun_exp_decl_statement_list
945 { $1 }
946 | fun_exp_decl_statement_list TCircles
947 function_decl_statement_or_expression_circles
948 { $1@Ast0.OTHER(Ast0.Circles(clt2mcode "ooo" $2,None))::$3 }
949 | fun_exp_decl_statement_list TCircles
950 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
951 function_decl_statement_or_expression_circles
952 { $1@Ast0.OTHER(Ast0.Circles(clt2mcode "ooo" $2,Some $5))::$7 }
953
954function_decl_statement_or_expression_stars:
955 /* empty */ { [] }
956 | fun_exp_decl_statement_list
957 { $1 }
958 | fun_exp_decl_statement_list TStars
959 function_decl_statement_or_expression_stars
960 { $1@Ast0.OTHER(Ast0.Stars(clt2mcode "***" $2,None))::$3 }
961 | fun_exp_decl_statement_list TStars
962 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
963 function_decl_statement_or_expression_stars
964 { $1@Ast0.OTHER(Ast0.Stars(clt2mcode "***" $2,Some $5))::$7 }
965
966decl_statement_or_expression_dots:
967 exp_decl_statement_list
968 { $1 }
969 | exp_decl_statement_list TEllipsis decl_statement_or_expression_dots
970 { $1@Ast0.Dots(clt2mcode "..." $2,None)::$3 }
971 | exp_decl_statement_list TEllipsis
972 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
973 decl_statement_or_expression_dots
974 { $1@Ast0.Dots(clt2mcode "..." $2,Some $5)::$7 }
975
976decl_statement_or_expression_circles:
977 exp_decl_statement_list
978 { $1 }
979 | exp_decl_statement_list TCircles decl_statement_or_expression_circles
980 { $1@Ast0.Dots(clt2mcode "..." $2,None)::$3 }
981 | exp_decl_statement_list TCircles
982 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
983 decl_statement_or_expression_circles
984 { $1@Ast0.Dots(clt2mcode "..." $2,Some $5)::$7 }
985
986decl_statement_or_expression_stars:
987 exp_decl_statement_list
988 { $1 }
989 | exp_decl_statement_list TStars decl_statement_or_expression_stars
990 { $1@Ast0.Stars(clt2mcode "***" $2,None)::$3 }
991 | exp_decl_statement_list TStars
992 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
993 decl_statement_or_expression_stars
994 { $1@Ast0.Stars(clt2mcode "***" $2,Some $5)::$7 }
995
996post_decl_statement_or_expression:
997 exp_decl_statement_list
998 { $1 }
999 | exp_decl_statement_list TEllipsis
1000 { $1@[Ast0.Dots(clt2mcode "..." $2,None)] }
1001 | exp_decl_statement_list TEllipsis
1002 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1003 { $1@[Ast0.Dots(clt2mcode "..." $2,Some $5)] }
1004 | exp_decl_statement_list TCircles
1005 { $1@[Ast0.Circles(clt2mcode "ooo" $2,None)] }
1006 | exp_decl_statement_list TCircles
1007 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1008 { $1@[Ast0.Circles(clt2mcode "ooo" $2,Some $5)] }
1009 | exp_decl_statement_list TStars
1010 { $1@[Ast0.Stars(clt2mcode "***" $2,None)] }
1011 | exp_decl_statement_list TStars
1012 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1013 { $1@[Ast0.Stars(clt2mcode "***" $2,Some $5)] }
1014 | exp_decl_statement_list TEllipsis post_decl_statement_or_expression_dots
1015 { $1@Ast0.Dots(clt2mcode "..." $2,None)::$3 }
1016 | exp_decl_statement_list TEllipsis
1017 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1018 post_decl_statement_or_expression_dots
1019 { $1@Ast0.Dots(clt2mcode "..." $2,Some $5)::$7 }
1020 | exp_decl_statement_list TCircles post_decl_statement_or_expression_dots
1021 { $1@Ast0.Circles(clt2mcode "ooo" $2,None)::$3 }
1022 | exp_decl_statement_list TCircles
1023 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1024 post_decl_statement_or_expression_dots
1025 { $1@Ast0.Circles(clt2mcode "ooo" $2,Some $5)::$7 }
1026 | exp_decl_statement_list TStars post_decl_statement_or_expression_dots
1027 { $1@Ast0.Stars(clt2mcode "***" $2,None)::$3 }
1028 | exp_decl_statement_list TStars
1029 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1030 post_decl_statement_or_expression_dots
1031 { $1@Ast0.Stars(clt2mcode "***" $2,Some $5)::$7 }
1032
1033post_decl_statement_or_expression_dots:
1034 exp_decl_statement_list
1035 { $1 }
1036 | exp_decl_statement_list TEllipsis
1037 { $1@[Ast0.Dots(clt2mcode "..." $2,None)] }
1038 | exp_decl_statement_list TEllipsis
1039 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1040 { $1@[Ast0.Dots(clt2mcode "..." $2,Some $5)] }
1041 | exp_decl_statement_list TEllipsis post_decl_statement_or_expression_dots
1042 { $1@Ast0.Dots(clt2mcode "..." $2,None)::$3 }
1043 | exp_decl_statement_list TEllipsis
1044 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1045 post_decl_statement_or_expression_dots
1046 { $1@Ast0.Dots(clt2mcode "..." $2,Some $5)::$7 }
1047
1048post_decl_statement_or_expression_circles:
1049 exp_decl_statement_list
1050 { $1 }
1051 | exp_decl_statement_list TCircles
1052 { $1@[Ast0.Circles(clt2mcode "ooo" $2,None)] }
1053 | exp_decl_statement_list TCircles
1054 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1055 { $1@[Ast0.Circles(clt2mcode "ooo" $2,Some $5)] }
1056 | exp_decl_statement_list TCircles post_decl_statement_or_expression_circles
1057 { $1@Ast0.Circles(clt2mcode "ooo" $2,None)::$3 }
1058 | exp_decl_statement_list TCircles
1059 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1060 post_decl_statement_or_expression_circles
1061 { $1@Ast0.Circles(clt2mcode "ooo" $2,Some $5)::$7 }
1062
1063post_decl_statement_or_expression_stars:
1064 exp_decl_statement_list
1065 { $1 }
1066 | exp_decl_statement_list TEllipsis
1067 { $1@[Ast0.Stars(clt2mcode "***" $2,None)] }
1068 | exp_decl_statement_list TEllipsis
1069 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1070 { $1@[Ast0.Stars(clt2mcode "***" $2,Some $5)] }
1071 | exp_decl_statement_list TEllipsis post_decl_statement_or_expression_stars
1072 { $1@Ast0.Stars(clt2mcode "***" $2,None)::$3 }
1073 | exp_decl_statement_list TEllipsis
1074 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1075 post_decl_statement_or_expression_stars
1076 { $1@Ast0.Stars(clt2mcode "***" $2,Some $5)::$7 }
1077
1078pre_post_decl_statement_or_expression:
1079 post_decl_statement_or_expression
1080 { if List.exists (function Ast0.Circles(_) -> true | _ -> false) $1
1081 then Ast0.CIRCLES($1)
1082 else if List.exists (function Ast0.Stars(_) -> true | _ -> false) $1
1083 then Ast0.STARS($1)
1084 else Ast0.DOTS($1) }
1085 | TEllipsis post_decl_statement_or_expression_dots
1086 { Ast0.DOTS(Ast0.Dots(clt2mcode "..." $1,None)::$2) }
1087 | TEllipsis TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1088 post_decl_statement_or_expression_dots
1089 { Ast0.DOTS(Ast0.Dots(clt2mcode "..." $1,Some $4)::$6) }
1090 | TCircles post_decl_statement_or_expression_circles
1091 { Ast0.CIRCLES(Ast0.Circles(clt2mcode "ooo" $1,None)::$2) }
1092 | TCircles TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1093 post_decl_statement_or_expression_circles
1094 { Ast0.CIRCLES(Ast0.Circles(clt2mcode "ooo" $1,Some $4)::$6) }
1095 | TStars post_decl_statement_or_expression_stars
1096 { Ast0.STARS(Ast0.Stars(clt2mcode "***" $1,None)::$2) }
1097 | TStars TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1098 post_decl_statement_or_expression_stars
1099 { Ast0.STARS(Ast0.Stars(clt2mcode "***" $1,Some $4)::$6) }
1100
1101/* a mix of declarations, statements and expressions. an expression must
1102be surrounded by ... */
1103
1104post_decl_statement_and_expression_dots:
1105 /* empty */ { [] }
1106 | pure_decl_statement_list { $1 }
1107 | expr TEllipsis post_decl_statement_and_expression_dots
1108 { Ast0.Exp($1)::Ast0.Dots(clt2mcode "..." $2,None)::$3 }
1109 | expr TEllipsis
1110 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1111 post_decl_statement_and_expression_dots
1112 { Ast0.Exp($1)::Ast0.Dots(clt2mcode "..." $2,Some $5)::$7 }
1113 | pure_decl_statement_list TEllipsis post_decl_statement_and_expression_dots
1114 { $1@Ast0.Dots(clt2mcode "..." $2,None)::$3 }
1115 | pure_decl_statement_list TEllipsis
1116 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1117 post_decl_statement_and_expression_dots
1118 { $1@Ast0.Dots(clt2mcode "..." $2,Some $5)::$7 }
1119
1120post_decl_statement_and_expression_circles:
1121 /* empty */ { [] }
1122 | pure_decl_statement_list { $1 }
1123 | expr TCircles post_decl_statement_and_expression_circles
1124 { Ast0.Exp($1)::Ast0.Circles(clt2mcode "ooo" $2,None)::$3 }
1125 | expr TCircles
1126 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1127 post_decl_statement_and_expression_circles
1128 { Ast0.Exp($1)::Ast0.Circles(clt2mcode "ooo" $2,Some $5)::$7 }
1129 | pure_decl_statement_list TCircles
1130 post_decl_statement_and_expression_circles
1131 { $1@Ast0.Circles(clt2mcode "ooo" $2,None)::$3 }
1132 | pure_decl_statement_list TCircles
1133 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1134 post_decl_statement_and_expression_circles
1135 { $1@Ast0.Circles(clt2mcode "ooo" $2,Some $5)::$7 }
1136
1137post_decl_statement_and_expression_stars:
1138 /* empty */ { [] }
1139 | pure_decl_statement_list { $1 }
1140 | expr TStars post_decl_statement_and_expression_stars
1141 { Ast0.Exp($1)::Ast0.Stars(clt2mcode "***" $2,None)::$3 }
1142 | expr TStars
1143 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1144 post_decl_statement_and_expression_stars
1145 { Ast0.Exp($1)::Ast0.Stars(clt2mcode "***" $2,Some $5)::$7 }
1146 | pure_decl_statement_list TStars post_decl_statement_and_expression_stars
1147 { $1@Ast0.Stars(clt2mcode "***" $2,None)::$3 }
1148 | pure_decl_statement_list TStars
1149 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1150 post_decl_statement_and_expression_stars
1151 { $1@Ast0.Stars(clt2mcode "***" $2,Some $5)::$7 }
1152
1153pre_post_decl_statement_and_expression:
1154 pure_decl_statement_list
1155 { top_dots $1 }
1156 | pure_decl_statement_list TEllipsis post_decl_statement_and_expression_dots
1157 { Ast0.DOTS($1@Ast0.Dots(clt2mcode "..." $2,None)::$3) }
1158 | pure_decl_statement_list TEllipsis
1159 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1160 post_decl_statement_and_expression_dots
1161 { Ast0.DOTS($1@Ast0.Dots(clt2mcode "..." $2,Some $5)::$7) }
1162 | pure_decl_statement_list TCircles
1163 post_decl_statement_and_expression_circles
1164 { Ast0.CIRCLES($1@Ast0.Circles(clt2mcode "ooo" $2,None)::$3) }
1165 | pure_decl_statement_list TCircles
1166 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1167 post_decl_statement_and_expression_circles
1168 { Ast0.CIRCLES($1@Ast0.Circles(clt2mcode "ooo" $2,Some $5)::$7) }
1169 | pure_decl_statement_list TStars post_decl_statement_and_expression_stars
1170 { Ast0.STARS($1@Ast0.Stars(clt2mcode "***" $2,None)::$3) }
1171 | pure_decl_statement_list TStars
1172 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1173 post_decl_statement_and_expression_stars
1174 { Ast0.STARS($1@Ast0.Stars(clt2mcode "***" $2,Some $5)::$7) }
1175 | TEllipsis post_decl_statement_and_expression_dots
1176 { Ast0.DOTS(Ast0.Dots(clt2mcode "..." $1,None)::$2) }
1177 | TEllipsis
1178 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1179 post_decl_statement_and_expression_dots
1180 { Ast0.DOTS(Ast0.Dots(clt2mcode "..." $1,Some $4)::$6) }
1181 | TCircles post_decl_statement_and_expression_circles
1182 { Ast0.CIRCLES(Ast0.Circles(clt2mcode "ooo" $1,None)::$2) }
1183 | TCircles
1184 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1185 post_decl_statement_and_expression_circles
1186 { Ast0.CIRCLES(Ast0.Circles(clt2mcode "ooo" $1,Some $4)::$6) }
1187 | TStars post_decl_statement_and_expression_stars
1188 { Ast0.STARS(Ast0.Stars(clt2mcode "***" $1,None)::$2) }
1189 | TStars
1190 TWhen TNotEq pre_post_decl_statement_or_expression TLineEnd
1191 post_decl_statement_and_expression_stars
1192 { Ast0.STARS(Ast0.Stars(clt2mcode "***" $1,Some $4)::$6) }
1193
1194pre_post_decl_statement_and_expression_opt:
1195 /* empty */ { Ast0.DOTS([]) }
1196 | pre_post_decl_statement_and_expression { $1 }
1197
1198pre_post_decl_statement_and_expression_opt_mid:
1199 pre_post_decl_statement_and_expression { [$1] }
1200 | /* empty */ { [Ast0.DOTS([])] }
1201 | pre_post_decl_statement_and_expression TMid0
1202 pre_post_decl_statement_and_expression_opt_mid { $1::$3 }
1203 | TMid0
1204 pre_post_decl_statement_and_expression_opt_mid { Ast0.DOTS([])::$2 }
1205
1206/* ---------------------------------------------------------------------- */
1207
1208dotless_eexpr_list:
1209 dexpr
1210 { [$1] }
1211 | dexpr TComma dotless_eexpr_list
1212 { $1::Ast0.EComma(clt2mcode "," $2)::$3 }
1213
1214eexpr_list:
1215 eexpr_list_start
1216 { if List.exists (function Ast0.Ecircles(_) -> true | _ -> false) $1
1217 then Ast0.CIRCLES($1)
1218 else if List.exists (function Ast0.Estars(_) -> true | _ -> false) $1
1219 then Ast0.STARS($1)
1220 else Ast0.DOTS($1) }
1221
1222eexpr_list_start:
1223 dexpr
1224 { [$1] }
1225 | TMetaExpList
1226 { let (nm,clt) = $1 in [Ast0.MetaExprList(clt2mcode nm clt)] }
1227 | TEllipsis
1228 { [Ast0.Edots(clt2mcode "..." $1,None)] }
1229 | TEllipsis TWhen TNotEq eexpr TLineEnd
1230 { [Ast0.Edots(clt2mcode "..." $1,Some $4)] }
1231 | TCircles
1232 { [Ast0.Ecircles(clt2mcode "ooo" $1,None)] }
1233 | TCircles TWhen TNotEq eexpr TLineEnd
1234 { [Ast0.Ecircles(clt2mcode "ooo" $1,Some $4)] }
1235 | TStars
1236 { [Ast0.Estars(clt2mcode "***" $1,None)] }
1237 | TStars TWhen TNotEq eexpr TLineEnd
1238 { [Ast0.Estars(clt2mcode "***" $1,Some $4)] }
1239 | dexpr TComma eexpr_list_start
1240 { $1::Ast0.EComma(clt2mcode "," $2)::$3 }
1241 | TMetaExpList TComma eexpr_list_start
1242 { let (nm,clt) = $1 in
1243 Ast0.MetaExprList(clt2mcode nm clt)::Ast0.EComma(clt2mcode "," $2)::$3 }
1244 | TEllipsis TComma eexpr_list_dots
1245 { Ast0.Edots(clt2mcode "..." $1,None)::
1246 Ast0.EComma(clt2mcode "," $2)::$3 }
1247 | TEllipsis TWhen TNotEq eexpr TLineEnd TComma eexpr_list_dots
1248 { Ast0.Edots(clt2mcode "..." $1,Some $4)::
1249 Ast0.EComma(clt2mcode "," $6)::$7 }
1250 | TCircles TComma eexpr_list_circles
1251 { Ast0.Ecircles(clt2mcode "ooo" $1,None)::
1252 Ast0.EComma(clt2mcode "," $2)::$3 }
1253 | TCircles TWhen TNotEq eexpr TLineEnd TComma eexpr_list_circles
1254 { Ast0.Ecircles(clt2mcode "ooo" $1,Some $4)::
1255 Ast0.EComma(clt2mcode "," $6)::$7 }
1256 | TStars TComma eexpr_list_stars
1257 { Ast0.Estars(clt2mcode "***" $1,None)::
1258 Ast0.EComma(clt2mcode "," $2)::$3 }
1259 | TStars TWhen TNotEq eexpr TLineEnd TComma eexpr_list_stars
1260 { Ast0.Estars(clt2mcode "***" $1,Some $4)::
1261 Ast0.EComma(clt2mcode "," $6)::$7 }
1262
1263eexpr_list_dots:
1264 dexpr
1265 { [$1] }
1266 | TMetaExpList
1267 { let (nm,clt) = $1 in [Ast0.MetaExprList(clt2mcode nm clt)] }
1268 | TEllipsis
1269 { [Ast0.Edots(clt2mcode "..." $1,None)] }
1270 | TEllipsis TWhen TNotEq eexpr TLineEnd
1271 { [Ast0.Edots(clt2mcode "..." $1,Some $4)] }
1272 | dexpr TComma eexpr_list_dots
1273 { $1::Ast0.EComma(clt2mcode "," $2)::$3 }
1274 | TMetaExpList TComma eexpr_list_dots
1275 { let (nm,clt) = $1 in
1276 Ast0.MetaExprList(clt2mcode nm clt)::Ast0.EComma(clt2mcode "," $2)::$3 }
1277 | TEllipsis TComma eexpr_list_dots
1278 { Ast0.Edots(clt2mcode "..." $1,None)::
1279 Ast0.EComma(clt2mcode "," $2)::$3 }
1280 | TEllipsis TWhen TNotEq eexpr TLineEnd TComma eexpr_list_dots
1281 { Ast0.Edots(clt2mcode "..." $1,Some $4)::
1282 Ast0.EComma(clt2mcode "," $6)::$7 }
1283
1284eexpr_list_circles:
1285 dexpr
1286 { [$1] }
1287 | TMetaExpList
1288 { let (nm,clt) = $1 in [Ast0.MetaExprList(clt2mcode nm clt)] }
1289 | TCircles
1290 { [Ast0.Ecircles(clt2mcode "ooo" $1,None)] }
1291 | TCircles TWhen TNotEq eexpr TLineEnd
1292 { [Ast0.Ecircles(clt2mcode "ooo" $1,Some $4)] }
1293 | dexpr TComma eexpr_list_circles
1294 { $1::Ast0.EComma(clt2mcode "," $2)::$3 }
1295 | TMetaExpList TComma eexpr_list_circles
1296 { let (nm,clt) = $1 in
1297 Ast0.MetaExprList(clt2mcode nm clt)::Ast0.EComma(clt2mcode "," $2)::$3 }
1298 | TCircles TComma eexpr_list_circles
1299 { Ast0.Ecircles(clt2mcode "ooo" $1,None)::
1300 Ast0.EComma(clt2mcode "," $2)::$3 }
1301 | TCircles TWhen TNotEq eexpr TLineEnd TComma eexpr_list_circles
1302 { Ast0.Ecircles(clt2mcode "ooo" $1,Some $4)::
1303 Ast0.EComma(clt2mcode "," $6)::$7 }
1304
1305eexpr_list_stars:
1306 dexpr
1307 { [$1] }
1308 | TMetaExpList
1309 { let (nm,clt) = $1 in [Ast0.MetaExprList(clt2mcode nm clt)] }
1310 | TStars
1311 { [Ast0.Estars(clt2mcode "***" $1,None)] }
1312 | TStars TWhen TNotEq eexpr TLineEnd
1313 { [Ast0.Estars(clt2mcode "***" $1,Some $4)] }
1314 | dexpr TComma eexpr_list_stars
1315 { $1::Ast0.EComma(clt2mcode "," $2)::$3 }
1316 | TMetaExpList TComma eexpr_list_stars
1317 { let (nm,clt) = $1 in
1318 Ast0.MetaExprList(clt2mcode nm clt)::Ast0.EComma(clt2mcode "," $2)::$3 }
1319 | TStars TComma eexpr_list_stars
1320 { Ast0.Estars(clt2mcode "***" $1,None)::
1321 Ast0.EComma(clt2mcode "," $2)::$3 }
1322 | TStars TWhen TNotEq eexpr TLineEnd TComma eexpr_list_stars
1323 { Ast0.Estars(clt2mcode "***" $1,Some $4)::
1324 Ast0.EComma(clt2mcode "," $6)::$7 }
1325
1326eexpr_list_opt: eexpr_list { $1 }
1327 | /* empty */ { Ast0.DOTS([]) }
1328
1329expr_mid:
1330 expr { [$1] }
1331 | expr TMid0 expr_mid { $1::$3 }
1332
1333eexpr_mid:
1334 eexpr { [$1] }
1335 | eexpr TMid0 eexpr_mid { $1::$3 }
1336
1337eexpr_opt: eexpr { Some ($1) }
1338 | /* empty */ { None }
1339