Skip to content

Add a build flavor to opt-out of BTCFI on OpenBSD. #80389

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Apr 3, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -575,6 +575,17 @@ set(SWIFT_DARWIN_XCRUN_TOOLCHAIN "XcodeDefault" CACHE STRING
set(SWIFT_DARWIN_STDLIB_INSTALL_NAME_DIR "/usr/lib/swift" CACHE STRING
"The directory of the install_name for standard library dylibs")

#
# User-configurable OpenBSD-specific options.
#

option(SWIFT_OPENBSD_BTCFI
"Emit branch target identification instructions and sign return addresses when available"
FALSE)
if(SWIFT_OPENBSD_BTCFI)
add_definitions("-DSWIFT_OPENBSD_BTCFI")
endif()

# We don't want to use the same install_name_dir as the standard library which
# will be installed in /usr/lib/swift. These private libraries should continue
# to use @rpath for now.
Expand Down
4 changes: 4 additions & 0 deletions include/swift/Basic/Platform.h
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,10 @@ namespace swift {
/// (eg. in /usr/lib/swift).
bool tripleRequiresRPathForSwiftLibrariesInOS(const llvm::Triple &triple);

/// Returns true if the given triple represents a version of OpenBSD
/// that enforces BTCFI by default.
bool tripleBTCFIByDefaultInOpenBSD(const llvm::Triple &triple);

/// Returns the platform name for a given target triple.
///
/// For example, the iOS simulator has the name "iphonesimulator", while real
Expand Down
4 changes: 4 additions & 0 deletions lib/Basic/Platform.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,10 @@ bool swift::tripleRequiresRPathForSwiftLibrariesInOS(
return false;
}

bool swift::tripleBTCFIByDefaultInOpenBSD(const llvm::Triple &triple) {
return triple.isOSOpenBSD() && triple.getArch() == llvm::Triple::aarch64;
}

DarwinPlatformKind swift::getDarwinPlatformKind(const llvm::Triple &triple) {
if (triple.isiOS()) {
if (triple.isTvOS()) {
Expand Down
10 changes: 10 additions & 0 deletions lib/Basic/TargetInfo.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -171,6 +171,16 @@ void printTripleInfo(const CompilerInvocation &invocation,
out << " \"compatibilityLibraries\": [ ],\n";
}

if (tripleBTCFIByDefaultInOpenBSD(triple)) {
#if SWIFT_OPENBSD_BTCFI
out << " \"openbsdBTCFIEnabled\": true,\n";
#else
out << " \"openbsdBTCFIEnabled\": false,\n";
#endif
} else {
out << " \"openbsdBTCFIEnabled\": false,\n";
}

out << " \"librariesRequireRPath\": "
<< (tripleRequiresRPathForSwiftLibrariesInOS(triple) ? "true" : "false")
<< "\n";
Expand Down
2 changes: 2 additions & 0 deletions lib/Driver/ToolChains.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -205,12 +205,14 @@ void ToolChain::addCommonFrontendArgs(const OutputInfo &OI,
}

if (Triple.isOSOpenBSD() && Triple.getArch() == llvm::Triple::aarch64) {
#ifdef SWIFT_OPENBSD_BTCFI
arguments.push_back("-Xcc");
arguments.push_back("-Xclang=-mbranch-target-enforce");
arguments.push_back("-Xcc");
arguments.push_back("-Xclang=-msign-return-address=non-leaf");
arguments.push_back("-Xcc");
arguments.push_back("-Xclang=-msign-return-address-key=a_key");
#endif
}

if (inputArgs.getLastArg(options::OPT_experimental_serialize_debug_info)) {
Expand Down
9 changes: 9 additions & 0 deletions lib/Driver/UnixToolChains.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -211,6 +211,15 @@ toolchains::GenericUnix::constructInvocation(const DynamicLinkJobAction &job,
#endif
}

if (tripleBTCFIByDefaultInOpenBSD(getTriple())) {
#ifndef SWIFT_OPENBSD_BTCFI
Arguments.push_back("-Xlinker");
Arguments.push_back("-z");
Arguments.push_back("-Xlinker");
Arguments.push_back("nobtcfi");
#endif
}

// Configure the toolchain.
if (const Arg *A = context.Args.getLastArg(options::OPT_tools_directory)) {
StringRef toolchainPath(A->getValue());
Expand Down
13 changes: 12 additions & 1 deletion utils/build-script-impl
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,9 @@ KNOWN_SETTINGS=(
darwin-toolchain-require-use-os-runtime "0" "When setting up a plist for a toolchain, require the users of the toolchain to link against the OS instead of the packaged toolchain runtime. 0 for false, 1 for true"
darwin-xcrun-toolchain "default" "the name of the toolchain to use on Darwin"

## OpenBSD options
openbsd-btcfi "" "enables BTCFI when possible. May cause stability problems."

## Runtime options
min-runtime-version "" "Used to specify the minimum host runtime version when building the compiler on non-Darwin platforms"

Expand Down Expand Up @@ -877,6 +880,12 @@ function set_build_options_for_host() {
swift_cmake_options+=(
-DCOVERAGE_DB="${COVERAGE_DB}"
)

if [[ "${OPENBSD_BTCFI}" ]]; then
swift_cmake_options+=(
-DSWIFT_OPENBSD_BTCFI:BOOL=TRUE
)
fi
}

function configure_default_options() {
Expand Down Expand Up @@ -1383,7 +1392,9 @@ function swift_c_flags() {
echo -n " -D_GNU_SOURCE -DHAVE_DECL_PROGRAM_INVOCATION_SHORT_NAME"
;;
openbsd-aarch64)
echo -n " -Xclang=-msign-return-address=non-leaf -Xclang=-msign-return-address-key=a_key -Xclang=-mbranch-target-enforce"
if [[ "${OPENBSD_BTCFI}" ]]; then
echo -n " -Xclang=-msign-return-address=non-leaf -Xclang=-msign-return-address-key=a_key -Xclang=-mbranch-target-enforce"
fi
;;
esac
}
Expand Down