Bug 1434943 - Support for MSVC in build.sh, r=jcj
☠☠ backed out by 1252064f09dc ☠ ☠
authorMartin Thomson <martin.thomson@gmail.com>
Fri, 01 Jun 2018 17:25:21 +1000
changeset 14496 8bea05067a0ba403f4066860ae8a59d4410e2e19
parent 14495 a74229a54349be704bdede56b6f567e0988b9653
child 14497 1252064f09dc772057e67b1852b84fd48783e65a
push id3196
push usermartin.thomson@gmail.com
push dateSun, 23 Sep 2018 19:25:41 +0000
reviewersjcj
bugs1434943
Bug 1434943 - Support for MSVC in build.sh, r=jcj This adds basic support for MSVC to build.sh. It uses the registry and vswhere (which is part of the standard mozilla-build setup now) to work out paths and set them properly. It's probably a little fragile, but it's better than the shoestring and tape we have in builds right now. I took the liberty of sanitizing the command-line options a little here. Mostly that is sorting them, but I also deprecated the -m32 option in favour of specifying target architecture with -t. That turned out to be a lot cleaner.
automation/taskcluster/graph/src/extend.js
build.sh
coreconf/fuzz.sh
coreconf/msvc.sh
coreconf/nspr.sh
help.txt
--- a/automation/taskcluster/graph/src/extend.js
+++ b/automation/taskcluster/graph/src/extend.js
@@ -147,23 +147,23 @@ queue.map(task => {
 });
 
 /*****************************************************************************/
 
 export default async function main() {
   await scheduleLinux("Linux 32 (opt)", {
     platform: "linux32",
     image: LINUX_IMAGE
-  }, "-m32 --opt");
+  }, "-t ia32 --opt");
 
   await scheduleLinux("Linux 32 (debug)", {
     platform: "linux32",
     collection: "debug",
     image: LINUX_IMAGE
-  }, "-m32");
+  }, "-t ia32");
 
   await scheduleLinux("Linux 64 (opt)", {
     platform: "linux64",
     image: LINUX_IMAGE
   }, "--opt");
 
   await scheduleLinux("Linux 64 (debug)", {
     platform: "linux64",
@@ -243,22 +243,22 @@ export default async function main() {
 
   await scheduleWindows("Windows 2012 64 (debug)", {
     platform: "windows2012-64",
     collection: "debug"
   }, "build_gyp.sh");
 
   await scheduleWindows("Windows 2012 32 (opt)", {
     platform: "windows2012-32",
-  }, "build_gyp.sh --opt -m32");
+  }, "build_gyp.sh --opt -t ia32");
 
   await scheduleWindows("Windows 2012 32 (debug)", {
     platform: "windows2012-32",
     collection: "debug"
-  }, "build_gyp.sh -m32");
+  }, "build_gyp.sh -t ia32");
 
   await scheduleFuzzing();
   await scheduleFuzzing32();
 
   await scheduleTools();
 
   let aarch64_base = {
     image: "franziskus/nss-aarch64-ci",
@@ -674,17 +674,17 @@ async function scheduleFuzzing32() {
   };
 
   // Build base definition.
   let build_base = merge(base, {
     command: [
       "/bin/bash",
       "-c",
       "bin/checkout.sh && " +
-      "nss/automation/taskcluster/scripts/build_gyp.sh -g -v --fuzz -m32"
+      "nss/automation/taskcluster/scripts/build_gyp.sh -g -v --fuzz -t ia32"
     ],
     artifacts: {
       public: {
         expires: 24 * 7,
         type: "directory",
         path: "/home/worker/artifacts"
       }
     },
@@ -701,17 +701,17 @@ async function scheduleFuzzing32() {
   let task_build_tls = queue.scheduleTask(merge(build_base, {
     name: "Linux 32 (debug, TLS fuzz)",
     symbol: "B",
     group: "TLS",
     command: [
       "/bin/bash",
       "-c",
       "bin/checkout.sh && " +
-      "nss/automation/taskcluster/scripts/build_gyp.sh -g -v --fuzz=tls -m32"
+      "nss/automation/taskcluster/scripts/build_gyp.sh -g -v --fuzz=tls -t ia32"
     ],
   }));
 
   // Schedule tests.
   queue.scheduleTask(merge(base, {
     parent: task_build_tls,
     name: "Gtests",
     command: [
@@ -1097,17 +1097,17 @@ async function scheduleTools() {
         expires: 24 * 7,
         type: "directory",
         path: "/home/worker/artifacts"
       }
     },
     command: [
       "/bin/bash",
       "-c",
-      "bin/checkout.sh && nss/automation/taskcluster/scripts/build_gyp.sh --disable-tests --emit-llvm -m32"
+      "bin/checkout.sh && nss/automation/taskcluster/scripts/build_gyp.sh --disable-tests --emit-llvm -t ia32"
     ]
   }));
 
   queue.scheduleTask(merge(base, {
     parent: task_saw,
     symbol: "bmul",
     group: "SAW",
     name: "bmul.saw",
--- a/build.sh
+++ b/build.sh
@@ -45,85 +45,95 @@ clean=0
 rebuild_gyp=0
 rebuild_nspr=0
 target=Debug
 verbose=0
 fuzz=0
 fuzz_tls=0
 fuzz_oss=0
 no_local_nspr=0
-armhf=0
 
 gyp_params=(--depth="$cwd" --generator-output=".")
-nspr_params=()
 ninja_params=()
 
-# try to guess sensible defaults
-arch=$(python "$cwd"/coreconf/detect_host_arch.py)
-if [ "$arch" = "x64" -o "$arch" = "aarch64" ]; then
-    build_64=1
-elif [ "$arch" = "arm" ]; then
-    armhf=1
+# Assume that the target architecture is the same as the host by default.
+host_arch=$(python "$cwd"/coreconf/detect_host_arch.py)
+target_arch=$host_arch
+
+# Assume that MSVC is wanted if this is running on windows.
+platform=$(uname -s)
+if [ "${platform%-*}" = "MINGW32_NT" -o "${platform%-*}" = "MINGW64_NT" ]; then
+    msvc=1
 fi
 
-# parse command line arguments
+# Parse command line arguments.
 while [ $# -gt 0 ]; do
-    case $1 in
+    case "$1" in
         -c) clean=1 ;;
         -cc) clean_only=1 ;;
-        --gyp|-g) rebuild_gyp=1 ;;
-        --nspr) nspr_clean; rebuild_nspr=1 ;;
+        -v) ninja_params+=(-v); verbose=1 ;;
         -j) ninja_params+=(-j "$2"); shift ;;
-        -v) ninja_params+=(-v); verbose=1 ;;
-        --test) gyp_params+=(-Dtest_build=1) ;;
-        --clang) export CC=clang; export CCC=clang++; export CXX=clang++ ;;
-        --gcc) export CC=gcc; export CCC=g++; export CXX=g++ ;;
-        --fuzz) fuzz=1 ;;
-        --fuzz=oss) fuzz=1; fuzz_oss=1 ;;
-        --fuzz=tls) fuzz=1; fuzz_tls=1 ;;
+        --gyp|-g) rebuild_gyp=1 ;;
+        --opt|-o) opt_build=1 ;;
+        -m32|--m32) target_arch=ia32; echo 'Warning: use -t instead of -m32' 1>&2 ;;
+        -t|--target) target_arch="$2"; shift ;;
+        --target=*) target_arch="${1#*=}" ;;
+        --clang) export CC=clang; export CCC=clang++; export CXX=clang++; msvc=0 ;;
+        --gcc) export CC=gcc; export CCC=g++; export CXX=g++; msvc=0 ;;
+        --msvc) msvc=1 ;;
         --scan-build) enable_scanbuild  ;;
         --scan-build=?*) enable_scanbuild "${1#*=}" ;;
