diff --git a/infer/src/backend/InferPrint.re b/infer/src/backend/InferPrint.re index 047e3edd9..8e79e1a66 100644 --- a/infer/src/backend/InferPrint.re +++ b/infer/src/backend/InferPrint.re @@ -477,18 +477,6 @@ let module IssuesJson = { let is_first_item = ref true; let pp_json_open fmt () => F.fprintf fmt "[@?"; let pp_json_close fmt () => F.fprintf fmt "]\n@?"; - let expand_links_under_buck_out file => - if (Utils.string_is_prefix Config.buck_generated_folder file) { - try { - let file = Unix.readlink file; - let source_file = DB.source_file_from_string file; - DB.source_file_to_rel_path source_file - } { - | Unix.Unix_error _ => file - } - } else { - file - }; /** Write bug report in JSON format */ let pp_issues_of_error_log fmt error_filter _ proc_loc_opt procname err_log => { @@ -522,7 +510,7 @@ let module IssuesJson = { let kind = Exceptions.err_kind_string ekind; let bug_type = Localise.to_string error_name; let procedure_id = Procname.to_filename procname; - let file = expand_links_under_buck_out (DB.source_file_to_string source_file); + let file = DB.source_file_to_string source_file; let json_ml_loc = switch ml_loc_opt { | Some (file, lnum, cnum, enum) when Config.reports_include_ml_loc => diff --git a/infer/src/backend/inferconfig.ml b/infer/src/backend/inferconfig.ml index 79d1da077..a38b7a5f4 100644 --- a/infer/src/backend/inferconfig.ml +++ b/infer/src/backend/inferconfig.ml @@ -262,7 +262,7 @@ let test () = directory_iter (fun path -> if DB.is_source_file path then - let source_file = (DB.source_file_from_string path) in + let source_file = DB.source_file_from_abs_path path in let matching = matching_analyzers source_file in if matching <> [] then let matching_s = join_strings ", " (IList.map fst matching) in diff --git a/infer/src/base/Config.ml b/infer/src/base/Config.ml index 78bcffe12..7c563d8ac 100644 --- a/infer/src/base/Config.ml +++ b/infer/src/base/Config.ml @@ -650,7 +650,8 @@ and calls_csv = and changed_files_index = CLOpt.mk_path_opt ~long:"changed-files-index" ~exes:CLOpt.[Toplevel] ~meta:"file" - "Specify the file containing the list of files from which reactive analysis should start" + "Specify the file containing the list of source files from which reactive analysis should \ + start. Source files should be specified relative to project root or be absolute" and check_duplicate_symbols = CLOpt.mk_bool ~long:"check-duplicate-symbols" diff --git a/infer/src/base/DB.ml b/infer/src/base/DB.ml index 205500291..3164e70e0 100644 --- a/infer/src/base/DB.ml +++ b/infer/src/base/DB.ml @@ -40,12 +40,6 @@ module SourceFileMap = Map.Make(OrderedSourceFile) module SourceFileSet = Set.Make(OrderedSourceFile) -let source_file_from_string path = - if Filename.is_relative path then - RelativeProjectRoot path - else - Absolute path - let rel_path_from_abs_path root fname = let relative_complemented_fname = filename_to_relative root fname in if string_is_prefix root fname && @@ -53,7 +47,6 @@ let rel_path_from_abs_path root fname = Some relative_complemented_fname else None (* The project root is not a prefix of the file name *) -(** convert a project root directory and a full path to a rooted source file *) let source_file_from_abs_path fname = (* IMPORTANT: results of realpath are cached to not ruin performance *) let fname_real = realpath fname in @@ -75,8 +68,8 @@ let curr_encoding = `Enc_crc let source_file_to_string fname = match fname with + | RelativeInferModel path -> "INFER_MODEL/" ^ path | RelativeProjectRoot path - | RelativeInferModel path | Absolute path -> path let source_file_pp fmt fname = @@ -96,7 +89,7 @@ let source_file_line_count source_file = let source_file_to_rel_path fname = match fname with | RelativeProjectRoot path -> path - | _ -> source_file_to_abs_path fname |> filename_to_relative Config.project_root + | _ -> source_file_to_abs_path fname (** string encoding of a source file (including path) as a single filename *) let source_file_encoding source_file = @@ -155,6 +148,20 @@ let source_file_of_header header_file = | _ -> None in Option.map source_file_from_abs_path file_opt +let changed_source_files_set = + let create_source_file path = + if Filename.is_relative path then + (* sources in changed-files-index may be specified relative to project root *) + RelativeProjectRoot path + else + source_file_from_abs_path path in + Option.map_default read_file None Config.changed_files_index |> + Option.map ( + IList.fold_left + (fun changed_files line -> SourceFileSet.add (create_source_file line) changed_files) + SourceFileSet.empty + ) + (** {2 Source Dirs} *) (** source directory: the directory inside the results dir corresponding to a source file *) @@ -405,11 +412,3 @@ let fold_paths_matching ~dir ~p ~init ~f = matcher function p *) let paths_matching dir p = fold_paths_matching ~dir ~p ~init:[] ~f:(fun x xs -> x :: xs) - -let changed_source_files_set = - Option.map_default read_file None Config.changed_files_index |> - Option.map ( - IList.fold_left - (fun changed_files line -> SourceFileSet.add (source_file_from_string line) changed_files) - SourceFileSet.empty - ) diff --git a/infer/src/base/DB.mli b/infer/src/base/DB.mli index 2f022f0e6..69f7f7f1a 100644 --- a/infer/src/base/DB.mli +++ b/infer/src/base/DB.mli @@ -94,21 +94,21 @@ val source_file_line_count : source_file -> int (** empty source file *) val source_file_empty : source_file +(** create source file from absolute path *) val source_file_from_abs_path : string -> source_file (** string encoding of a source file (including path) as a single filename *) val source_file_encoding : source_file -> string -(** convert a source file to a string *) +(** convert a source file to a string + WARNING: result may not be valid file path, do not use this function to perform operations + on filenames *) val source_file_to_string : source_file -> string -(** convert a string obtained by source_file_to_string to a source file *) -val source_file_from_string : string -> source_file - (** pretty print source_file *) val source_file_pp : Format.formatter -> source_file -> unit -(** get the full path of a source file, raise No_project_root exception when used with a relative source file and no project root specified *) +(** get the full path of a source file *) val source_file_to_abs_path : source_file -> string (** get the relative path of a source file *) @@ -126,6 +126,9 @@ val source_file_is_under_project_root : source_file -> bool file exists. returns None otherwise *) val source_file_of_header : source_file -> source_file option +(** Set of files read from --changed-files-index file, None if option not specified *) +val changed_source_files_set : SourceFileSet.t option + (** {2 Source Dirs} *) (** source directory: the directory inside the results dir corresponding to a source file *) @@ -170,6 +173,3 @@ val fold_paths_matching : (** Return all file paths recursively under the given directory which match the given predicate *) val paths_matching : string -> (string -> bool) -> string list - -(** Set of files read from --changed-files-index file, None if option not specified *) -val changed_source_files_set : SourceFileSet.t option diff --git a/infer/src/clang/cFrontend_utils.ml b/infer/src/clang/cFrontend_utils.ml index b0230dc0e..9615be5eb 100644 --- a/infer/src/clang/cFrontend_utils.ml +++ b/infer/src/clang/cFrontend_utils.ml @@ -625,12 +625,6 @@ struct let class_name = Ast_utils.get_class_name_from_member field_qual_name in Ident.create_fieldname (Mangled.mangled field_name class_name) 0 - let get_rel_file_path file_opt = - match file_opt with - | Some file -> - DB.source_file_to_string (DB.source_file_from_abs_path file) - | None -> "" - let is_cpp_translation translation_unit_context = let lang = translation_unit_context.CFrontend_config.lang in lang = CFrontend_config.CPP || lang = CFrontend_config.ObjCPP @@ -660,6 +654,11 @@ struct | _ -> assert false) let mk_procname_from_function translation_unit_context name function_decl_info_opt = + let get_rel_file_path file_opt = + match file_opt with + | Some file -> + DB.source_file_to_string (DB.source_file_from_abs_path file) + | None -> "" in let file = match function_decl_info_opt with | Some (decl_info, function_decl_info) -> diff --git a/infer/src/harness/inhabit.ml b/infer/src/harness/inhabit.ml index 17d80602f..a09c6a82a 100644 --- a/infer/src/harness/inhabit.ml +++ b/infer/src/harness/inhabit.ml @@ -202,22 +202,18 @@ let inhabit_call tenv (procname, receiver) cfg env = with Not_found -> env (** create a dummy file for the harness and associate them in the exe_env *) -let create_dummy_harness_file harness_name = - let dummy_file_name = - let dummy_file_dir = - Filename.get_temp_dir_name () in - let file_str = - Procname.java_get_class_name - harness_name ^ "_" ^Procname.java_get_method harness_name ^ ".java" in - Filename.concat dummy_file_dir file_str in - DB.source_file_from_string dummy_file_name +let create_dummy_harness_filename harness_name = + let dummy_file_dir = + Filename.get_temp_dir_name () in + let file_str = + Procname.java_get_class_name + harness_name ^ "_" ^Procname.java_get_method harness_name ^ ".java" in + Filename.concat dummy_file_dir file_str (** write the SIL for the harness to a file *) (* TODO (t3040429): fill this file up with Java-like code that matches the SIL *) -let write_harness_to_file harness_instrs harness_file = - let harness_file = - let harness_file_name = DB.source_file_to_abs_path harness_file in - create_outfile harness_file_name in +let write_harness_to_file harness_instrs harness_file_name = + let harness_file = create_outfile harness_file_name in let pp_harness fmt = IList.iter (fun instr -> Format.fprintf fmt "%a\n" (Sil.pp_instr pe_text) instr) harness_instrs in do_outf harness_file (fun outf -> @@ -266,7 +262,7 @@ let setup_harness_cfg harness_name env cg cfg = let inhabit_trace tenv trace harness_name cg cfg = if IList.length trace > 0 then let source_file = Cg.get_source cg in - let harness_file = create_dummy_harness_file harness_name in + let harness_filename = create_dummy_harness_filename harness_name in let start_line = 1 in let empty_env = let pc = { Location.line = start_line; col = 1; file = source_file; } in @@ -279,5 +275,5 @@ let inhabit_trace tenv trace harness_name cg cfg = let env'' = IList.fold_left (fun env to_call -> inhabit_call tenv to_call cfg env) empty_env trace in try setup_harness_cfg harness_name env'' cg cfg; - write_harness_to_file (IList.rev env''.instrs) harness_file + write_harness_to_file (IList.rev env''.instrs) harness_filename with Not_found -> ()