From b16284636d3a52b503e8942f3d0c267291aa3f9e Mon Sep 17 00:00:00 2001 From: Vitali Sepetnitsky Date: Thu, 19 Jun 2025 01:59:22 +0300 Subject: [PATCH] FIPS --- cpython-unix/build-cpython.sh | 6 ++++-- cpython-unix/build-openssl-3.0.sh | 4 +++- cpython-unix/build.py | 34 +++++++++++++++---------------- pythonbuild/buildenv.py | 4 ++-- pythonbuild/cpython.py | 14 ++++++++----- pythonbuild/downloads.py | 8 ++++---- 6 files changed, 39 insertions(+), 31 deletions(-) diff --git a/cpython-unix/build-cpython.sh b/cpython-unix/build-cpython.sh index 2296f2bfd..c6e858e34 100755 --- a/cpython-unix/build-cpython.sh +++ b/cpython-unix/build-cpython.sh @@ -44,7 +44,9 @@ sed "${sed_args[@]}" "s|/tools/host|${TOOLS_PATH}/host|g" ${TOOLS_PATH}/host/sha # We force linking of external static libraries by removing the shared # libraries. This is hacky. But we're building in a temporary container # and it gets the job done. -find ${TOOLS_PATH}/deps -name '*.so*' -exec rm {} \; +# FIPS: In order to build FIPS compatible Python, we don't want to +# remove the shared libraries libssl and libcrypto +find ${TOOLS_PATH}/deps -name '*.so*' ! -name 'libssl.*' ! -name 'libcrypto.*' -exec rm {} \; tar -xf Python-${PYTHON_VERSION}.tar.xz @@ -389,7 +391,7 @@ CONFIGURE_FLAGS=" --build=${BUILD_TRIPLE} --host=${TARGET_TRIPLE} --prefix=/install - --with-openssl=${TOOLS_PATH}/deps + --with-builtin-hashlib-hashes=sha256,sha512 --with-system-expat --with-system-libmpdec --without-ensurepip diff --git a/cpython-unix/build-openssl-3.0.sh b/cpython-unix/build-openssl-3.0.sh index 1d1f91348..1006e5984 100755 --- a/cpython-unix/build-openssl-3.0.sh +++ b/cpython-unix/build-openssl-3.0.sh @@ -37,12 +37,14 @@ EXTRA_TARGET_CFLAGS=${EXTRA_TARGET_CFLAGS/\-arch x86_64/} EXTRA_FLAGS="${EXTRA_FLAGS} ${EXTRA_TARGET_CFLAGS}" +# FIPS: Notice the 'fips' and 'shared' flags /usr/bin/perl ./Configure \ + fips \ --prefix=/tools/deps \ --libdir=lib \ ${OPENSSL_TARGET} \ no-legacy \ - no-shared \ + shared \ no-tests \ ${EXTRA_FLAGS} diff --git a/cpython-unix/build.py b/cpython-unix/build.py index 6f98e990f..45812603d 100755 --- a/cpython-unix/build.py +++ b/cpython-unix/build.py @@ -258,13 +258,18 @@ def simple_build( if "static" in build_options: env["STATIC"] = 1 - add_target_env(env, host_platform, target_triple, build_env) - + # FIPS: For openssl, build locally and not on container, so skip setting toolchain env if entry in ("openssl-1.1", "openssl-3.0"): settings = get_targets(TARGETS_CONFIG)[target_triple] env["OPENSSL_TARGET"] = settings["openssl_target"] + else: + add_target_env(env, host_platform, target_triple, build_env) - build_env.run("build-%s.sh" % entry, environment=env) + build_env.run( + "build-%s.sh" % entry, + environment=env, + user=("build" if client is None else "root") + ) build_env.get_tools_archive(dest_archive, tools_path) @@ -281,10 +286,7 @@ def build_binutils(client, image, host_platform): add_env_common(env) - build_env.run( - "build-binutils.sh", - environment=env, - ) + build_env.run("build-binutils.sh", user="root", environment=env) build_env.get_tools_archive( toolchain_archive_path("binutils", host_platform), "host" @@ -366,7 +368,7 @@ def build_libedit( add_target_env(env, host_platform, target_triple, build_env) - build_env.run("build-libedit.sh", environment=env) + build_env.run("build-libedit.sh", environment=env, user="root") build_env.get_tools_archive(dest_archive, "deps") @@ -408,7 +410,7 @@ def build_tix( add_target_env(env, host_platform, target_triple, build_env) - build_env.run("build-tix.sh", environment=env) + build_env.run("build-tix.sh", environment=env, user="root") build_env.get_tools_archive(dest_archive, "deps") @@ -469,10 +471,7 @@ def build_cpython_host( if meets_python_maximum_version(python_version, v): env[f"PYTHON_MEETS_MAXIMUM_VERSION_{normal_version}"] = "1" - build_env.run( - "build-cpython-host.sh", - environment=env, - ) + build_env.run("build-cpython-host.sh", environment=env, user="root") build_env.get_tools_archive(dest_archive, "host") @@ -846,7 +845,7 @@ def build_cpython( add_target_env(env, host_platform, target_triple, build_env) - build_env.run("build-cpython.sh", environment=env) + build_env.run("build-cpython.sh", environment=env, user="root") extension_module_loading = ["builtin"] crt_features = [] @@ -1145,11 +1144,12 @@ def main(): "zlib", ): tools_path = "host" if action in ("m4", "patchelf") else "deps" - + # FIPS: Build ssl library locally + _client = client if 'ssl' not in action else None simple_build( settings, - client, - get_image(client, ROOT, BUILD, docker_image), + _client, + get_image(_client, ROOT, BUILD, docker_image), action, host_platform=host_platform, target_triple=target_triple, diff --git a/pythonbuild/buildenv.py b/pythonbuild/buildenv.py index 4b2a0e6e4..1eefb72f5 100644 --- a/pythonbuild/buildenv.py +++ b/pythonbuild/buildenv.py @@ -50,7 +50,7 @@ def install_toolchain_archive( p = build_dir / basename self.copy_file(p) - self.run(["/bin/tar", "-C", "/tools", "-xf", "/build/%s" % p.name]) + self.run(["/bin/tar", "-C", "/tools", "-xf", "/build/%s" % p.name], user="root") def install_artifact_archive( self, build_dir, package_name, target_triple, build_options @@ -66,7 +66,7 @@ def install_artifact_archive( p = build_dir / basename self.copy_file(p) - self.run(["/bin/tar", "-C", "/tools", "-xf", "/build/%s" % p.name]) + self.run(["/bin/tar", "-C", "/tools", "-xf", "/build/%s" % p.name], user="root") def install_toolchain( self, diff --git a/pythonbuild/cpython.py b/pythonbuild/cpython.py index f339037ce..9392e36dc 100644 --- a/pythonbuild/cpython.py +++ b/pythonbuild/cpython.py @@ -492,11 +492,15 @@ def derive_setup_local( enabled_extensions[name]["setup_line"] = name.encode("ascii") continue - # Force static linking if we're doing a fully static build, otherwise, - # respect the `build-mode` falling back to `static` if not defined. - section = ( - "static" if "static" in build_options else info.get("build-mode", "static") - ) + # FIPS: Always shared + if name in ("_ssl", "_hashlib"): + section = "shared" + else: + # Force static linking if we're doing a fully static build, otherwise, + # respect the `build-mode` falling back to `static` if not defined. + section = ( + "static" if "static" in build_options else info.get("build-mode", "static") + ) enabled_extensions[name]["build-mode"] = section # Presumably this means the extension comes from the distribution's diff --git a/pythonbuild/downloads.py b/pythonbuild/downloads.py index f59afd82c..52eda5cf2 100644 --- a/pythonbuild/downloads.py +++ b/pythonbuild/downloads.py @@ -245,10 +245,10 @@ # using the latest available. # Remember to update OPENSSL_VERSION_INFO in verify_distribution.py whenever upgrading. "openssl-3.0": { - "url": "https://www.openssl.org/source/openssl-3.0.16.tar.gz", - "size": 15334967, - "sha256": "57e03c50feab5d31b152af2b764f10379aecd8ee92f16c985983ce4a99f7ef86", - "version": "3.0.16", + "url": "https://www.openssl.org/source/openssl-3.0.2.tar.gz", + "size": 15038141, + "sha256": "98e91ccead4d4756ae3c9cde5e09191a8e586d9f4d50838e7ec09d6411dfdb63", + "version": "3.0.2", "library_names": ["crypto", "ssl"], "licenses": ["Apache-2.0"], "license_file": "LICENSE.openssl-3.txt",