@@ -407,15 +407,36 @@ let main () =
407407 (* Initialize I/O + interaction module *)
408408 let module State = struct
409409 type t = {
410- prvopts : prv_options ;
411- input : string option ;
412- terminal : T .terminal lazy_t ;
413- interactive : bool ;
414- eco : bool ;
415- gccompact : int option ;
416- docgen : bool ;
417- outdirp : string option ;
410+ (* ---*) prvopts : prv_options ;
411+ (* ---*) input : string option ;
412+ (* ---*) terminal : T .terminal lazy_t ;
413+ (* ---*) interactive : bool ;
414+ (* ---*) eco : bool ;
415+ (* ---*) gccompact : int option ;
416+ (* ---*) docgen : bool ;
417+ (* ---*) outdirp : string option ;
418+ mutable trace : trace1 list option ;
418419 }
420+
421+ and trace1 =
422+ { position : int
423+ ; goals : string list option
424+ ; messages : (EcGState .loglevel * string ) list }
425+
426+ module Trace = struct
427+ let trace0 : trace1 =
428+ { position = 0 ; goals = None ; messages = [] ; }
429+
430+ let push1_message (trace1 : trace1 ) (msg , lvl ) : trace1 =
431+ { trace1 with messages = (msg, lvl) :: trace1.messages }
432+
433+ let push_message (trace : trace1 list ) msg =
434+ match trace with
435+ | [] ->
436+ [push1_message trace0 msg]
437+ | trace1 :: trace ->
438+ push1_message trace1 msg :: trace
439+ end
419440 end in
420441
421442 let state : State.t =
@@ -471,7 +492,8 @@ let main () =
471492 ; eco = false
472493 ; gccompact = None
473494 ; docgen = false
474- ; outdirp = None }
495+ ; outdirp = None
496+ ; trace = None }
475497
476498 end
477499
@@ -493,14 +515,20 @@ let main () =
493515 lazy (T. from_channel ~name ~gcstats ~progress (open_in name))
494516 in
495517
518+ let trace0 =
519+ if cmpopts.cmpo_trace then
520+ Some [State. { position = 0 ; goals = None ; messages = [] }]
521+ else None in
522+
496523 { prvopts = {cmpopts.cmpo_provers with prvo_iterate = true }
497524 ; input = Some name
498525 ; terminal = terminal
499526 ; interactive = false
500527 ; eco = cmpopts.cmpo_noeco
501528 ; gccompact = cmpopts.cmpo_compact
502529 ; docgen = false
503- ; outdirp = None }
530+ ; outdirp = None
531+ ; trace = trace0 }
504532
505533 end
506534
@@ -543,7 +571,8 @@ let main () =
543571 ; eco = true
544572 ; gccompact = None
545573 ; docgen = true
546- ; outdirp = docopts.doco_outdirp }
574+ ; outdirp = docopts.doco_outdirp
575+ ; trace = None }
547576 end
548577
549578 in
@@ -571,7 +600,20 @@ let main () =
571600
572601 assert (nameo <> input);
573602
574- let eco = EcEco. {
603+ let eco =
604+ let mktrace (trace : State.trace1 list ) : EcEco.ecotrace =
605+ let mktrace1 (trace1 : State.trace1 ) : int * EcEco.ecotrace1 =
606+ let goals = Option. value ~default: [] trace1.goals in
607+ let messages =
608+ let for1 (lvl , msg ) =
609+ Format. sprintf " %s: %s"
610+ (EcGState. string_of_loglevel lvl)
611+ msg in
612+ String. concat " \n " (List. rev_map for1 trace1.messages) in
613+ (trace1.position, EcEco. { goals; messages; })
614+ in List. rev_map mktrace1 trace in
615+
616+ EcEco. {
575617 eco_root = EcEco. {
576618 eco_digest = Digest. file input;
577619 eco_kind = kind;
@@ -584,6 +626,7 @@ let main () =
584626 eco_kind = x.rqd_kind;
585627 } in (x.rqd_name, (ecr, x.rqd_direct)))
586628 (EcScope.Theory. required scope));
629+ eco_trace = Option. map mktrace state.trace;
587630 } in
588631
589632 let out = open_out nameo in
@@ -665,7 +708,10 @@ let main () =
665708 EcScope. hierror " invalid pragma: `%s'\n %!" x);
666709
667710 let notifier (lvl : EcGState.loglevel ) (lazy msg ) =
668- T. notice ~immediate: true lvl msg terminal
711+ state.trace < - state.trace |> Option. map (fun trace ->
712+ State.Trace. push_message trace (lvl, msg)
713+ );
714+ T. notice ~immediate: true lvl msg terminal;
669715 in
670716
671717 EcCommands. addnotifier notifier;
@@ -694,8 +740,25 @@ let main () =
694740 let timed = p.EP. gl_debug = Some `Timed in
695741 let break = p.EP. gl_debug = Some `Break in
696742 let ignore_fail = ref false in
743+
744+ state.trace < - state.trace |> Option. map (fun trace ->
745+ { State.Trace. trace0 with position = loc.loc_echar } :: trace
746+ );
747+
697748 try
698749 let tdelta = EcCommands. process ~src ~timed ~break p.EP. gl_action in
750+
751+ state.trace < - state.trace |> Option. map (fun trace ->
752+ match trace with
753+ | [] -> assert false
754+ | trace1 :: trace ->
755+ assert (Option. is_none trace1.State. goals);
756+ let goals = EcCommands. pp_all_goals () in
757+ let goals = if List. is_empty goals then None else Some goals in
758+ let trace1 = { trace1 with goals } in
759+ trace1 :: trace
760+ );
761+
699762 if p.EP. gl_fail then begin
700763 ignore_fail := true ;
701764 raise (EcScope. HiScopeError (None , " this command is expected to fail" ))
@@ -713,10 +776,10 @@ let main () =
713776 raise (EcScope. toperror_of_exn ~gloc: loc e)
714777 end ;
715778 if T. interactive terminal then begin
716- let error =
717- Format. asprintf
718- " The following error has been ignored:@.@.@%a"
719- EcPException. exn_printer e in
779+ let error =
780+ Format. asprintf
781+ " The following error has been ignored:@.@.@%a"
782+ EcPException. exn_printer e in
720783 T. notice ~immediate: true `Info error terminal
721784 end
722785 end )
0 commit comments