-        --opt|-o) opt_build=1 ;;
-        -m32|--m32) build_64=0 ;;
+        --disable-tests) gyp_params+=(-Ddisable_tests=1) ;;
+        --pprof) gyp_params+=(-Duse_pprof=1) ;;
         --asan) enable_sanitizer asan ;;
         --msan) enable_sanitizer msan ;;
         --ubsan) enable_ubsan ;;
         --ubsan=?*) enable_ubsan "${1#*=}" ;;
+        --fuzz) fuzz=1 ;;
+        --fuzz=oss) fuzz=1; fuzz_oss=1 ;;
+        --fuzz=tls) fuzz=1; fuzz_tls=1 ;;
         --sancov) enable_sancov ;;
         --sancov=?*) enable_sancov "${1#*=}" ;;
-        --pprof) gyp_params+=(-Duse_pprof=1) ;;
+        --emit-llvm) gyp_params+=(-Demit_llvm=1 -Dsign_libs=0) ;;
+        --no-zdefs) gyp_params+=(-Dno_zdefs=1) ;;
+        --test) gyp_params+=(-Dtest_build=1) ;;
         --ct-verif) gyp_params+=(-Dct_verif=1) ;;
-        --emit-llvm) gyp_params+=(-Demit_llvm=1 -Dsign_libs=0) ;;
-        --disable-tests) gyp_params+=(-Ddisable_tests=1) ;;
-        --no-zdefs) gyp_params+=(-Dno_zdefs=1) ;;
-        --system-sqlite) gyp_params+=(-Duse_system_sqlite=1) ;;
+        --nspr) nspr_clean; rebuild_nspr=1 ;;
         --with-nspr=?*) set_nspr_path "${1#*=}"; no_local_nspr=1 ;;
         --system-nspr) set_nspr_path "/usr/include/nspr/:"; no_local_nspr=1 ;;
