aboutsummaryrefslogtreecommitdiff
path: root/lib/qparser/qsp_single_line.mly
blob: 933098290ad09e6b104d622deb0ba41657f63bbf (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
%%

empty:
    | {}

(** The whole block is parametrized over a token named END. In most of the
    cases this token indicate the end of line, but in the case of recursive
    inline instruction, this can become an empty marker (because the whole
    instruction is nested inside a end_line terminated block)
    *)
%public inlined_block(END):
    | s = terminated(instruction, END) 
        { s }
    | a = onliner(ACT) END
      { let loc, label, statements, _, _ = a in 
        let label = Analyzer.Expression.v label in
        Analyzer.Instruction.act loc ~label statements
      }
    (* This case create a conflict in the resolution : the case 
            if a: if b: '' else ''
        can be interpreted as
            if a: (if b: '' else '')
        or
            if a: (if b: '') else ''
     *)
    | a = onliner(IF)
      else_opt = preceded(ELSE, inlined_block(empty))?
      END
      { let loc, expr, statements, loc_s, _body = a in 
        let elifs = []
        and else_ = match else_opt with 
          | None -> None
          | Some instructions -> Some ($loc(else_opt), [ instructions ]) in

        Analyzer.Instruction.if_
            loc 
            (loc_s, Analyzer.Expression.v expr, statements) 
            ~elifs
            ~else_
      }

final_inline_instruction:
    | hd = inline_instruction 
      tl = inlined_block(empty)
      { tl :: hd }
    | hd = inline_instruction 
      COMMENT
      { (Analyzer.Instruction.comment $loc) :: hd }

onliner(TOKEN):
      | TOKEN
        e = expression
        COLUMN
        s = rev (final_inline_instruction)
      { $loc, e, s, $loc(s), None }

(* This is basicaly just a loop to add as many instruction separated by & *)
inline_instruction:
    | hd = inline_instruction
      tl = instruction
      AMPERSAND+
      { tl :: hd }
    | 
      { [] }