From dd2b9675d6a721da62024ae811c29a2db4650d8c Mon Sep 17 00:00:00 2001 From: Jules Villard Date: Tue, 16 Oct 2018 04:01:54 -0700 Subject: [PATCH] [log] print only innermost source file context of crash Summary: When the backend crashes we print which instruction/file/... we were analysing, but because of recursion we can end up repeating that information all the way to the toplevel call. This makes sure we only print the innermost one, we don't care about the calling context because the analysis is compositional. Reviewed By: mbouaziz Differential Revision: D10381141 fbshipit-source-id: 1c92bb861 --- infer/src/absint/AbstractInterpreter.ml | 14 ++++++++++++-- infer/src/backend/ondemand.ml | 21 +++++++++++++++------ 2 files changed, 27 insertions(+), 8 deletions(-) diff --git a/infer/src/absint/AbstractInterpreter.ml b/infer/src/absint/AbstractInterpreter.ml index 9d1dc4c55..dc02f8b91 100644 --- a/infer/src/absint/AbstractInterpreter.ml +++ b/infer/src/absint/AbstractInterpreter.ml @@ -114,6 +114,9 @@ module AbstractInterpreterCommon (TransferFunctions : TransferFunctions.SIL) = s NodePrinter.finish_session underlying_node + (** reference to log errors only at the innermost recursive call *) + let logged_error = ref false + let exec_instrs ~debug proc_data node node_id ~visit_count pre inv_map = let on_instrs instrs = if Config.write_html && debug <> DefaultNoExecInstr_UseFromLowerHilAbstractInterpreterOnly @@ -123,9 +126,16 @@ module AbstractInterpreterCommon (TransferFunctions : TransferFunctions.SIL) = s (Node.underlying_node node) ; let astate_post = let compute_post pre instr = - try TransferFunctions.exec_instr pre proc_data node instr with exn -> + try + let post = TransferFunctions.exec_instr pre proc_data node instr in + (* don't forget to reset this so we output messages for future errors too *) + logged_error := false ; + post + with exn -> IExn.reraise_after exn ~f:(fun () -> - L.internal_error "In instruction %a@\n" (Sil.pp_instr Pp.text) instr ) + if not !logged_error then ( + L.internal_error "In instruction %a@\n" (Sil.pp_instr Pp.text) instr ; + logged_error := true ) ) in Instrs.fold ~f:compute_post ~init:pre instrs in diff --git a/infer/src/backend/ondemand.ml b/infer/src/backend/ondemand.ml index f6c98b82b..3ed4c7da2 100644 --- a/infer/src/backend/ondemand.ml +++ b/infer/src/backend/ondemand.ml @@ -116,6 +116,9 @@ let restore_global_state st = Timeout.resume_previous_timeout () +(** reference to log errors only at the innermost recursive call *) +let logged_error = ref false + let run_proc_analysis analyze_proc ~caller_pdesc callee_pdesc = let callee_pname = Procdesc.get_proc_name callee_pdesc in let log_elapsed_time = @@ -164,17 +167,23 @@ let run_proc_analysis analyze_proc ~caller_pdesc callee_pdesc = else initial_summary in let final_summary = postprocess summary in - restore_global_state old_state ; final_summary + restore_global_state old_state ; + (* don't forget to reset this so we output messages for future errors too *) + logged_error := false ; + final_summary with exn -> ( + let backtrace = Printexc.get_backtrace () in IExn.reraise_if exn ~f:(fun () -> - let source_file = attributes.ProcAttributes.translation_unit in - let location = attributes.ProcAttributes.loc in - L.internal_error "While analysing function %a:%a at %a@\n" SourceFile.pp source_file - Typ.Procname.pp callee_pname Location.pp_file_pos location ; + if not !logged_error then ( + let source_file = attributes.ProcAttributes.translation_unit in + let location = attributes.ProcAttributes.loc in + L.internal_error "While analysing function %a:%a at %a@\n" SourceFile.pp source_file + Typ.Procname.pp callee_pname Location.pp_file_pos location ; + logged_error := true ) ; restore_global_state old_state ; not Config.keep_going ) ; L.internal_error "@\nERROR RUNNING BACKEND: %a %s@\n@\nBACK TRACE@\n%s@?" Typ.Procname.pp - callee_pname (Exn.to_string exn) (Printexc.get_backtrace ()) ; + callee_pname (Exn.to_string exn) backtrace ; match exn with | SymOp.Analysis_failure_exe kind -> (* in production mode, log the timeout/crash and continue with the summary we had before