+        --system-sqlite) gyp_params+=(-Duse_system_sqlite=1) ;;
+        --enable-fips) gyp_params+=(-Ddisable_fips=0) ;;
         --enable-libpkix) gyp_params+=(-Ddisable_libpkix=0) ;;
-        --enable-fips) gyp_params+=(-Ddisable_fips=0) ;;
         *) show_help; exit 2 ;;
     esac
     shift
 done
 
+# Set the target architecture and build type.
+gyp_params+=(-Dtarget_arch="$target_arch")
 if [ "$opt_build" = 1 ]; then
     target=Release
 else
     target=Debug
 fi
-if [ "$build_64" = 1 ]; then
-    nspr_params+=(--enable-64bit)
-elif [ ! "$armhf" = 1 ]; then
-    gyp_params+=(-Dtarget_arch=ia32)
-fi
+
+# Do special setup.
 if [ "$fuzz" = 1 ]; then
     source "$cwd"/coreconf/fuzz.sh
 fi
+nspr_set_flags $sanitizer_flags
+if [ ! -z "$sanitizer_flags" ]; then
+    gyp_params+=(-Dsanitizer_flags="$sanitizer_flags")
+fi
 
-# set paths
+if [ "$msvc" = 1 ]; then
+    source "$cwd"/coreconf/msvc.sh
+fi
+
+# Setup build paths.
 target_dir="$cwd"/out/$target
 mkdir -p "$target_dir"
 dist_dir="$cwd"/../dist
 dist_dir=$(mkdir -p "$dist_dir"; cd "$dist_dir"; pwd -P)
 gyp_params+=(-Dnss_dist_dir="$dist_dir")
 
 # -c = clean first
 if [ "$clean" = 1 -o "$clean_only" = 1 ]; then
@@ -144,61 +154,58 @@ fi
 check_config()
 {
     local newconf="$1".new oldconf="$1"
     shift
     mkdir -p $(dirname "$newconf")
     echo CC="$CC" >"$newconf"
     echo CCC="$CCC" >>"$newconf"
     echo CXX="$CXX" >>"$newconf"
+    echo target_arch="$target_arch" >>"$newconf"
     for i in "$@"; do echo $i; done | sort >>"$newconf"
 
     # Note: The following diff fails if $oldconf isn't there as well, which
     # happens if we don't have a previous successful build.
     ! diff -q "$newconf" "$oldconf" >/dev/null 2>&1
 }
 
 gyp_config="$cwd"/out/gyp_config
 nspr_config="$cwd"/out/$target/nspr_config
 
