[infer][ondemand] add a `--keep-going` command line option to specify when to catch the exceptions raised during the analysis

Summary: This will allow us to gradually get rid of the exceptions thrown during the analysis while detecting the regressions earlier

Reviewed By: jberdine, jvillard

Differential Revision: D5385154

fbshipit-source-id: 605e3f5
master
Jeremy Dubreil 7 years ago committed by Facebook Github Bot
parent 3bff58da1e
commit ad54126dab

@ -31,7 +31,7 @@ module Make (P : Payload) : S with type payload = P.payload = struct
let update_summary payload summary = P.update_payload payload summary
let read_summary caller_pdesc callee_pname =
match Ondemand.analyze_proc_name ~propagate_exceptions:false caller_pdesc callee_pname with
match Ondemand.analyze_proc_name caller_pdesc callee_pname with
| None
-> None
| Some summary

@ -128,7 +128,7 @@ let iterate_callbacks call_graph exe_env =
| None
-> failwithf "Could not find proc desc for %a" Typ.Procname.pp pname
| Some pdesc
-> ignore (Ondemand.analyze_proc_desc ~propagate_exceptions:true pdesc pdesc)
-> ignore (Ondemand.analyze_proc_desc pdesc pdesc)
in
Ondemand.set_callbacks callbacks ;
(* Invoke procedure callbacks using on-demand anlaysis schedulling *)

@ -1391,9 +1391,7 @@ let interprocedural_algorithm_closures ~prepare_proc exe_env : Tasks.closure lis
let call_graph = Exe_env.get_cg exe_env in
let process_one_proc proc_name =
prepare_proc proc_name ;
let analyze proc_desc =
ignore (Ondemand.analyze_proc_desc ~propagate_exceptions:false proc_desc proc_desc)
in
let analyze proc_desc = ignore (Ondemand.analyze_proc_desc proc_desc proc_desc) in
match Exe_env.get_proc_desc exe_env proc_name with
| Some proc_desc
when Config.reactive_mode

@ -95,7 +95,7 @@ let restore_global_state st =
State.restore_state st.symexec_state ;
Timeout.resume_previous_timeout ()
let run_proc_analysis ~propagate_exceptions analyze_proc curr_pdesc callee_pdesc =
let run_proc_analysis analyze_proc curr_pdesc callee_pdesc =
let curr_pname = Procdesc.get_proc_name curr_pdesc in
let callee_pname = Procdesc.get_proc_name callee_pdesc in
let log_elapsed_time =
@ -141,18 +141,18 @@ let run_proc_analysis ~propagate_exceptions analyze_proc curr_pdesc callee_pdesc
L.internal_error "@\nONDEMAND EXCEPTION %a %s@.@.BACK TRACE@.%s@?" Typ.Procname.pp callee_pname
(Exn.to_string exn) (Printexc.get_backtrace ()) ;
restore_global_state old_state ;
if propagate_exceptions then raise exn
else
if Config.keep_going then
match exn with
| SymOp.Analysis_failure_exe kind
-> (* in production mode, log the timeout/crash and continue with the summary we had before
the failure occurred *)
the failure occurred *)
log_error_and_continue exn initial_summary kind
| _
-> (* this happens with assert false or some other unrecognized exception *)
log_error_and_continue exn initial_summary (FKcrash (Exn.to_string exn))
else raise exn
let analyze_proc_desc ~propagate_exceptions curr_pdesc callee_pdesc : Specs.summary option =
let analyze_proc_desc curr_pdesc callee_pdesc : Specs.summary option =
let callee_pname = Procdesc.get_proc_name callee_pdesc in
let proc_attributes = Procdesc.get_attributes callee_pdesc in
match !callbacks_ref with
@ -161,15 +161,13 @@ let analyze_proc_desc ~propagate_exceptions curr_pdesc callee_pdesc : Specs.summ
Typ.Procname.pp callee_pname Typ.Procname.pp (Procdesc.get_proc_name curr_pdesc)
| Some callbacks
-> if should_be_analyzed callee_pname proc_attributes then
Some
(run_proc_analysis ~propagate_exceptions callbacks.analyze_ondemand curr_pdesc
callee_pdesc)
Some (run_proc_analysis callbacks.analyze_ondemand curr_pdesc callee_pdesc)
else Specs.get_summary callee_pname
(** analyze_proc_name curr_pdesc proc_name
performs an on-demand analysis of proc_name
triggered during the analysis of curr_pname. *)
let analyze_proc_name ~propagate_exceptions curr_pdesc callee_pname : Specs.summary option =
let analyze_proc_name curr_pdesc callee_pname : Specs.summary option =
match !callbacks_ref with
| None
-> failwithf "No callbacks registered to analyze proc name %a when analyzing %a@."
@ -178,7 +176,7 @@ let analyze_proc_name ~propagate_exceptions curr_pdesc callee_pname : Specs.summ
-> if procedure_should_be_analyzed callee_pname then
match callbacks.get_proc_desc callee_pname with
| Some callee_pdesc
-> analyze_proc_desc ~propagate_exceptions curr_pdesc callee_pdesc
-> analyze_proc_desc curr_pdesc callee_pdesc
| None
-> Specs.get_summary callee_pname
else Specs.get_summary callee_pname

