open LexToken let semi = parser [< 'SEMI _ >] -> () let vbar = parser [< 'VBAR _ >] -> () let end_ = parser [< 'End _ >] -> () let rbracket = parser [< 'RBRACKET _ >] -> () let times = parser [< 'TIMES _ >] -> () let arrow = parser [< 'ARROW _ >] -> fun _ _ -> () let comma = parser [< 'COMMA _ >] -> () let rbrace = parser [< 'RBRACE _ >] -> () let equal = parser [< 'EQUAL _ >] -> () let ass = parser [< 'ASS _ >] -> () let dot = parser [< 'DOT _ >] -> () let down = parser [< 'Down _ >] -> () let or_ = parser [< 'Or _ >] -> fun _ _ -> () let and_ = parser [< 'And _ >] -> fun _ _ -> () let cat = parser [< 'CAT _ >] -> fun _ _ -> () let cons = parser [< 'CONS _ >] -> () let cons' = parser [< 'CONS _ >] -> fun _ _ -> () let list = parser [< 'List _ >] -> () let map = parser [< 'Map _ >] -> () let set = parser [< 'Set _ >] -> () let left_assoc item op = let rec op_elem i = parser [< f=op; j=item; r = op_elem (f i j) ?! >] -> r | [< >] -> i in parser [< i=item; r = op_elem i >] -> r let rec right_assoc item op = parser [< i=item >] -> i | [< i=item; f=op; j = right_assoc item op ?! >] -> f i j let opt item = parser [< i=item >] -> Some i | [< >] -> None let rec series item sep term = parser [< i=item; l = after_item item sep term >] -> i,l and after_item item sep term = parser [< t=term >] -> [], None, t | [< s=sep; io = item_or_closing item sep term >] -> match io with `Some (item, items, term, closing) -> (s, item)::items, term, closing | `Closing closing -> [], Some s, closing and item_or_closing item sep term = parser [< t=term >] -> `Closing t | [< s = series item sep term >] -> let item, (items, term, closing) = s in `Some (item, items, term, closing) (* Compound constructs *) let par item = parser [< 'LPAR _; _=item; 'RPAR _ >] -> () let brackets item = parser [< 'LBRACKET _; _=item; 'RBRACKET _ >] -> () (* Sequences *) (* Possibly empty sequence of items *) let rec seq item = parser [< h,t = nseq item >] -> h::t (* Non-empty sequence of items *) and nseq item = parser [< i=item; l = seq item >] -> i,l (* Non-empty separated sequence of items *) and nsepseq item sep = parser [< i=item >] -> i, [] | [< i=item; s=sep; h,t = nsepseq item sep ?! >] -> i, (s,h)::t (* Possibly empty separated sequence of items *) (* and sepseq item sep = opt (nsepseq item sep) *) (* Main *) let rec contract = parser [< _ = nseq declaration; 'EOF _ >] -> () and declaration = parser [< _ = type_decl; _ = opt semi >] -> () | [< _ = const_decl; _ = opt semi >] -> () | [< _ = lambda_decl; _ = opt semi >] -> () and type_decl = parser [< 'Type _; 'Ident _; 'Is _; _=type_expr >] -> () and type_expr = parser [< _=cartesian >] -> () | [< _=nsepseq variant vbar >] -> () | [< 'VBAR _; _ = nsepseq variant vbar >] -> () | [< 'Record _; _=record_type_expr >] -> () and record_type_expr = parser [< _ = series field_decl semi end_ >] -> () | [< 'LBRACKET _; _ = series field_decl semi rbracket >] -> () and variant = parser [< 'Constr _; _ = opt of_cartesian >] -> () and of_cartesian = parser [< 'Of _; _=cartesian >] -> () and cartesian = parser [< _ = nsepseq function_type times >] -> () and function_type strm = right_assoc core_type arrow strm and core_type = parser [< 'Ident _; _ = opt type_tuple >] -> () | [< 'Map _; _=type_tuple >] -> () | [< 'Set _; _ = par type_expr >] -> () | [< 'List _; _ = par type_expr >] -> () | [< _ = par type_expr >] -> () and type_tuple = parser [< _ = par (nsepseq type_expr comma) >] -> () and field_decl = parser [< 'Ident _; 'COLON _; _=type_expr >] -> () (* Function and procedure declarations *) and lambda_decl = parser [< _=fun_decl >] -> () | [< _=proc_decl >] -> () and fun_decl = parser [< 'Function _; 'Ident _; _=parameters; 'COLON _; _=type_expr; 'Is _; _ = seq local_decl; _=block; 'With _; _=expr >] -> () and proc_decl = parser [< 'Procedure _; 'Ident _; _parameters; 'Is _; _ = seq local_decl; _=block >] -> () and parameters = parser [< p = par (nsepseq param_decl semi) >] -> p and param_decl = parser [< 'Var _; 'Ident _; 'COLON _; _=param_type >] -> () | [< 'Const _; 'Ident _; 'COLON _; _=param_type >] -> () and param_type = parser [< c = cartesian >] -> c and block = parser [< 'Begin _; _ = series statement semi end_ >] -> () | [< 'Block _; 'LBRACE _; _ = series statement semi rbrace >] -> () and statement = parser [< _=instruction >] -> () | [< _=data_decl >] -> () and data_decl = parser [< _=const_decl >] -> () | [< _=var_decl >] -> () and const_decl = parser [< 'Const _; _ = unqualified_decl equal >] -> () and var_decl = parser [< 'Var _; _ = unqualified_decl ass >] -> () and local_decl = parser [< _=fun_decl; _ = opt semi >] -> () | [< _=proc_decl; _ = opt semi >] -> () | [< _=data_decl; _ = opt semi >] -> () and unqualified_decl op = parser [< 'Ident _; 'COLON _; _=type_expr; _=op; _=expr >] -> () and instruction = parser [< _=block >] -> () | [< 'If _; _=expr; 'Then _; _=if_clause; _ = opt semi; 'Else _; _=if_clause >] -> () | [< _ = case instruction >] -> () | [< 'Ident _; _=instruction_1 >] -> () | [< _=loop >] -> () | [< 'Fail _; _=expr >] -> () | [< 'Skip _ >] -> () | [< 'Patch _; _=path; 'With _; _=structure >] -> () | [< 'Remove _; _=expr; 'From _; _=remove_suffix >] -> () and remove_suffix = parser [< 'Map _; _=path >] -> () | [< 'Set _; _=path >] -> () and instruction_1 = parser [< _=arguments >] -> () | [< 'ASS _; _=expr >] -> () | [< _ = brackets expr; 'ASS _; _=expr >] -> () | [< _=selections; _ = opt (brackets expr); 'ASS _; _=expr >] -> () and path = parser [< 'Ident _; _ = opt selections >] -> () and selections = parser [< 'DOT _; _ = nsepseq selection dot >] -> () and injection kind element = parser [< _=kind; _ = inj_suffix element >] -> () and inj_suffix element = parser [< _ = series element semi end_ >] -> () | [< 'End _ >] -> () | [< 'LBRACKET _; _ = bracketed element >] -> () and bracketed element = parser [< _ = series element semi rbracket >] -> () | [< 'RBRACKET _ >] -> () and binding = parser [< _=expr; 'ARROW _; _=expr >] -> () and if_clause = parser [< _=instruction >] -> () | [< 'LBRACE _; _ = series statement comma rbrace >] -> () and case rhs = parser [< 'Case _; _=expr; 'Of _; _ = case_suffix rhs >] -> () and case_suffix rhs = parser [< _ = cases rhs; 'End _ >] -> () | [< 'LBRACKET _; _ = cases rhs; 'RBRACKET _ >] -> () and cases rhs = parser [< _ = nsepseq (case_clause rhs) vbar >] -> () | [< 'VBAR _; _ = nsepseq (case_clause rhs) vbar >] -> () and case_clause rhs = parser [< _=pattern; 'ARROW _; _=rhs >] -> () and loop = parser [< 'While _; _=expr; _=block >] -> () | [< 'For _; 'Ident _; _=for_suffix >] -> () and for_suffix = parser [< 'ASS _; _=expr; _ = opt down; 'To _; _=expr; _ = opt step_clause; _=block >] -> () | [< 'In _; _=expr; _=block >] -> () | [< 'ARROW _; 'Ident _; 'In _; _=expr; _=block >] -> () and step_clause = parser [< 'Step _; _=expr >] -> () (* Expressions *) and interactive = parser [< _=expr; 'EOF _ >] -> () and expr = parser [< _ = case expr >] -> () | [< _=disj_expr >] -> () and disj_expr strm = left_assoc conj_expr or_ strm and conj_expr strm = left_assoc set_membership and_ strm and set_membership = parser [< _ = comp_expr; _ = opt contains_clause >] -> () and contains_clause = parser [< 'Contains _; _=set_membership >] -> () and comp_expr strm = left_assoc cat_expr op_comp strm and op_comp = parser [< 'LT _ >] -> fun _ _ -> () | [< 'LEQ _ >] -> fun _ _ -> () | [< 'GT _ >] -> fun _ _ -> () | [< 'GEQ _ >] -> fun _ _ -> () | [< 'EQUAL _ >] -> fun _ _ -> () | [< 'NEQ _ >] -> fun _ _ -> () and cat_expr strm = right_assoc cons_expr cat strm and cons_expr strm = left_assoc add_expr cons' strm and add_expr strm = left_assoc mult_expr add_op strm and add_op = parser [< 'PLUS _ >] -> fun _ _ -> () | [< 'MINUS _ >] -> fun _ _ -> () and mult_expr strm = left_assoc unary_expr mult_op strm and mult_op = parser [< 'TIMES _ >] -> fun _ _ -> () | [< 'SLASH _ >] -> fun _ _ -> () | [< 'Mod _ >] -> fun _ _ -> () and unary_expr = parser [< 'MINUS _; _=core_expr >] -> () | [< 'Not _; _=core_expr >] -> () | [< _=core_expr >] -> () and core_expr = parser [< 'Int _ >] -> () | [< 'Nat _ >] -> () | [< 'Mutez _ >] -> () | [< 'Ident _; _ = opt core_suffix >] -> () | [< 'String _ >] -> () | [< 'Bytes _ >] -> () | [< 'C_False _ >] -> () | [< 'C_True _ >] -> () | [< 'C_Unit _ >] -> () | [< 'C_None _ >] -> () | [< 'C_Some _; _=arguments >] -> () | [< 'Constr _; _ = opt arguments >] -> () | [< _ = par paren_expr >] -> () | [< _ = injection list expr >] -> () | [< 'Nil _ >] -> () | [< _=structure >] -> () and core_suffix = parser [< _ = brackets expr >] -> () | [< 'DOT _; _ = nsepseq selection dot; _ = opt (brackets expr) >] -> () | [< _=arguments >] -> () and paren_expr = parser [< _=disj_expr; _ = opt paren_expr_1 >] -> () | [< _ = case expr; _ = opt paren_expr_2 >] -> () and paren_expr_1 = parser [< 'COLON _; _=type_expr >] -> () | [< 'COMMA _; _ = nsepseq expr comma >] -> () and paren_expr_2 = parser [< 'COMMA _; _ = nsepseq expr comma >] -> () and structure = parser [< _ = injection map binding >] -> () | [< _ = injection set expr >] -> () | [< _=record_expr >] -> () and selection = parser [< 'Ident _ >] -> () | [< 'Int _ >] -> () and record_expr = parser [< 'Record _; _=record_expr_suffix >] -> () and record_expr_suffix = parser [< _ = series field_assignment semi end_ >] -> () | [< 'LBRACKET _; _ = series field_assignment semi rbracket >] -> () and field_assignment = parser [< 'Ident _; 'EQUAL _; _=expr >] -> () and arguments = parser [< _ = par (nsepseq expr comma) >] -> () (* Patterns *) and pattern = parser [< _ = nsepseq core_pattern cons >] -> () and core_pattern = parser [< 'Ident _ >] -> () | [< 'WILD _ >] -> () | [< 'Int _ >] -> () | [< 'String _ >] -> () | [< 'C_Unit _ >] -> () | [< 'C_False _ >] -> () | [< 'C_True _ >] -> () | [< 'C_None _ >] -> () | [< 'C_Some _; _ = par core_pattern >] -> () | [< 'Constr _; _ = opt tuple_pattern >] -> () | [< _ = injection list core_pattern >] -> () | [< 'Nil _ >] -> () | [< _ = par (opt paren_pattern) >] -> () and paren_pattern = parser [< 'CONS _; _=pattern >] -> () | [< 'COMMA _; _ = nsepseq core_pattern comma >] -> () and tuple_pattern = parser [< _ = par (nsepseq core_pattern comma) >] -> ()