+# Now check what needs to be rebuilt.
 # If we don't have a build directory make sure that we rebuild.
 if [ ! -d "$target_dir" ]; then
     rebuild_nspr=1
     rebuild_gyp=1
 elif [ ! -d "$dist_dir"/$target ]; then
     rebuild_nspr=1
 fi
 
-# Update NSPR ${C,CXX,LD}FLAGS.
-nspr_set_flags $sanitizer_flags
-
-if check_config "$nspr_config" "${nspr_params[@]}" \
+if check_config "$nspr_config" \
                  nspr_cflags="$nspr_cflags" \
                  nspr_cxxflags="$nspr_cxxflags" \
                  nspr_ldflags="$nspr_ldflags"; then
     rebuild_nspr=1
 fi
 
-# Forward sanitizer flags.
-if [ ! -z "$sanitizer_flags" ]; then
-    gyp_params+=(-Dsanitizer_flags="$sanitizer_flags")
-fi
-
 if check_config "$gyp_config" "${gyp_params[@]}"; then
     rebuild_gyp=1
 fi
 
-# save the chosen target
+# Save the chosen target.
 mkdir -p "$dist_dir"
 echo $target > "$dist_dir"/latest
 
+# Build.
+# NSPR.
 if [[ "$rebuild_nspr" = 1 && "$no_local_nspr" = 0 ]]; then
-    nspr_build "${nspr_params[@]}"
+    nspr_build
     mv -f "$nspr_config".new "$nspr_config"
 fi
+# gyp.
 if [ "$rebuild_gyp" = 1 ]; then
     if ! hash ${GYP} 2> /dev/null; then
         echo "Please install gyp" 1>&2
         exit 1
     fi
     # These extra arguments aren't used in determining whether to rebuild.
     obj_dir="$dist_dir"/$target
     gyp_params+=(-Dnss_dist_obj_dir=$obj_dir)
@@ -206,18 +213,18 @@ if [ "$rebuild_gyp" = 1 ]; then
         set_nspr_path "$obj_dir/include/nspr:$obj_dir/lib"
     fi
 
     run_verbose run_scanbuild ${GYP} -f ninja "${gyp_params[@]}" "$cwd"/nss.gyp
 
     mv -f "$gyp_config".new "$gyp_config"
 fi
 
-# Run ninja.
-if hash ninja 2>/dev/null; then
+# ninja.
+if hash ninja-build 2>/dev/null; then
+    ninja=ninja-build
+elif hash ninja 2>/dev/null; then
     ninja=ninja
-elif hash ninja-build 2>/dev/null; then
-    ninja=ninja-build
 else
     echo "Please install ninja" 1>&2
     exit 1
 fi
 run_scanbuild $ninja -C "$target_dir" "${ninja_params[@]}"
--- a/coreconf/fuzz.sh
+++ b/coreconf/fuzz.sh
@@ -1,17 +1,16 @@
 #!/usr/bin/env bash
 # This file is used by build.sh to setup fuzzing.
 
 set +e
 
 # Default to clang if CC is not set.
 if [ -z "$CC" ]; then
-    command -v clang &> /dev/null 2>&1
-    if [ $? != 0 ]; then
+    if ! command -v clang &> /dev/null 2>&1; then
         echo "Fuzzing requires clang!"
         exit 1
     fi
     export CC=clang
     export CCC=clang++
     export CXX=clang++
 fi
 
