From a9253d8996f93d7e645e9c1db26724ae046a2084 Mon Sep 17 00:00:00 2001 From: Josh Berdine Date: Thu, 15 Dec 2016 06:04:20 -0800 Subject: [PATCH] Directly handle javac -classes_out option in build command Summary: The javac -classes_out option is used to set the results directory for the buck build system integration. Reviewed By: jeremydubreil Differential Revision: D4162907 fbshipit-source-id: 75d0a6d --- infer/lib/python/inferlib/jwlib.py | 7 ------- infer/src/base/CommandLineOption.ml | 29 +++++++++++++++++++--------- infer/src/base/CommandLineOption.mli | 3 +++ infer/src/base/Config.ml | 17 ++++++++++++++++ 4 files changed, 40 insertions(+), 16 deletions(-) diff --git a/infer/lib/python/inferlib/jwlib.py b/infer/lib/python/inferlib/jwlib.py index bf163911c..b0b475f38 100644 --- a/infer/lib/python/inferlib/jwlib.py +++ b/infer/lib/python/inferlib/jwlib.py @@ -246,12 +246,6 @@ class AnalyzerWithFrontendWrapper(analyze.AnalyzerWrapper): if self.javac.original_arguments is None: raise Exception('No javac command detected') - if self.args.buck: - self.args.infer_out = os.path.join( - self.javac.args.classes_out, - config.BUCK_INFER_OUT) - self.args.infer_out = os.path.abspath(self.args.infer_out) - def compute_buck_key(self): javac_version = self.javac.get_version() infer_version = utils.infer_key(self.args.analyzer) @@ -296,7 +290,6 @@ class AnalyzerWithFrontendWrapper(analyze.AnalyzerWrapper): infer_cmd = [utils.get_cmd_in_bin_dir('InferJava')] infer_cmd += [ - '-results_dir', self.args.infer_out, '-verbose_out', self.javac.verbose_out, '-suppress_warnings_out', self.javac.suppress_warnings_out, ] diff --git a/infer/src/base/CommandLineOption.ml b/infer/src/base/CommandLineOption.ml index d2076ced2..abff13d33 100644 --- a/infer/src/base/CommandLineOption.ml +++ b/infer/src/base/CommandLineOption.ml @@ -526,16 +526,21 @@ let prepend_to_argv args = args @ cl_args (** [prefix_before_rest (prefix @ ["--" :: rest])] is [prefix] where "--" is not in [prefix]. *) -let prefix_before_rest args = - let rec prefix_before_rest_ rev_keep = function - | [] | "--" :: _ -> IList.rev rev_keep - | keep :: args -> prefix_before_rest_ (keep :: rev_keep) args in - prefix_before_rest_ [] args +let rev_prefix_before_rest args = + let rec rev_prefix_before_rest_ rev_keep = function + | [] | "--" :: _ -> rev_keep + | keep :: args -> rev_prefix_before_rest_ (keep :: rev_keep) args in + rev_prefix_before_rest_ [] args (** environment variable use to pass arguments from parent to child processes *) let args_env_var = "INFER_ARGS" +let extra_env_args = ref [] + +let extend_env_args args = + extra_env_args := List.rev_append args !extra_env_args + let parse ?(incomplete=false) ?(accept_unknown=false) ?config_file current_exe exe_usage = let full_speclist = ref [] in @@ -669,8 +674,14 @@ let parse ?(incomplete=false) ?(accept_unknown=false) ?config_file current_exe e | Arg.Help usage_msg -> Pervasives.print_string usage_msg; exit 0 in parse_loop (); - if not incomplete then - Unix.putenv - ~key:args_env_var - ~data:(encode_argv_to_env (prefix_before_rest (IList.tl (Array.to_list !args_to_parse)))) ; + if not incomplete then ( + (* reread args_to_parse instead of using all_args since mk_path_helper may have modified them *) + let prog_args = + List.rev_append + (rev_prefix_before_rest (Array.to_list !args_to_parse)) + (List.rev !extra_env_args) in + (* do not include program path in args passed via env var *) + let args = Option.value (List.tl prog_args) ~default:[] in + Unix.putenv ~key:args_env_var ~data:(encode_argv_to_env args) + ); curr_usage diff --git a/infer/src/base/CommandLineOption.mli b/infer/src/base/CommandLineOption.mli index 462655e9d..130fc0588 100644 --- a/infer/src/base/CommandLineOption.mli +++ b/infer/src/base/CommandLineOption.mli @@ -137,6 +137,9 @@ val args_env_var : string (** separator of argv elements when encoded into environment variables *) val env_var_sep : char +(** [extend_env_args args] appends [args] to those passed via [args_env_var] *) +val extend_env_args : string list -> unit + (** [parse env_var exe_usage exe] parses command line arguments as specified by preceding calls to the [mk_*] functions, and returns a function that prints the usage message and help text then exits. [exe] is used to construct the help message appropriate for that executable. The decoded diff --git a/infer/src/base/Config.ml b/infer/src/base/Config.ml index 1fa4916fe..90e22e078 100644 --- a/infer/src/base/Config.ml +++ b/infer/src/base/Config.ml @@ -78,6 +78,8 @@ let buck_generated_folder = "buck-out/gen" let buck_infer_deps_file_name = "infer-deps.txt" +let buck_results_dir_name = "infer" + let captured_dir_name = "captured" let checks_disabled_by_default = [ @@ -1229,14 +1231,29 @@ and xml_specs = CLOpt.mk_bool ~deprecated:["xml"] ~long:"xml-specs" "Export specs into XML files file1.xml ... filen.xml" +let javac_classes_out = ref None + (* The "rest" args must appear after "--" on the command line, and hence after other args, so they are allowed to refer to the other arg variables. *) let rest = + let classes_out_spec = + Arg.String (fun classes_out -> + javac_classes_out := Some classes_out ; + if !buck then ( + let classes_out_infer = resolve classes_out ^/ buck_results_dir_name in + (* extend env var args to pass args to children that do not receive the rest args *) + CLOpt.extend_env_args ["--results-dir"; classes_out_infer] ; + results_dir := classes_out_infer + ) + ) in CLOpt.mk_subcommand ~exes:CLOpt.[Toplevel] "Stop argument processing, use remaining arguments as a build command" (fun build_exe -> match Filename.basename build_exe with + | "java" | "javac" -> [ + ("-classes_out", classes_out_spec, ""); ("-d", classes_out_spec, "") + ] | _ -> [] )