@ -20,14 +20,12 @@ type callbacks = {analyze_ondemand: analyze_ondemand; get_proc_desc: get_proc_de
val get_proc_desc : get_proc_desc
(** Find a proc desc for the procedure, perhaps loading it from disk. *)
val analyze_proc_desc :
propagate_exceptions:bool -> Procdesc.t -> Procdesc.t -> Specs.summary option
val analyze_proc_desc : Procdesc.t -> Procdesc.t -> Specs.summary option
(** analyze_proc_desc curr_pdesc callee_pdesc
performs an on-demand analysis of callee_pdesc
triggered during the analysis of curr_pdesc. *)
val analyze_proc_name :
propagate_exceptions:bool -> Procdesc.t -> Typ.Procname.t -> Specs.summary option
val analyze_proc_name : Procdesc.t -> Typ.Procname.t -> Specs.summary option
(** analyze_proc_name curr_pdesc proc_name
performs an on-demand analysis of proc_name
triggered during the analysis of curr_pdesc. *)

@ -696,12 +696,10 @@ let resolve_and_analyze tenv caller_pdesc prop args callee_proc_name call_flags
whether the method is defined or generated by the specialization *)
let analyze_ondemand resolved_pname : Specs.summary option =
if Typ.Procname.equal resolved_pname callee_proc_name then
Ondemand.analyze_proc_name ~propagate_exceptions:true caller_pdesc callee_proc_name
Ondemand.analyze_proc_name caller_pdesc callee_proc_name
else
(* Create the type sprecialized procedure description and analyze it directly *)
let analyze specialized_pdesc =
Ondemand.analyze_proc_desc ~propagate_exceptions:true caller_pdesc specialized_pdesc
in
let analyze specialized_pdesc = Ondemand.analyze_proc_desc caller_pdesc specialized_pdesc in
let resolved_proc_desc_option =
match Ondemand.get_proc_desc resolved_pname with
| Some resolved_proc_desc
@ -1239,7 +1237,7 @@ let rec sym_exec tenv current_pdesc _instr (prop_: Prop.normal Prop.t) path
let exec_skip_call ret_annots ret_type =
skip_call norm_prop path pname ret_annots loc ret_id (Some ret_type) url_handled_args
in
match Ondemand.analyze_proc_name ~propagate_exceptions:true current_pdesc pname with
match Ondemand.analyze_proc_name current_pdesc pname with
| None
-> let ret_typ = Typ.java_proc_return_typ callee_pname_java in
let ret_annots = load_ret_annots callee_pname in
@ -1263,9 +1261,7 @@ let rec sym_exec tenv current_pdesc _instr (prop_: Prop.normal Prop.t) path
| []
-> callee_pname
in
let resolved_summary_opt =
Ondemand.analyze_proc_name ~propagate_exceptions:true current_pdesc resolved_pname
in
let resolved_summary_opt = Ondemand.analyze_proc_name current_pdesc resolved_pname in
let callee_pdesc_opt = Ondemand.get_proc_desc resolved_pname in
let ret_typ_opt = Option.map ~f:Procdesc.get_ret_type callee_pdesc_opt in
let sentinel_result =