@@ -19,18 +18,18 @@ gyp_params+=(-Dtest_build=1 -Dfuzz=1 -Ds
 
 # Add debug symbols even for opt builds.
 nspr_params+=(--enable-debug-symbols)
 
 if [ "$fuzz_oss" = 1 ]; then
   gyp_params+=(-Dno_zdefs=1 -Dfuzz_oss=1)
 else
   enable_sanitizer asan
-  # Ubsan doesn't build on 32-bit at the moment. Disable it.
-  if [ "$build_64" = 1 ]; then
+  # Ubsan only builds on x64 for the moment.
+  if [ "$target_arch" = "x64" ]; then
     enable_ubsan
   fi
   enable_sancov
 fi
 
 if [ "$fuzz_tls" = 1 ]; then
   gyp_params+=(-Dfuzz_tls=1)
 fi
new file mode 100644
--- /dev/null
+++ b/coreconf/msvc.sh
@@ -0,0 +1,98 @@
+#!/bin/bash
+# This configures the environment for running MSVC.  It uses vswhere, the
+# registry, and a little knowledge of how MSVC is laid out.
+
+if ! hash vswhere 2>/dev/null; then
+    echo "Can't find vswhere on the path, aborting" 1>&2
+    exit 1
+fi
+
+if ! hash reg 2>/dev/null; then
+    echo "Can't find reg on the path, aborting" 1>&2
+    exit 1
+fi
+
+# Turn a unix-y path into a windows one.
+fixpath() {
+    if hash cygpath 2>/dev/null; then
+        cygpath --unix "$1"
+    else # haxx
+        echo "$1" | sed -e 's,\\,/,g;s,^\(.\):,/\L\1,;s,/$,,'
+    fi
+}
+
+# Query the registry.  This takes $1 and tags that on the end of several
+# different paths, looking for a value called $2 at that location.
+# e.g.,
+#   regquery Microsoft\Microsoft SDKs\Windows\v10.0 ProductVersion
+# looks for a REG_SZ value called ProductVersion at
+#   HKLM\SOFTWARE\Wow6432Node\Microsoft\Microsoft SDKs\Windows\v10.0
+#   HKLU\SOFTWARE\Wow6432Node\Microsoft\Microsoft SDKs\Windows\v10.0
+#   etc...
+regquery() {
+    search=("HKLM\\SOFTWARE\\Wow6432Node" \
+            "HKCU\\SOFTWARE\\Wow6432Node" \
+            "HKLM\\SOFTWARE" \
+            "HKCU\\SOFTWARE")
+    for i in "${search[@]}"; do
+        r=$(reg query "${i}\\${1}" -v "$2" | sed -e 's/ *'"$2"' *REG_SZ *//;t;d')
+        if [ -n "$r" ]; then
+            echo "$r"
+            return 0
+        fi
+    done
+    return 1
+}
+
+case "$target_arch" in
+    ia32) m=x86 ;;
+    x64) m="$target_arch" ;;
+    *)
+        echo "No support for target architecture '$target_arch' with MSVC." 1>&2
+        exit 1
+esac
+
+VSCOMPONENT=Microsoft.VisualStudio.Component.VC.Tools.x86.x64
+VSPATH=$(vswhere -latest -requires "$VSCOMPONENT" -property installationPath)
+export VSPATH=$(fixpath "$VSPATH")
+export WINDOWSSDKDIR="${VSPATH}/SDK"
+export VCINSTALLDIR="${VSPATH}/VC"
+
+CRTREG="Microsoft\\Microsoft SDKs\\Windows\\v10.0"
+UniversalCRTSdkDir=$(regquery "$CRTREG" InstallationFolder)
+UniversalCRTSdkDir=$(fixpath "$UniversalCRTSdkDir")
+UCRTVersion=$(regquery "$CRTREG" ProductVersion)
+UCRTVersion=$(cd "${UniversalCRTSdkDir}/include"; ls -d "${UCRTVersion}"* | tail -1)
+
+VCVER=$(cat "${VCINSTALLDIR}/Auxiliary/Build/Microsoft.VCToolsVersion.default.txt")
+REDISTVER=$(cat "${VCINSTALLDIR}/Auxiliary/Build/Microsoft.VCRedistVersion.default.txt")
+export WIN32_REDIST_DIR="${VCINSTALLDIR}/Redist/MSVC/${REDISTVER}/${m}/Microsoft.VC141.CRT"
+export WIN_UCRT_REDIST_DIR="${UniversalCRTSdkDir}/Redist/ucrt/DLLs/${m}"
+
+if [ "$m" == "x86" ]; then
+    PATH="${PATH}:${VCINSTALLDIR}/Tools/MSVC/${VCVER}/bin/HostX64/x86"
+    PATH="${PATH}:${VCINSTALLDIR}/Tools/MSVC/${VCVER}/bin/Hostx86/x86"
+fi
+PATH="${PATH}:${VCINSTALLDIR}/Tools/MSVC/${VCVER}/bin/HostX64/x64"
+PATH="${PATH}:${UniversalCRTSdkDir}/bin/${UCRTVersion}/x64"
+PATH="${PATH}:${UniversalCRTSdkDir}/bin/${UCRTVersion}/x86"
+PATH="${PATH}:${WIN32_REDIST_DIR}"
+export PATH
+
+INCLUDE="${VCINSTALLDIR}/Tools/MSVC/${VCVER}/ATLMFC/include"
+INCLUDE="${INCLUDE}:${VCINSTALLDIR}/Tools/MSVC/${VCVER}/include"
+INCLUDE="${INCLUDE}:${UniversalCRTSdkDir}/include/${UCRTVersion}/ucrt"
+INCLUDE="${INCLUDE}:${UniversalCRTSdkDir}/include/${UCRTVersion}/shared"
+INCLUDE="${INCLUDE}:${UniversalCRTSdkDir}/include/${UCRTVersion}/um"
+INCLUDE="${INCLUDE}:${UniversalCRTSdkDir}/include/${UCRTVersion}/winrt"
+INCLUDE="${INCLUDE}:${UniversalCRTSdkDir}/include/${UCRTVersion}/cppwinrt"
+export INCLUDE
+
+LIB="${VCINSTALLDIR}/lib/${m}"
+LIB="${VCINSTALLDIR}/Tools/MSVC/${VCVER}/lib/${m}"
+LIB="${LIB}:${UniversalCRTSdkDir}/lib/${UCRTVersion}/ucrt/${m}"
+LIB="${LIB}:${UniversalCRTSdkDir}/lib/${UCRTVersion}/um/${m}"
+export LIB
+
+export GYP_MSVS_OVERRIDE_PATH="${VSPATH}"
+export GYP_MSVS_VERSION=$(vswhere -latest -requires "$VSCOMPONENT" -property catalog_productLineVersion)
--- a/coreconf/nspr.sh
+++ b/coreconf/nspr.sh
@@ -27,16 +27,19 @@ nspr_build()
     mkdir -p "$nspr_dir"
 
     # These NSPR options are directory-specific, so they don't need to be
     # included in nspr_opt and changing them doesn't force a rebuild of NSPR.
     extra_params=(--prefix="$dist_dir"/$target)
     if [ "$opt_build" = 1 ]; then
         extra_params+=(--disable-debug --enable-optimize)
     fi
