@@ -65,7 +65,11 @@ def add_python_version_argument(parser: argparse.ArgumentParser):
6565 type = str ,
6666 choices = ["3.10" , "3.11" , "3.12" , "3.13" ],
6767 default = f"{ sys .version_info .major } .{ sys .version_info .minor } " ,
68- help = "Hermetic Python version to use" ,
68+ help =
69+ """
70+ Hermetic Python version to use. Default is to use the version of the
71+ Python binary that executed the CLI.
72+ """ ,
6973 )
7074
7175
@@ -74,7 +78,11 @@ def add_cuda_version_argument(parser: argparse.ArgumentParser):
7478 "--cuda_version" ,
7579 type = str ,
7680 default = None ,
77- help = "Hermetic CUDA version to use" ,
81+ help =
82+ """
83+ Hermetic CUDA version to use. Default is to use the version specified
84+ in the .bazelrc.
85+ """ ,
7886 )
7987
8088
@@ -83,7 +91,11 @@ def add_cudnn_version_argument(parser: argparse.ArgumentParser):
8391 "--cudnn_version" ,
8492 type = str ,
8593 default = None ,
86- help = "Hermetic cuDNN version to use" ,
94+ help =
95+ """
96+ Hermetic cuDNN version to use. Default is to use the version specified
97+ in the .bazelrc.
98+ """ ,
8799 )
88100
89101
@@ -100,7 +112,11 @@ def add_cuda_compute_capabilities_argument(parser: argparse.ArgumentParser):
100112 "--cuda_compute_capabilities" ,
101113 type = str ,
102114 default = None ,
103- help = "A comma-separated list of CUDA compute capabilities to support." ,
115+ help =
116+ """
117+ A comma-separated list of CUDA compute capabilities to support. Default
118+ is to use the values specified in the .bazelrc.
119+ """ ,
104120 )
105121
106122
@@ -110,8 +126,8 @@ def add_build_cuda_with_clang_argument(parser: argparse.ArgumentParser):
110126 action = "store_true" ,
111127 help = """
112128 Should CUDA code be compiled using Clang? The default behavior is to
113- compile CUDA with NVCC. Ignored if --use_ci_bazelrc_flags is set, we
114- always build CUDA with NVCC in CI builds.
129+ compile CUDA with NVCC. Ignored if --use_ci_bazelrc_flags is set, CI
130+ builds always build CUDA with NVCC in CI builds.
115131 """ ,
116132 )
117133
@@ -169,21 +185,23 @@ def add_global_arguments(parser: argparse.ArgumentParser):
169185
170186 parser .add_argument (
171187 "--bazel_startup_options" ,
172- type = str ,
173- default = "" ,
188+ action = "append" ,
189+ default = [] ,
174190 help = """
175- Space separated list of additional startup options to pass to Bazel
176- E.g. --bazel_startup_options='--nobatch --noclient_debug'
191+ Additional startup options to pass to Bazel, can be specified multiple
192+ times to pass multiple options.
193+ E.g. --bazel_startup_options='--nobatch'
177194 """ ,
178195 )
179196
180197 parser .add_argument (
181198 "--bazel_build_options" ,
182- type = str ,
183- default = "" ,
199+ action = "append" ,
200+ default = [] ,
184201 help = """
185- Space separated list of additional build options to pass to Bazel
186- E.g. --bazel_build_options='--local_resources=HOST_CPUS --nosandbox_debug'
202+ Additional build options to pass to Bazel, can be specified multiple
203+ times to pass multiple options.
204+ E.g. --bazel_build_options='--local_resources=HOST_CPUS'
187205 """ ,
188206 )
189207
@@ -207,7 +225,8 @@ def add_artifact_subcommand_global_arguments(parser: argparse.ArgumentParser):
207225 action = "store_true" ,
208226 help = """
209227 When set, the CLI will assume the build is being run in CI or CI like
210- environment and will use the "rbe_/ci_" configs in the .bazelrc.
228+ environment and will use the "rbe_/ci_" configs in the .bazelrc. These
229+ configs apply release features and set a custom C++ Clang toolchain.
211230 """ ,
212231 )
213232
@@ -218,9 +237,12 @@ def add_artifact_subcommand_global_arguments(parser: argparse.ArgumentParser):
218237 )
219238
220239 parser .add_argument (
221- "--enable_mkl_dnn " ,
240+ "--disable_mkl_dnn " ,
222241 action = "store_true" ,
223- help = "Enables MKL-DNN." ,
242+ help = """
243+ Disables MKL-DNN. Ignored if --use_ci_bazelrc_flags is set, CI bazelrc
244+ flags enable MKL-DNN as default.
245+ """ ,
224246 )
225247
226248 parser .add_argument (
@@ -230,20 +252,17 @@ def add_artifact_subcommand_global_arguments(parser: argparse.ArgumentParser):
230252 )
231253
232254 parser .add_argument (
233- "--enable_release_cpu_features" ,
234- action = "store_true" ,
235- help = """
236- Enables CPU features that should be enabled for a release build, which
237- on x86-64 architectures enables AVX.
238- """ ,
239- )
240-
241- parser .add_argument (
242- "--enable_native_cpu_features" ,
243- action = "store_true" ,
255+ "--target_cpu_features" ,
256+ choices = ["release" , "native" , "default" ],
257+ default = "release" ,
244258 help = """
245- Enables -march=native, which generates code targeted to use all features
246- of the current machine.
259+ What CPU features should we target? Release enables CPU features that
260+ should be enabled for a release build, which on x86-64 architectures
261+ enables AVX. Native enables -march=native, which generates code targeted
262+ to use all features of the current machine. Default means don't opt-in
263+ to any architectural features and use whatever the C compiler generates
264+ by default. Ignored if --use_ci_bazelrc_flags is set, CI bazelrc flags
265+ enable release CPU features as default.
247266 """ ,
248267 )
249268
@@ -252,8 +271,8 @@ def add_artifact_subcommand_global_arguments(parser: argparse.ArgumentParser):
252271 type = str ,
253272 default = "" ,
254273 help = """
255- Path to the Clang binary to use. Ignored if --use_ci_bazelrc_flags is
256- set as we use a custom Clang toolchain in that case .
274+ Path to the Clang binary to use. Ignored if --use_ci_bazelrc_flags, CI
275+ bazelrc flags set a custom Clang toolchain.
257276 """ ,
258277 )
259278
@@ -270,17 +289,18 @@ def add_artifact_subcommand_global_arguments(parser: argparse.ArgumentParser):
270289 parser .add_argument (
271290 "--output_path" ,
272291 type = str ,
273- default = os .environ .get (
274- "JAXCI_OUTPUT_DIR" , os .path .join (os .getcwd (), "dist" )
275- ),
292+ default = os .path .join (os .getcwd (), "dist" ),
276293 help = "Directory to which the JAX wheel packages should be written." ,
277294 )
278295
279-
280- def parse_and_append_bazel_options (bazel_command : command .CommandBuilder , bazel_options : str ):
281- """Parses the bazel options and appends them to the bazel command."""
282- for option in bazel_options .split (" " ):
283- bazel_command .append (option )
296+ parser .add_argument (
297+ "--configure_only" ,
298+ action = "store_true" ,
299+ help = """
300+ If true, writes the Bazel options to the .jax_configure.bazelrc file but
301+ does not build the artifacts. Ignored if --use_ci_bazelrc_flags is set.
302+ """ ,
303+ )
284304
285305
286306async def main ():
@@ -394,7 +414,8 @@ async def main():
394414 logging .debug (
395415 "Additional Bazel startup options: %s" , args .bazel_startup_options
396416 )
397- parse_and_append_bazel_options (bazel_command , args .bazel_startup_options )
417+ for option in args .bazel_startup_options :
418+ bazel_command .append (option )
398419
399420 bazel_command .append ("run" )
400421
@@ -409,7 +430,8 @@ async def main():
409430 logging .debug (
410431 "Using additional build options: %s" , args .bazel_build_options
411432 )
412- parse_and_append_bazel_options (bazel_command , args .bazel_build_options )
433+ for option in args .bazel_build_options :
434+ bazel_command .append (option )
413435
414436 if args .nightly_update :
415437 logging .debug (
@@ -445,15 +467,20 @@ async def main():
445467 else :
446468 clang_path = args .clang_path or utils .get_clang_path_or_exit ()
447469 logging .debug ("Using Clang as the compiler, clang path: %s" , clang_path )
448- bazel_command .append (f"--action_env CLANG_COMPILER_PATH={ clang_path } " )
449- bazel_command .append (f"--repo_env CC={ clang_path } " )
450- bazel_command .append (f"--repo_env BAZEL_COMPILER={ clang_path } " )
470+ # Use double quotes around clang path to avoid path issues on Windows.
471+ bazel_command .append (f'--action_env=CLANG_COMPILER_PATH="{ clang_path } "' )
472+ bazel_command .append (f'--repo_env=CC="{ clang_path } "' )
473+ bazel_command .append (f'--repo_env=BAZEL_COMPILER="{ clang_path } "' )
451474 bazel_command .append ("--config=clang" )
452475
476+ if not args .disable_mkl_dnn :
477+ logging .debug ("Enabling MKL DNN" )
478+ bazel_command .append ("--config=mkl_open_source_only" )
479+
453480 if "cuda" in args .command :
454481 bazel_command .append ("--config=cuda" )
455482 bazel_command .append (
456- f" --action_env=CLANG_CUDA_COMPILER_PATH={ clang_path } "
483+ f' --action_env=CLANG_CUDA_COMPILER_PATH=" { clang_path } "'
457484 )
458485 if args .build_cuda_with_clang :
459486 logging .debug ("Building CUDA with Clang" )
@@ -462,40 +489,37 @@ async def main():
462489 logging .debug ("Building CUDA with NVCC" )
463490 bazel_command .append ("--config=build_cuda_with_nvcc" )
464491
492+ if args .target_cpu_features == "release" :
493+ logging .debug (
494+ "Using release cpu features: --config=avx_%s" ,
495+ "windows" if os_name == "windows" else "posix" ,
496+ )
497+ if arch in ["x86_64" , "AMD64" ]:
498+ bazel_command .append (
499+ "--config=avx_windows"
500+ if os_name == "windows"
501+ else "--config=avx_posix"
502+ )
503+ elif args .target_cpu_features == "native" :
504+ if os_name == "windows" :
505+ logger .warning (
506+ "--target_cpu_features=native is not supported on Windows;"
507+ " ignoring."
508+ )
509+ else :
510+ logging .debug ("Using native cpu features: --config=native_arch_posix" )
511+ bazel_command .append ("--config=native_arch_posix" )
512+ else :
513+ logging .debug ("Using default cpu features" )
514+
465515 if args .target_cpu :
466516 logging .debug ("Target CPU: %s" , args .target_cpu )
467517 bazel_command .append (f"--cpu={ args .target_cpu } " )
468518
469- if args .enable_mkl_dnn :
470- logging .debug ("Enabling MKL DNN" )
471- bazel_command .append ("--config=mkl_open_source_only" )
472-
473519 if hasattr (args , "disable_nccl" ) and args .disable_nccl :
474520 logging .debug ("Disabling NCCL" )
475521 bazel_command .append ("--config=nonccl" )
476522
477- if args .enable_release_cpu_features :
478- logging .debug (
479- "Using release cpu features: --config=avx_%s" ,
480- "windows" if os_name == "windows" else "posix" ,
481- )
482- if arch in ["x86_64" , "AMD64" ]:
483- bazel_command .append (
484- "--config=avx_windows"
485- if os_name == "windows"
486- else "--config=avx_posix"
487- )
488-
489- if args .enable_native_cpu_features :
490- if os_name == "windows" :
491- logger .warning (
492- "--target_cpu_features=native is not supported on Windows;"
493- " ignoring."
494- )
495- else :
496- logging .debug ("Using native cpu features: --config=native_arch_posix" )
497- bazel_command .append ("--config=native_arch_posix" )
498-
499523 if "cuda" in args .command :
500524 if args .cuda_version :
501525 logging .debug ("Hermetic CUDA version: %s" , args .cuda_version )
@@ -513,54 +537,56 @@ async def main():
513537 args .cuda_compute_capabilities ,
514538 )
515539 bazel_command .append (
516- "--repo_env"
517- f" HERMETIC_CUDA_COMPUTE_CAPABILITIES={ args .cuda_compute_capabilities } "
540+ f"--repo_env=HERMETIC_CUDA_COMPUTE_CAPABILITIES={ args .cuda_compute_capabilities } "
518541 )
519542
520543 if "rocm" in args .command :
521544 bazel_command .append ("--config=rocm" )
522545
523546 if args .rocm_path :
524547 logging .debug ("ROCm tookit path: %s" , args .rocm_path )
525- bazel_command .append (f" --action_env ROCM_PATH=' { args .rocm_path } '" )
548+ bazel_command .append (f' --action_env= ROCM_PATH=" { args .rocm_path } "' )
526549 if args .rocm_amdgpu_targets :
527550 logging .debug ("ROCm AMD GPU targets: %s" , args .rocm_amdgpu_targets )
528551 bazel_command .append (
529- f"--action_env TF_ROCM_AMDGPU_TARGETS={ args .rocm_amdgpu_targets } "
552+ f"--action_env= TF_ROCM_AMDGPU_TARGETS={ args .rocm_amdgpu_targets } "
530553 )
531554
532555 if args .local_xla_path :
533556 logging .debug ("Local XLA path: %s" , args .local_xla_path )
534- bazel_command .append (f" --override_repository=xla={ args .local_xla_path } " )
557+ bazel_command .append (f' --override_repository=xla=" { args .local_xla_path } "' )
535558
536559 if args .bazel_build_options :
537560 logging .debug (
538561 "Additional Bazel build options: %s" , args .bazel_build_options
539562 )
540- parse_and_append_bazel_options (bazel_command , args .bazel_build_options )
563+ for option in args .bazel_build_options :
564+ bazel_command .append (option )
565+
566+ if not args .use_ci_bazelrc_flags :
567+ with open (".jax_configure.bazelrc" , "w" ) as f :
568+ jax_configure_options = utils .get_jax_configure_bazel_options (bazel_command .command )
569+ f .write (jax_configure_options )
570+ logging .debug ("Bazel options written to .jax_configure.bazelrc" )
571+ if args .configure_only :
572+ logging .debug ("--configure_only is set, exiting without running any Bazel commands." )
573+ sys .exit (0 )
541574
542575 # Append the build target to the Bazel command.
543576 build_target = ARTIFACT_BUILD_TARGET_DICT [args .command ]
544577 bazel_command .append (build_target )
545578
546- # Read output directory. Default is store the artifacts in the "dist/"
547- # directory in JAX's GitHub repository root.
548- output_path = args .output_path
549-
550- # If running on Windows, adjust the paths for compatibility.
551- if os_name == "windows" :
552- output_path = utils .adjust_paths_for_windows (output_path )
579+ bazel_command .append ("--" )
553580
581+ output_path = args .output_path
554582 logger .debug ("Artifacts output directory: %s" , output_path )
555583
556- bazel_command .append ("--" )
557-
558584 if args .editable :
559585 logger .debug ("Building an editable build" )
560586 output_path = os .path .join (output_path , args .command )
561587 bazel_command .append ("--editable" )
562588
563- bazel_command .append (f" --output_path={ output_path } " )
589+ bazel_command .append (f' --output_path=" { output_path } "' )
564590 bazel_command .append (f"--cpu={ target_cpu } " )
565591
566592 if "cuda" in args .command :
0 commit comments