@ -786,6 +786,7 @@ and ( bo_debug
, failures_allowed
, filtering
, frontend_tests
, keep_going
, linters_developer_mode
, only_cheap_debug
, print_buckets
@ -833,6 +834,10 @@ and ( bo_debug
"Show the internal bucket of Infer reports in their textual description"
and print_types =
CLOpt.mk_bool ~long:"print-types" ~default:false "Print types in symbolic heaps"
and keep_going =
CLOpt.mk_bool ~long:"keep-going"
~in_help:CLOpt.([(Analyze, manual_generic)])
~default:true "Keep going when the analysis encounters a failure"
and reports_include_ml_loc =
CLOpt.mk_bool ~deprecated:["with_infer_src_loc"] ~long:"reports-include-ml-loc"
"Include the location in the Infer source code from where reports are generated"
@ -875,7 +880,7 @@ and ( bo_debug
and debug_exceptions =
CLOpt.mk_bool_group ~long:"debug-exceptions"
"Generate lightweight debugging information: just print the internal exceptions during analysis (also sets $(b,--developer-mode), $(b,--no-filtering), $(b,--print-buckets), $(b,--reports-include-ml-loc))"
[developer_mode; print_buckets; reports_include_ml_loc] [filtering]
[developer_mode; print_buckets; reports_include_ml_loc] [filtering; keep_going]
and default_linters =
CLOpt.mk_bool ~long:"default-linters"
~in_help:CLOpt.([(Capture, manual_clang_linters)])
@ -919,6 +924,7 @@ and ( bo_debug
, failures_allowed
, filtering
, frontend_tests
, keep_going
, linters_developer_mode
, only_cheap_debug
, print_buckets
@ -2079,6 +2085,8 @@ and svg = !svg
and symops_per_iteration = !symops_per_iteration
and keep_going = !keep_going
and test_filtering = !test_filtering
and testing_mode = !testing_mode

@ -457,6 +457,8 @@ val jobs : int
val join_cond : int
val keep_going : bool
val latex : string option
val linter : string option

@ -127,7 +127,7 @@ let method_has_annot annot tenv pname =
let method_overrides_annot annot tenv pname = method_overrides (method_has_annot annot) tenv pname
let lookup_annotation_calls caller_pdesc annot pname =
match Ondemand.analyze_proc_name ~propagate_exceptions:false caller_pdesc pname with
match Ondemand.analyze_proc_name caller_pdesc pname with
| Some {Specs.payload= {Specs.annot_map= Some annot_map}} -> (
try AnnotReachabilityDomain.find annot annot_map
with Not_found -> AnnotReachabilityDomain.SinkMap.empty )

@ -522,7 +522,7 @@ let typecheck_instr tenv ext calls_this checks (node: Procdesc.Node.t) idenv get
, etl_
, loc
, cflags )
-> ignore (Ondemand.analyze_proc_name ~propagate_exceptions:true curr_pdesc callee_pname) ;
-> ignore (Ondemand.analyze_proc_name curr_pdesc callee_pname) ;
let callee_attributes =
match Specs.proc_resolve_attributes (* AttributesTable.load_attributes *) callee_pname with
| Some proc_attributes

Loading…
Cancel
Save