2020-11-25 18:51:19 +03:00
|
|
|
(* This file is part of the Catala compiler, a specification language for tax and social benefits
|
|
|
|
computation rules. Copyright (C) 2020 Inria, contributor: Denis Merigoux
|
|
|
|
<denis.merigoux@inria.fr>
|
|
|
|
|
|
|
|
Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except
|
|
|
|
in compliance with the License. You may obtain a copy of the License at
|
|
|
|
|
|
|
|
http://www.apache.org/licenses/LICENSE-2.0
|
|
|
|
|
|
|
|
Unless required by applicable law or agreed to in writing, software distributed under the License
|
|
|
|
is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express
|
|
|
|
or implied. See the License for the specific language governing permissions and limitations under
|
|
|
|
the License. *)
|
|
|
|
|
2021-01-21 23:33:04 +03:00
|
|
|
open Utils
|
2020-11-26 12:38:13 +03:00
|
|
|
open Ast
|
2020-11-25 18:51:19 +03:00
|
|
|
|
2020-11-26 17:48:26 +03:00
|
|
|
let typ_needs_parens (e : typ Pos.marked) : bool =
|
2020-12-28 01:53:02 +03:00
|
|
|
match Pos.unmark e with TArrow _ | TArray _ -> true | _ -> false
|
2020-11-26 17:48:26 +03:00
|
|
|
|
2021-01-09 23:03:32 +03:00
|
|
|
let format_uid_list (fmt : Format.formatter) (infos : Uid.MarkedString.info list) : unit =
|
|
|
|
Format.fprintf fmt "%a"
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ".")
|
|
|
|
(fun fmt info ->
|
|
|
|
Format.fprintf fmt "%s"
|
2021-01-13 14:04:14 +03:00
|
|
|
(Utils.Cli.print_with_style
|
|
|
|
(let first_letter = CamomileLibraryDefault.Camomile.UTF8.get (Pos.unmark info) 0 in
|
|
|
|
try
|
|
|
|
match CamomileLibraryDefault.Camomile.UCharInfo.general_category first_letter with
|
|
|
|
| `Ll -> []
|
|
|
|
| `Lu -> [ ANSITerminal.red ]
|
|
|
|
| _ -> []
|
|
|
|
with _ -> [])
|
2021-01-09 23:03:32 +03:00
|
|
|
"%s"
|
|
|
|
(Format.asprintf "%a" Utils.Uid.MarkedString.format_info info))))
|
|
|
|
infos
|
|
|
|
|
2020-12-10 13:35:56 +03:00
|
|
|
let format_tlit (fmt : Format.formatter) (l : typ_lit) : unit =
|
|
|
|
match l with
|
|
|
|
| TUnit -> Format.fprintf fmt "unit"
|
|
|
|
| TBool -> Format.fprintf fmt "boolean"
|
|
|
|
| TInt -> Format.fprintf fmt "integer"
|
|
|
|
| TRat -> Format.fprintf fmt "decimal"
|
|
|
|
| TMoney -> Format.fprintf fmt "money"
|
|
|
|
| TDuration -> Format.fprintf fmt "duration"
|
|
|
|
| TDate -> Format.fprintf fmt "date"
|
|
|
|
|
2021-01-14 02:17:24 +03:00
|
|
|
let rec format_typ (ctx : Ast.decl_ctx) (fmt : Format.formatter) (typ : typ Pos.marked) : unit =
|
|
|
|
let format_typ = format_typ ctx in
|
2020-11-26 17:48:26 +03:00
|
|
|
let format_typ_with_parens (fmt : Format.formatter) (t : typ Pos.marked) =
|
|
|
|
if typ_needs_parens t then Format.fprintf fmt "(%a)" format_typ t
|
|
|
|
else Format.fprintf fmt "%a" format_typ t
|
|
|
|
in
|
2020-11-25 18:51:19 +03:00
|
|
|
match Pos.unmark typ with
|
2020-12-10 13:35:56 +03:00
|
|
|
| TLit l -> Format.fprintf fmt "%a" format_tlit l
|
2021-01-14 02:17:24 +03:00
|
|
|
| TTuple (ts, None) ->
|
|
|
|
Format.fprintf fmt "@[<hov 2>(%a)]"
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt "@ *@ ")
|
|
|
|
(fun fmt t -> Format.fprintf fmt "%a" format_typ t))
|
2020-12-03 22:11:41 +03:00
|
|
|
ts
|
2021-01-14 02:17:24 +03:00
|
|
|
| TTuple (ts, Some s) ->
|
|
|
|
Format.fprintf fmt "%a @[<hov 2>{@ %a@ }@]" Ast.StructName.format_t s
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ";@ ")
|
|
|
|
(fun fmt (t, f) ->
|
|
|
|
Format.fprintf fmt "%a:@ %a" Ast.StructFieldName.format_t f format_typ t))
|
|
|
|
(List.combine ts (Ast.StructMap.find s ctx.ctx_structs))
|
|
|
|
| TEnum (ts, e) ->
|
|
|
|
Format.fprintf fmt "%a [@[<hov 2>%a@]]" Ast.EnumName.format_t e
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt "@ |@ ")
|
|
|
|
(fun fmt (t, f) ->
|
|
|
|
Format.fprintf fmt "%a:@ %a" Ast.EnumConstructor.format_t f format_typ t))
|
|
|
|
(List.combine ts (Ast.EnumMap.find e ctx.ctx_enums))
|
2020-11-27 18:27:10 +03:00
|
|
|
| TArrow (t1, t2) ->
|
|
|
|
Format.fprintf fmt "@[<hov 2>%a →@ %a@]" format_typ_with_parens t1 format_typ t2
|
2020-12-28 01:53:02 +03:00
|
|
|
| TArray t1 -> Format.fprintf fmt "@[%a@ array@]" format_typ t1
|
2020-12-30 00:26:10 +03:00
|
|
|
| TAny -> Format.fprintf fmt "any"
|
2020-11-26 12:38:13 +03:00
|
|
|
|
|
|
|
let format_lit (fmt : Format.formatter) (l : lit Pos.marked) : unit =
|
|
|
|
match Pos.unmark l with
|
|
|
|
| LBool b -> Format.fprintf fmt "%b" b
|
2020-12-09 18:45:23 +03:00
|
|
|
| LInt i -> Format.fprintf fmt "%s" (Z.to_string i)
|
2020-11-26 12:38:13 +03:00
|
|
|
| LEmptyError -> Format.fprintf fmt "∅"
|
2020-11-26 15:38:42 +03:00
|
|
|
| LUnit -> Format.fprintf fmt "()"
|
2020-12-09 18:45:23 +03:00
|
|
|
| LRat i ->
|
|
|
|
let sign = Q.sign i in
|
|
|
|
let n = Z.abs (Q.num i) in
|
|
|
|
let d = Z.abs (Q.den i) in
|
|
|
|
let int_part = Z.ediv n d in
|
|
|
|
let n = ref (Z.erem n d) in
|
|
|
|
let digits = ref [] in
|
|
|
|
let leading_zeroes (digits : Z.t list) : int =
|
|
|
|
match
|
|
|
|
List.fold_right
|
|
|
|
(fun digit num_leading_zeroes ->
|
|
|
|
match num_leading_zeroes with
|
|
|
|
| `End _ -> num_leading_zeroes
|
|
|
|
| `Begin i -> if Z.(digit = zero) then `Begin (i + 1) else `End i)
|
|
|
|
digits (`Begin 0)
|
|
|
|
with
|
|
|
|
| `End i -> i
|
|
|
|
| `Begin i -> i
|
|
|
|
in
|
|
|
|
while
|
|
|
|
!n <> Z.zero && List.length !digits - leading_zeroes !digits < !Utils.Cli.max_prec_digits
|
|
|
|
do
|
|
|
|
n := Z.mul !n (Z.of_int 10);
|
|
|
|
digits := Z.ediv !n d :: !digits;
|
|
|
|
n := Z.erem !n d
|
|
|
|
done;
|
|
|
|
Format.fprintf fmt "%s%a.%a%s"
|
|
|
|
(if sign < 0 then "-" else "")
|
|
|
|
Z.pp_print int_part
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun _fmt () -> ())
|
|
|
|
(fun fmt digit -> Format.fprintf fmt "%a" Z.pp_print digit))
|
|
|
|
(List.rev !digits)
|
|
|
|
( if List.length !digits - leading_zeroes !digits = !Utils.Cli.max_prec_digits then "…"
|
|
|
|
else "" )
|
2021-01-09 23:03:32 +03:00
|
|
|
| LMoney e -> (
|
|
|
|
match !Utils.Cli.locale_lang with
|
|
|
|
| `En -> Format.fprintf fmt "$%.2f" Q.(to_float (of_bigint e / of_int 100))
|
|
|
|
| `Fr -> Format.fprintf fmt "%.2f €" Q.(to_float (of_bigint e / of_int 100)) )
|
2021-01-14 15:04:15 +03:00
|
|
|
| LDate d -> Format.fprintf fmt "%s" (CalendarLib.Printer.Date.to_string d)
|
|
|
|
| LDuration d -> (
|
|
|
|
let x, y, z = CalendarLib.Date.Period.ymd d in
|
|
|
|
let to_print =
|
|
|
|
List.filter (fun (a, _) -> a <> 0) [ (x, "years"); (y, "months"); (z, "days") ]
|
|
|
|
in
|
|
|
|
match to_print with
|
|
|
|
| [] -> Format.fprintf fmt "empty duration"
|
|
|
|
| _ ->
|
|
|
|
Format.fprintf fmt "%a"
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ",@ ")
|
|
|
|
(fun fmt (d, l) -> Format.fprintf fmt "%d %s" d l))
|
|
|
|
to_print )
|
2020-11-26 12:38:13 +03:00
|
|
|
|
2020-12-09 20:14:52 +03:00
|
|
|
let format_op_kind (fmt : Format.formatter) (k : op_kind) =
|
2020-12-10 13:35:56 +03:00
|
|
|
Format.fprintf fmt "%s"
|
|
|
|
(match k with KInt -> "" | KRat -> "." | KMoney -> "$" | KDate -> "@" | KDuration -> "^")
|
2020-12-09 20:14:52 +03:00
|
|
|
|
2020-11-26 12:38:13 +03:00
|
|
|
let format_binop (fmt : Format.formatter) (op : binop Pos.marked) : unit =
|
2020-12-09 20:14:52 +03:00
|
|
|
match Pos.unmark op with
|
|
|
|
| Add k -> Format.fprintf fmt "+%a" format_op_kind k
|
|
|
|
| Sub k -> Format.fprintf fmt "-%a" format_op_kind k
|
|
|
|
| Mult k -> Format.fprintf fmt "*%a" format_op_kind k
|
|
|
|
| Div k -> Format.fprintf fmt "/%a" format_op_kind k
|
|
|
|
| And -> Format.fprintf fmt "%s" "&&"
|
|
|
|
| Or -> Format.fprintf fmt "%s" "||"
|
|
|
|
| Eq -> Format.fprintf fmt "%s" "=="
|
|
|
|
| Neq -> Format.fprintf fmt "%s" "!="
|
2020-12-10 13:51:50 +03:00
|
|
|
| Lt k -> Format.fprintf fmt "%s%a" "<" format_op_kind k
|
|
|
|
| Lte k -> Format.fprintf fmt "%s%a" "<=" format_op_kind k
|
|
|
|
| Gt k -> Format.fprintf fmt "%s%a" ">" format_op_kind k
|
|
|
|
| Gte k -> Format.fprintf fmt "%s%a" ">=" format_op_kind k
|
2020-12-28 01:53:02 +03:00
|
|
|
| Map -> Format.fprintf fmt "map"
|
2021-01-10 20:11:46 +03:00
|
|
|
| Filter -> Format.fprintf fmt "filter"
|
2020-12-28 01:53:02 +03:00
|
|
|
|
|
|
|
let format_ternop (fmt : Format.formatter) (op : ternop Pos.marked) : unit =
|
|
|
|
match Pos.unmark op with Fold -> Format.fprintf fmt "fold"
|
2020-11-26 12:38:13 +03:00
|
|
|
|
2020-12-11 12:51:46 +03:00
|
|
|
let format_log_entry (fmt : Format.formatter) (entry : log_entry) : unit =
|
2021-01-09 19:44:45 +03:00
|
|
|
match entry with
|
2021-01-13 14:04:14 +03:00
|
|
|
| VarDef -> Format.fprintf fmt "%s" (Utils.Cli.print_with_style [ ANSITerminal.blue ] "≔ ")
|
|
|
|
| BeginCall -> Format.fprintf fmt "%s" (Utils.Cli.print_with_style [ ANSITerminal.yellow ] "→ ")
|
|
|
|
| EndCall -> Format.fprintf fmt "%s" (Utils.Cli.print_with_style [ ANSITerminal.yellow ] "← ")
|
2021-01-20 21:58:48 +03:00
|
|
|
| PosRecordIfTrueBool ->
|
|
|
|
Format.fprintf fmt "%s" (Utils.Cli.print_with_style [ ANSITerminal.green ] "☛ ")
|
2020-12-11 12:51:46 +03:00
|
|
|
|
2020-11-26 12:38:13 +03:00
|
|
|
let format_unop (fmt : Format.formatter) (op : unop Pos.marked) : unit =
|
2020-12-09 13:23:03 +03:00
|
|
|
Format.fprintf fmt "%s"
|
2020-12-11 12:51:46 +03:00
|
|
|
( match Pos.unmark op with
|
|
|
|
| Minus _ -> "-"
|
|
|
|
| Not -> "~"
|
|
|
|
| ErrorOnEmpty -> "error_empty"
|
|
|
|
| Log (entry, infos) ->
|
|
|
|
Format.asprintf "log@[<hov 2>[%a|%a]@]" format_log_entry entry
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ".")
|
|
|
|
(fun fmt info -> Utils.Uid.MarkedString.format_info fmt info))
|
2020-12-28 01:53:02 +03:00
|
|
|
infos
|
2021-01-04 02:13:59 +03:00
|
|
|
| Length -> "length"
|
2021-01-05 18:00:15 +03:00
|
|
|
| IntToRat -> "int_to_rat"
|
|
|
|
| GetDay -> "get_day"
|
|
|
|
| GetMonth -> "get_month"
|
|
|
|
| GetYear -> "get_year" )
|
2020-11-26 12:38:13 +03:00
|
|
|
|
2020-11-26 15:38:42 +03:00
|
|
|
let needs_parens (e : expr Pos.marked) : bool =
|
2020-12-11 12:51:46 +03:00
|
|
|
match Pos.unmark e with EAbs _ | EApp _ -> true | _ -> false
|
2020-11-26 15:38:42 +03:00
|
|
|
|
|
|
|
let format_var (fmt : Format.formatter) (v : Var.t) : unit =
|
2021-01-04 02:13:59 +03:00
|
|
|
Format.fprintf fmt "%s" (Bindlib.name_of v)
|
2020-11-26 15:38:42 +03:00
|
|
|
|
2021-01-14 02:17:24 +03:00
|
|
|
let rec format_expr (ctx : Ast.decl_ctx) (fmt : Format.formatter) (e : expr Pos.marked) : unit =
|
|
|
|
let format_expr = format_expr ctx in
|
2020-11-26 15:38:42 +03:00
|
|
|
let format_with_parens (fmt : Format.formatter) (e : expr Pos.marked) =
|
|
|
|
if needs_parens e then Format.fprintf fmt "(%a)" format_expr e
|
|
|
|
else Format.fprintf fmt "%a" format_expr e
|
|
|
|
in
|
2020-11-26 12:38:13 +03:00
|
|
|
match Pos.unmark e with
|
2020-11-27 20:36:38 +03:00
|
|
|
| EVar v -> Format.fprintf fmt "%a" format_var (Pos.unmark v)
|
2021-01-14 02:17:24 +03:00
|
|
|
| ETuple (es, None) ->
|
2020-12-31 02:28:26 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>(%a)@]"
|
2020-12-05 20:12:53 +03:00
|
|
|
(Format.pp_print_list
|
2020-12-31 02:28:26 +03:00
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ",@ ")
|
2021-01-14 02:17:24 +03:00
|
|
|
(fun fmt e -> Format.fprintf fmt "%a" format_expr e))
|
2020-11-26 12:38:13 +03:00
|
|
|
es
|
2021-01-14 02:17:24 +03:00
|
|
|
| ETuple (es, Some s) ->
|
|
|
|
Format.fprintf fmt "%a {@[<hov 2>%a@]}" Ast.StructName.format_t s
|
|
|
|
(Format.pp_print_list
|
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ",@ ")
|
|
|
|
(fun fmt (e, struct_field) ->
|
|
|
|
Format.fprintf fmt "\"%a\":@ %a" Ast.StructFieldName.format_t struct_field format_expr
|
|
|
|
e))
|
|
|
|
(List.combine es (Ast.StructMap.find s ctx.ctx_structs))
|
2020-12-28 01:53:02 +03:00
|
|
|
| EArray es ->
|
2020-12-31 02:28:26 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>[%a]@]"
|
2020-12-28 01:53:02 +03:00
|
|
|
(Format.pp_print_list
|
2020-12-30 00:26:10 +03:00
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt ";@ ")
|
2021-01-09 19:44:45 +03:00
|
|
|
(fun fmt e -> Format.fprintf fmt "%a" format_expr e))
|
2020-12-28 01:53:02 +03:00
|
|
|
es
|
2021-01-14 02:17:24 +03:00
|
|
|
| ETupleAccess (e1, n, s, _ts) -> (
|
|
|
|
match s with
|
2020-12-05 20:12:53 +03:00
|
|
|
| None -> Format.fprintf fmt "%a.%d" format_expr e1 n
|
2021-01-14 02:17:24 +03:00
|
|
|
| Some s ->
|
|
|
|
Format.fprintf fmt "%a.\"%a\"" format_expr e1 Ast.StructFieldName.format_t
|
|
|
|
(List.nth (Ast.StructMap.find s ctx.ctx_structs) n) )
|
|
|
|
| EInj (e, n, en, _ts) ->
|
|
|
|
Format.fprintf fmt "@[<hov 2>%a@ %a@]" Ast.EnumConstructor.format_t
|
|
|
|
(List.nth (Ast.EnumMap.find en ctx.ctx_enums) n)
|
|
|
|
format_expr e
|
|
|
|
| EMatch (e, es, e_name) ->
|
2020-12-30 14:02:09 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>match@ %a@ with@ %a@]" format_expr e
|
2020-12-05 20:12:53 +03:00
|
|
|
(Format.pp_print_list
|
2020-12-30 14:02:09 +03:00
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt "@ |@ ")
|
2020-12-05 20:12:53 +03:00
|
|
|
(fun fmt (e, c) ->
|
2021-01-14 02:17:24 +03:00
|
|
|
Format.fprintf fmt "%a@ %a" Ast.EnumConstructor.format_t c format_expr e))
|
|
|
|
(List.combine es (Ast.EnumMap.find e_name ctx.ctx_enums))
|
2020-11-26 12:38:13 +03:00
|
|
|
| ELit l -> Format.fprintf fmt "%a" format_lit (Pos.same_pos_as l e)
|
2020-11-26 15:38:42 +03:00
|
|
|
| EApp ((EAbs (_, binder, taus), _), args) ->
|
|
|
|
let xs, body = Bindlib.unmbind binder in
|
|
|
|
let xs_tau = List.map2 (fun x tau -> (x, tau)) (Array.to_list xs) taus in
|
|
|
|
let xs_tau_arg = List.map2 (fun (x, tau) arg -> (x, tau, arg)) xs_tau args in
|
|
|
|
Format.fprintf fmt "@[%a%a@]"
|
|
|
|
(Format.pp_print_list
|
2020-12-30 14:02:09 +03:00
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt "@ ")
|
2020-11-26 15:38:42 +03:00
|
|
|
(fun fmt (x, tau, arg) ->
|
|
|
|
Format.fprintf fmt "@[@[<hov 2>let@ %a@ :@ %a@ =@ %a@]@ in@\n@]" format_var x
|
2021-01-14 02:17:24 +03:00
|
|
|
(format_typ ctx) tau format_expr arg))
|
2020-11-26 15:38:42 +03:00
|
|
|
xs_tau_arg format_expr body
|
2020-11-26 12:38:13 +03:00
|
|
|
| EAbs (_, binder, taus) ->
|
|
|
|
let xs, body = Bindlib.unmbind binder in
|
|
|
|
let xs_tau = List.map2 (fun x tau -> (x, tau)) (Array.to_list xs) taus in
|
2020-12-30 14:02:09 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>λ@ %a →@ %a@]"
|
2020-11-26 12:38:13 +03:00
|
|
|
(Format.pp_print_list
|
2020-12-30 14:02:09 +03:00
|
|
|
~pp_sep:(fun fmt () -> Format.fprintf fmt "@ ")
|
2020-12-30 00:26:10 +03:00
|
|
|
(fun fmt (x, tau) ->
|
2021-01-14 02:17:24 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>(%a:@ %a)@]" format_var x (format_typ ctx) tau))
|
2020-11-26 12:38:13 +03:00
|
|
|
xs_tau format_expr body
|
2021-01-10 20:11:46 +03:00
|
|
|
| EApp ((EOp (Binop ((Ast.Map | Ast.Filter) as op)), _), [ arg1; arg2 ]) ->
|
|
|
|
Format.fprintf fmt "@[<hov 2>%a@ %a@ %a@]" format_binop (op, Pos.no_pos) format_with_parens
|
|
|
|
arg1 format_with_parens arg2
|
2020-11-26 12:38:13 +03:00
|
|
|
| EApp ((EOp (Binop op), _), [ arg1; arg2 ]) ->
|
2020-12-30 00:26:10 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>%a@ %a@ %a@]" format_with_parens arg1 format_binop
|
|
|
|
(op, Pos.no_pos) format_with_parens arg2
|
2020-11-26 12:38:13 +03:00
|
|
|
| EApp ((EOp (Unop op), _), [ arg1 ]) ->
|
2020-12-30 00:26:10 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>%a@ %a@]" format_unop (op, Pos.no_pos) format_with_parens arg1
|
2020-11-26 12:38:13 +03:00
|
|
|
| EApp (f, args) ->
|
2020-12-30 00:26:10 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>%a@ %a@]" format_expr f
|
2020-11-26 15:38:42 +03:00
|
|
|
(Format.pp_print_list ~pp_sep:(fun fmt () -> Format.fprintf fmt "@ ") format_with_parens)
|
2020-11-26 12:38:13 +03:00
|
|
|
args
|
|
|
|
| EIfThenElse (e1, e2, e3) ->
|
2021-01-09 19:44:45 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2> if@ @[<hov 2>%a@]@ then@ @[<hov 2>%a@]@ else@ @[<hov 2>%a@]@]"
|
|
|
|
format_expr e1 format_expr e2 format_expr e3
|
2020-12-28 01:53:02 +03:00
|
|
|
| EOp (Ternop op) -> Format.fprintf fmt "%a" format_ternop (op, Pos.no_pos)
|
2020-11-26 12:38:13 +03:00
|
|
|
| EOp (Binop op) -> Format.fprintf fmt "%a" format_binop (op, Pos.no_pos)
|
|
|
|
| EOp (Unop op) -> Format.fprintf fmt "%a" format_unop (op, Pos.no_pos)
|
2020-12-18 17:59:15 +03:00
|
|
|
| EDefault (exceptions, just, cons) ->
|
|
|
|
if List.length exceptions = 0 then
|
2020-12-30 00:26:10 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>⟨%a@ ⊢@ %a⟩@]" format_expr just format_expr cons
|
2020-11-26 15:38:42 +03:00
|
|
|
else
|
2020-12-30 14:02:09 +03:00
|
|
|
Format.fprintf fmt "@[<hov 2>⟨%a@ |@ %a@ ⊢@ %a@ ⟩@]"
|
2020-11-26 15:38:42 +03:00
|
|
|
(Format.pp_print_list ~pp_sep:(fun fmt () -> Format.fprintf fmt ",@ ") format_expr)
|
2020-12-18 17:59:15 +03:00
|
|
|
exceptions format_expr just format_expr cons
|
2020-12-10 20:11:43 +03:00
|
|
|
| EAssert e' -> Format.fprintf fmt "@[<hov 2>assert@ (%a)@]" format_expr e'
|