From f9fdf94e12b79fd75de3a7069456380976bf0e05 Mon Sep 17 00:00:00 2001 From: Eelco Dolstra Date: Tue, 27 May 2025 15:25:51 +0200 Subject: [PATCH] Fix macOS build --- .../unix/build/darwin-derivation-builder.cc | 71 +++++++++++-------- src/libstore/unix/build/derivation-builder.cc | 20 ++++-- 2 files changed, 54 insertions(+), 37 deletions(-) diff --git a/src/libstore/unix/build/darwin-derivation-builder.cc b/src/libstore/unix/build/darwin-derivation-builder.cc index 2ba54ad97..5e06dbe55 100644 --- a/src/libstore/unix/build/darwin-derivation-builder.cc +++ b/src/libstore/unix/build/darwin-derivation-builder.cc @@ -14,11 +14,20 @@ struct DarwinDerivationBuilder : DerivationBuilderImpl { PathsInChroot pathsInChroot; + /** + * Whether full sandboxing is enabled. Note that macOS builds + * always have *some* sandboxing (see sandbox-minimal.sb). + */ + bool useSandbox; + DarwinDerivationBuilder( - Store & store, std::unique_ptr miscMethods, DerivationBuilderParams params) + Store & store, + std::unique_ptr miscMethods, + DerivationBuilderParams params, + bool useSandbox) : DerivationBuilderImpl(store, std::move(miscMethods), std::move(params)) + , useSandbox(useSandbox) { - useChroot = true; } void prepareSandbox() override @@ -26,32 +35,6 @@ struct DarwinDerivationBuilder : DerivationBuilderImpl pathsInChroot = getPathsInSandbox(); } - void execBuilder(const Strings & args, const Strings & envStrs) override - { - posix_spawnattr_t attrp; - - if (posix_spawnattr_init(&attrp)) - throw SysError("failed to initialize builder"); - - if (posix_spawnattr_setflags(&attrp, POSIX_SPAWN_SETEXEC)) - throw SysError("failed to initialize builder"); - - if (drv.platform == "aarch64-darwin") { - // Unset kern.curproc_arch_affinity so we can escape Rosetta - int affinity = 0; - sysctlbyname("kern.curproc_arch_affinity", NULL, NULL, &affinity, sizeof(affinity)); - - cpu_type_t cpu = CPU_TYPE_ARM64; - posix_spawnattr_setbinpref_np(&attrp, 1, &cpu, NULL); - } else if (drv.platform == "x86_64-darwin") { - cpu_type_t cpu = CPU_TYPE_X86_64; - posix_spawnattr_setbinpref_np(&attrp, 1, &cpu, NULL); - } - - posix_spawn( - NULL, drv.builder.c_str(), NULL, &attrp, stringsToCharPtrs(args).data(), stringsToCharPtrs(envStrs).data()); - } - void setUser() override { DerivationBuilderImpl::setUser(); @@ -59,7 +42,7 @@ struct DarwinDerivationBuilder : DerivationBuilderImpl /* This has to appear before import statements. */ std::string sandboxProfile = "(version 1)\n"; - if (useChroot) { + if (useSandbox) { /* Lots and lots and lots of file functions freak out if they can't stat their full ancestry */ PathSet ancestry; @@ -101,7 +84,7 @@ struct DarwinDerivationBuilder : DerivationBuilderImpl # include "sandbox-defaults.sb" ; - if (!derivationType->isSandboxed()) + if (!derivationType.isSandboxed()) sandboxProfile += # include "sandbox-network.sb" ; @@ -193,7 +176,33 @@ struct DarwinDerivationBuilder : DerivationBuilderImpl } } } -} + + void execBuilder(const Strings & args, const Strings & envStrs) override + { + posix_spawnattr_t attrp; + + if (posix_spawnattr_init(&attrp)) + throw SysError("failed to initialize builder"); + + if (posix_spawnattr_setflags(&attrp, POSIX_SPAWN_SETEXEC)) + throw SysError("failed to initialize builder"); + + if (drv.platform == "aarch64-darwin") { + // Unset kern.curproc_arch_affinity so we can escape Rosetta + int affinity = 0; + sysctlbyname("kern.curproc_arch_affinity", NULL, NULL, &affinity, sizeof(affinity)); + + cpu_type_t cpu = CPU_TYPE_ARM64; + posix_spawnattr_setbinpref_np(&attrp, 1, &cpu, NULL); + } else if (drv.platform == "x86_64-darwin") { + cpu_type_t cpu = CPU_TYPE_X86_64; + posix_spawnattr_setbinpref_np(&attrp, 1, &cpu, NULL); + } + + posix_spawn( + NULL, drv.builder.c_str(), NULL, &attrp, stringsToCharPtrs(args).data(), stringsToCharPtrs(envStrs).data()); + } +}; } diff --git a/src/libstore/unix/build/derivation-builder.cc b/src/libstore/unix/build/derivation-builder.cc index 142f75d14..1eff3487b 100644 --- a/src/libstore/unix/build/derivation-builder.cc +++ b/src/libstore/unix/build/derivation-builder.cc @@ -308,8 +308,6 @@ protected: */ void runChild(); -private: - /** * Move the current process into the chroot, if any. Called early * by runChild(). @@ -330,6 +328,8 @@ private: */ virtual void execBuilder(const Strings & args, const Strings & envStrs); +private: + /** * Check that the derivation outputs all exist and register them * as valid. @@ -2119,7 +2119,7 @@ std::unique_ptr makeDerivationBuilder( throw Error("derivation '%s' has '__noChroot' set, " "but that's not allowed when 'sandbox' is 'true'", store.printStorePath(params.drvPath)); #ifdef __APPLE__ - if (drvOptions.additionalSandboxProfile != "") + if (params.drvOptions.additionalSandboxProfile != "") throw Error("derivation '%s' specifies a sandbox profile, " "but this is only allowed when 'sandbox' is 'relaxed'", store.printStorePath(params.drvPath)); #endif @@ -2158,16 +2158,24 @@ std::unique_ptr makeDerivationBuilder( std::move(params)); #endif - if (useSandbox) - throw Error("sandboxing builds is not supported on this platform"); - if (params.drvOptions.useUidRange(params.drv)) throw Error("feature 'uid-range' is only supported in sandboxed builds"); + #ifdef __APPLE__ + return std::make_unique( + store, + std::move(miscMethods), + std::move(params), + useSandbox); + #else + if (useSandbox) + throw Error("sandboxing builds is not supported on this platform"); + return std::make_unique( store, std::move(miscMethods), std::move(params)); + #endif } }