+    if [ "$target_arch" = "x64" ]; then
+        extra_params+=(--enable-64bit)
+    fi
 
     echo "NSPR [1/3] configure ..."
     pushd "$nspr_dir" >/dev/null
     CFLAGS="$nspr_cflags" CXXFLAGS="$nspr_cxxflags" \
           LDFLAGS="$nspr_ldflags" CC="$CC" CXX="$CCC" \
           run_verbose ../configure "${extra_params[@]}" "$@"
     popd >/dev/null
     echo "NSPR [2/3] make ..."
--- a/help.txt
+++ b/help.txt
@@ -1,50 +1,50 @@
-Usage: build.sh [-hcv] [-cc] [-j <n>] [--nspr] [--gyp|-g] [--opt|-o] [-m32]
-                [--test] [--pprof] [--scan-build[=output]] [--ct-verif]
-                [--asan] [--ubsan] [--msan] [--sancov[=edge|bb|func|...]]
-                [--disable-tests] [--fuzz[=tls|oss]] [--system-sqlite]
-                [--no-zdefs] [--with-nspr] [--system-nspr] [--enable-libpkix]
-                [--enable-fips]
+Usage: build.sh [-h] [-c|-cc] [-v] [-j <n>] [--gyp|-g] [--opt|-o]
+                [-t <x64|x86|...>|--target=<x64|x86|...>]
+                [--clang|--gcc|--msvc] [--scan-build[=dir]] [--disable-tests]
+                [--pprof] [--asan] [--msan] [--ubsan[=bool,shift,...]
+                [--fuzz[=tls|oss]] [--sancov[=edge|bb|func|...]]
+                [--emit-llvm] [--no-zdefs] [--test] [--ct-verif]
+                [--nspr|--with-nspr=<include>:<lib>|--system-nspr]
+                [--system-sqlite] [--enable-fips] [--enable-libpkix]
 
 This script builds NSS with gyp and ninja.
 
-This build system is still under development.  It does not yet support all
-the features or platforms that NSS supports.
-
 NSS build tool options:
 
     -h               display this help and exit
     -c               clean before build
     -cc              clean without building
     -v               verbose build
     -j <n>           run at most <n> concurrent jobs
-    --nspr           force a rebuild of NSPR
     --gyp|-g         force a rerun of gyp
     --opt|-o         do an opt build
-    -m32             do a 32-bit build on a 64-bit system
+    --target|-t      specify target architecture (e.g., x86, x64, aarch64)
     --clang          build with clang and clang++
     --gcc            build with gcc and g++
-    --test           ignore map files and export everything we have
+    --msvc           build with MSVC
+    --scan-build     run the build with scan-build
+                     --scan-build=<dir> sets the output path for scan-build
+    --disable-tests  don't build tests and corresponding cmdline utils
+    --pprof          build with gperftool support
+    --asan           enable address sanitizer
+    --msan           enable memory sanitizer
+    --ubsan          enable undefined behavior sanitizer
+                     --ubsan=bool,shift,... sets specific UB sanitizers
     --fuzz           build fuzzing targets (this always enables test builds)
                      --fuzz=tls to enable TLS fuzzing mode
                      --fuzz=oss to build for OSS-Fuzz
-    --pprof          build with gperftool support
-    --ct-verif       build with valgrind for ct-verif
-    --scan-build     run the build with scan-build (scan-build has to be in the path)
-                     --scan-build=/out/path sets the output path for scan-build
-    --asan           do an asan build
-    --ubsan          do an ubsan build
-                     --ubsan=bool,shift,... sets specific UB sanitizers
-    --msan           do an msan build
     --sancov         do sanitize coverage builds
                      --sancov=func sets coverage to function level for example
     --emit-llvm      emit LLVM bitcode while building
                      (requires the gold linker, use clang-3.8 for SAW)
-    --disable-tests  don't build tests and corresponding cmdline utils
+    --no-zdefs       don't set -Wl,-z,defs
+    --test           ignore map files and export everything we have
+    --ct-verif       build with valgrind for ct-verif
+    --nspr           force a rebuild of NSPR
+    --with-nspr      use the NSPR build at the given locations
+                     --with-nspr=<include>:<lib> sets include and lib paths
+    --system-nspr    attempt to use system nspr
+                     shorthand for --with-nspr=/usr/include/nspr:
     --system-sqlite  use system sqlite
-    --no-zdefs       don't set -Wl,-z,defs
-    --with-nspr      don't build NSPR but use the one at the given location, e.g.
-                     --with-nspr=/path/to/nspr/include:/path/to/nspr/lib
-    --system-nspr    use system nspr. This requires an installation of NSPR and
-                     might not work on all systems.
-    --enable-libpkix make libpkix part of the build.
-    --enable-fips    don't disable FIPS checks.
+    --enable-fips    enable FIPS checks
+    --enable-libpkix make libpkix part of the build