diff --git a/CMakeLists.txt b/CMakeLists.txt index cb6a3b33df1..a585788051c 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -52,7 +52,11 @@ find_package(Foundation QUIET) find_package(SQLite3 REQUIRED) # Enable `package` modifier for the whole package. -add_compile_options("$<$:-package-name;SwiftPM>") +if(CMAKE_SYSTEM_NAME STREQUAL FreeBSD) + add_compile_options("$<$:-package-name;SwiftPM>" -L/usr/local/lib) +else() + add_compile_options("$<$:-package-name;SwiftPM>") +endif() add_subdirectory(BuildSupport/SwiftSyntax) add_subdirectory(Sources) diff --git a/Package.swift b/Package.swift index 235acef7228..ca5b6c01be5 100644 --- a/Package.swift +++ b/Package.swift @@ -201,7 +201,7 @@ let package = Package( name: "Basics", dependencies: [ "_AsyncFileSystem", - .target(name: "SPMSQLite3", condition: .when(platforms: [.macOS, .iOS, .tvOS, .watchOS, .visionOS, .macCatalyst, .linux])), + .target(name: "SPMSQLite3", condition: .when(platforms: [.macOS, .iOS, .tvOS, .watchOS, .visionOS, .macCatalyst, .linux, .custom("freebsd")])), .product(name: "SwiftToolchainCSQLite", package: "swift-toolchain-sqlite", condition: .when(platforms: [.windows, .android])), .product(name: "DequeModule", package: "swift-collections"), .product(name: "OrderedCollections", package: "swift-collections"), diff --git a/Sources/Basics/Archiver/ZipArchiver.swift b/Sources/Basics/Archiver/ZipArchiver.swift index 58917f4e29d..a1753fec047 100644 --- a/Sources/Basics/Archiver/ZipArchiver.swift +++ b/Sources/Basics/Archiver/ZipArchiver.swift @@ -85,6 +85,13 @@ public struct ZipArchiver: Archiver, Cancellable { arguments: ["tar.exe", "-a", "-c", "-f", destinationPath.pathString, directory.basename], workingDirectory: directory.parentDirectory ) + #elseif os(FreeBSD) + // On FreeBSD, the unzip command is available in base but not the zip command. + // Therefore; we use libarchive(bsdtar) to produce the ZIP archive instead. + let process = AsyncProcess( + arguments: ["tar", "-c", "--format", "zip", "-f", destinationPath.pathString, directory.basename], + workingDirectory: directory.parentDirectory + ) #else // This is to work around `swift package-registry publish` tool failing on // Amazon Linux 2 due to it having an earlier Glibc version (rdar://116370323) diff --git a/Sources/Basics/Cancellator.swift b/Sources/Basics/Cancellator.swift index c1c0ffaf580..508aa47124c 100644 --- a/Sources/Basics/Cancellator.swift +++ b/Sources/Basics/Cancellator.swift @@ -80,7 +80,7 @@ public final class Cancellator: Cancellable, Sendable { // Install the default signal handler. var action = sigaction() - #if canImport(Darwin) || os(OpenBSD) + #if canImport(Darwin) || os(OpenBSD) || os(FreeBSD) action.__sigaction_u.__sa_handler = SIG_DFL #elseif canImport(Musl) action.__sa_handler.sa_handler = SIG_DFL diff --git a/Sources/Basics/Concurrency/AsyncProcess.swift b/Sources/Basics/Concurrency/AsyncProcess.swift index aefab04fcf3..710c156a76d 100644 --- a/Sources/Basics/Concurrency/AsyncProcess.swift +++ b/Sources/Basics/Concurrency/AsyncProcess.swift @@ -553,7 +553,7 @@ package final class AsyncProcess { return stdinPipe.fileHandleForWriting #elseif(!canImport(Darwin) || os(macOS)) // Initialize the spawn attributes. - #if canImport(Darwin) || os(Android) || os(OpenBSD) + #if canImport(Darwin) || os(Android) || os(OpenBSD) || os(FreeBSD) var attributes: posix_spawnattr_t? = nil #else var attributes = posix_spawnattr_t() @@ -598,7 +598,7 @@ package final class AsyncProcess { posix_spawnattr_setflags(&attributes, Int16(flags)) // Setup the file actions. - #if canImport(Darwin) || os(Android) || os(OpenBSD) + #if canImport(Darwin) || os(Android) || os(OpenBSD) || os(FreeBSD) var fileActions: posix_spawn_file_actions_t? = nil #else var fileActions = posix_spawn_file_actions_t() @@ -614,6 +614,8 @@ package final class AsyncProcess { if #available(macOS 10.15, *) { posix_spawn_file_actions_addchdir_np(&fileActions, workingDirectory) } + #elseif os(FreeBSD) + posix_spawn_file_actions_addchdir_np(&fileActions, workingDirectory) #elseif os(Linux) guard SPM_posix_spawn_file_actions_addchdir_np_supported() else { throw AsyncProcess.Error.workingDirectoryNotSupported diff --git a/Sources/Basics/DispatchTimeInterval+Extensions.swift b/Sources/Basics/DispatchTimeInterval+Extensions.swift index 2f37d472994..07f5be1f575 100644 --- a/Sources/Basics/DispatchTimeInterval+Extensions.swift +++ b/Sources/Basics/DispatchTimeInterval+Extensions.swift @@ -95,7 +95,7 @@ extension DispatchTimeInterval { } // remove when available to all platforms -#if os(Linux) || os(Windows) || os(Android) || os(OpenBSD) +#if os(Linux) || os(Windows) || os(Android) || os(OpenBSD) || os(FreeBSD) extension DispatchTime { public func distance(to: DispatchTime) -> DispatchTimeInterval { let final = to.uptimeNanoseconds diff --git a/Sources/Basics/Triple+Basics.swift b/Sources/Basics/Triple+Basics.swift index a5921b4122a..8247465475f 100644 --- a/Sources/Basics/Triple+Basics.swift +++ b/Sources/Basics/Triple+Basics.swift @@ -62,6 +62,10 @@ extension Triple { os == .openbsd } + public func isFreeBSD() -> Bool { + os == .freebsd + } + /// Returns the triple string for the given platform version. /// /// This is currently meant for Apple platforms only. @@ -139,7 +143,7 @@ extension Triple { switch os { case _ where isDarwin(): return ".dylib" - case .linux, .openbsd: + case .linux, .openbsd, .freebsd: return ".so" case .win32: return ".dll" @@ -179,7 +183,7 @@ extension Triple { switch os { case _ where isDarwin(): return "" - case .linux, .openbsd: + case .linux, .openbsd, .freebsd: return "" case .win32: return ".exe" diff --git a/Sources/Basics/Vendor/Triple+Platforms.swift b/Sources/Basics/Vendor/Triple+Platforms.swift index ea0b1b147da..d26931b0ca7 100644 --- a/Sources/Basics/Vendor/Triple+Platforms.swift +++ b/Sources/Basics/Vendor/Triple+Platforms.swift @@ -304,7 +304,7 @@ extension Triple { case .linux: return environment == .android ? "android" : "linux" - case .freeBSD: + case .freebsd: return "freebsd" case .openbsd: return "openbsd" diff --git a/Sources/Basics/Vendor/Triple.swift b/Sources/Basics/Vendor/Triple.swift index 23f2be259b1..441962f43ea 100644 --- a/Sources/Basics/Vendor/Triple.swift +++ b/Sources/Basics/Vendor/Triple.swift @@ -1089,7 +1089,7 @@ extension Triple { case cloudABI = "cloudabi" case darwin case dragonFly = "dragonfly" - case freeBSD = "freebsd" + case freebsd = "freebsd" case fuchsia case ios case kfreebsd @@ -1137,7 +1137,7 @@ extension Triple { case _ where os.hasPrefix("dragonfly"): return .dragonFly case _ where os.hasPrefix("freebsd"): - return .freeBSD + return .freebsd case _ where os.hasPrefix("fuchsia"): return .fuchsia case _ where os.hasPrefix("ios"): diff --git a/Sources/Build/BuildDescription/ProductBuildDescription.swift b/Sources/Build/BuildDescription/ProductBuildDescription.swift index fb78c14baa3..e72921f20ba 100644 --- a/Sources/Build/BuildDescription/ProductBuildDescription.swift +++ b/Sources/Build/BuildDescription/ProductBuildDescription.swift @@ -270,7 +270,7 @@ public final class ProductBuildDescription: SPMBuildCore.ProductBuildDescription // Set rpath such that dynamic libraries are looked up // adjacent to the product, unless overridden. if !self.buildParameters.linkingParameters.shouldDisableLocalRpath { - if triple.isLinux() { + if triple.isLinux() || triple.isFreeBSD() { args += ["-Xlinker", "-rpath=$ORIGIN"] } else if triple.isDarwin() { let rpath = self.product.type == .test ? "@loader_path/../../../" : "@loader_path" diff --git a/Sources/Build/BuildDescription/SwiftModuleBuildDescription.swift b/Sources/Build/BuildDescription/SwiftModuleBuildDescription.swift index 94e902be0e4..fe4a9cdb0f5 100644 --- a/Sources/Build/BuildDescription/SwiftModuleBuildDescription.swift +++ b/Sources/Build/BuildDescription/SwiftModuleBuildDescription.swift @@ -144,7 +144,7 @@ public final class SwiftModuleBuildDescription { public var moduleOutputPath: AbsolutePath { // note: needs to be public because of sourcekit-lsp // If we're an executable and we're not allowing test targets to link against us, we hide the module. let triple = buildParameters.triple - let allowLinkingAgainstExecutables = (triple.isDarwin() || triple.isLinux() || triple.isWindows()) && self.toolsVersion >= .v5_5 + let allowLinkingAgainstExecutables = (triple.isDarwin() || triple.isLinux() || triple.isFreeBSD() || triple.isWindows()) && self.toolsVersion >= .v5_5 let dirPath = (target.type == .executable && !allowLinkingAgainstExecutables) ? self.tempsPath : self.modulesPath return dirPath.appending(component: "\(self.target.c99name).swiftmodule") } diff --git a/Sources/Build/BuildPlan/BuildPlan+Product.swift b/Sources/Build/BuildPlan/BuildPlan+Product.swift index 10fa8c6bc3b..038ab6515db 100644 --- a/Sources/Build/BuildPlan/BuildPlan+Product.swift +++ b/Sources/Build/BuildPlan/BuildPlan+Product.swift @@ -63,7 +63,7 @@ extension BuildPlan { for description in dependencies.staticTargets { if case let target as ClangModule = description.module.underlying, target.isCXX { let triple = buildProduct.buildParameters.triple - if triple.isDarwin() { + if triple.isDarwin() || triple.isFreeBSD() { buildProduct.additionalFlags += ["-lc++"] } else if triple.isWindows() { // Don't link any C++ library. diff --git a/Sources/Build/BuildPlan/BuildPlan.swift b/Sources/Build/BuildPlan/BuildPlan.swift index d2b73cdaa85..886a268007c 100644 --- a/Sources/Build/BuildPlan/BuildPlan.swift +++ b/Sources/Build/BuildPlan/BuildPlan.swift @@ -148,7 +148,7 @@ extension BuildParameters { let args: [String] if self.triple.isApple() { args = ["-alias", "_\(target.c99name)_main", "_main"] - } else if self.triple.isLinux() { + } else if self.triple.isLinux() || self.triple.isFreeBSD() { args = ["--defsym", "main=\(target.c99name)_main"] } else { return nil diff --git a/Sources/Commands/SwiftTestCommand.swift b/Sources/Commands/SwiftTestCommand.swift index e46c1f2bd9f..c9a16dcf1c0 100644 --- a/Sources/Commands/SwiftTestCommand.swift +++ b/Sources/Commands/SwiftTestCommand.swift @@ -1491,7 +1491,7 @@ private extension Basics.Diagnostic { /// it duplicates the definition of this constant in its own source. Any changes /// to this constant in either package must be mirrored in the other. private var EXIT_NO_TESTS_FOUND: CInt { -#if os(macOS) || os(Linux) || canImport(Android) +#if os(macOS) || os(Linux) || canImport(Android) || os(FreeBSD) EX_UNAVAILABLE #elseif os(Windows) ERROR_NOT_FOUND diff --git a/Sources/PackageCollections/Providers/JSONPackageCollectionProvider.swift b/Sources/PackageCollections/Providers/JSONPackageCollectionProvider.swift index b3e8d458055..1df42244400 100644 --- a/Sources/PackageCollections/Providers/JSONPackageCollectionProvider.swift +++ b/Sources/PackageCollections/Providers/JSONPackageCollectionProvider.swift @@ -32,7 +32,7 @@ private typealias JSONModel = PackageCollectionModel.V1 struct JSONPackageCollectionProvider: PackageCollectionProvider { // TODO: This can be removed when the `Security` framework APIs that the `PackageCollectionsSigning` // module depends on are available on all Apple platforms. - #if os(macOS) || os(Linux) || os(Windows) || os(Android) + #if os(macOS) || os(Linux) || os(Windows) || os(Android) || os(FreeBSD) static let isSignatureCheckSupported = true #else static let isSignatureCheckSupported = false @@ -551,6 +551,8 @@ extension PackageModel.Platform { self = PackageModel.Platform.wasi case let name where name.contains("openbsd"): self = PackageModel.Platform.openbsd + case let name where name.contains("freebsd"): + self = PackageModel.Platform.freebsd default: return nil } diff --git a/Sources/PackageDescription/SupportedPlatforms.swift b/Sources/PackageDescription/SupportedPlatforms.swift index e18b8a251f7..704d7f06558 100644 --- a/Sources/PackageDescription/SupportedPlatforms.swift +++ b/Sources/PackageDescription/SupportedPlatforms.swift @@ -69,6 +69,10 @@ public struct Platform: Equatable, Sendable { /// The OpenBSD platform. @available(_PackageDescription, introduced: 5.8) public static let openbsd: Platform = Platform(name: "openbsd") + + /// The FreeBSD platform. + @available(_PackageDescription, introduced: 999.0) + public static let freebsd: Platform = Platform(name: "freebsd") } /// A platform that the Swift package supports. diff --git a/Sources/PackageLoading/Platform.swift b/Sources/PackageLoading/Platform.swift index f073e0bce0e..b98a3848cf4 100644 --- a/Sources/PackageLoading/Platform.swift +++ b/Sources/PackageLoading/Platform.swift @@ -25,6 +25,7 @@ public enum Platform: Equatable, Sendable { case darwin case linux(LinuxFlavor) case windows + case freebsd /// Recognized flavors of linux. public enum LinuxFlavor: Equatable, Sendable { @@ -44,6 +45,8 @@ extension Platform { { case "darwin"?: return .darwin + case "freebsd"?: + return .freebsd case "linux"?: return Platform.findCurrentPlatformLinux(localFileSystem) default: @@ -89,7 +92,7 @@ extension Platform { public var dynamicLibraryExtension: String { switch self { case .darwin: return ".dylib" - case .linux, .android: return ".so" + case .linux, .android, .freebsd: return ".so" case .windows: return ".dll" } } @@ -97,7 +100,7 @@ extension Platform { public var executableExtension: String { switch self { case .windows: return ".exe" - case .linux, .android, .darwin: return "" + case .linux, .android, .darwin, .freebsd: return "" } } } diff --git a/Sources/PackageLoading/Target+PkgConfig.swift b/Sources/PackageLoading/Target+PkgConfig.swift index 2eae23dd168..8ed3d9db588 100644 --- a/Sources/PackageLoading/Target+PkgConfig.swift +++ b/Sources/PackageLoading/Target+PkgConfig.swift @@ -154,6 +154,8 @@ extension SystemPackageProviderDescription { return " yum install \(packages.joined(separator: " "))\n" case .nuget(let packages): return " nuget install \(packages.joined(separator: " "))\n" + case .pkg(let packages): + return " pkg install \(packages.joined(separator: " "))\n" } } @@ -180,9 +182,13 @@ extension SystemPackageProviderDescription { switch platform { case .darwin, .windows, .linux: return true - case .android: + case .android, .freebsd: return false } + case .pkg: + if case .freebsd = platform { + return true + } } return false } @@ -215,6 +221,8 @@ extension SystemPackageProviderDescription { return [] case .nuget: return [] + case .pkg: + return [] } } diff --git a/Sources/PackageModel/Manifest/SystemPackageProviderDescription.swift b/Sources/PackageModel/Manifest/SystemPackageProviderDescription.swift index cef227bee18..72dc61489cf 100644 --- a/Sources/PackageModel/Manifest/SystemPackageProviderDescription.swift +++ b/Sources/PackageModel/Manifest/SystemPackageProviderDescription.swift @@ -16,11 +16,12 @@ public enum SystemPackageProviderDescription: Hashable, Codable, Sendable { case apt([String]) case yum([String]) case nuget([String]) + case pkg([String]) } extension SystemPackageProviderDescription { private enum CodingKeys: String, CodingKey { - case brew, apt, yum, nuget + case brew, apt, yum, nuget, pkg } public func encode(to encoder: Encoder) throws { @@ -38,6 +39,9 @@ extension SystemPackageProviderDescription { case let .nuget(a1): var unkeyedContainer = container.nestedUnkeyedContainer(forKey: .nuget) try unkeyedContainer.encode(a1) + case let .pkg(a1): + var unkeyedContainer = container.nestedUnkeyedContainer(forKey: .pkg) + try unkeyedContainer.encode(a1) } } @@ -63,6 +67,10 @@ extension SystemPackageProviderDescription { var unkeyedValues = try values.nestedUnkeyedContainer(forKey: key) let a1 = try unkeyedValues.decode([String].self) self = .nuget(a1) + case .pkg: + var unkeyedValues = try values.nestedUnkeyedContainer(forKey: key) + let a1 = try unkeyedValues.decode([String].self) + self = .pkg(a1) } } } diff --git a/Sources/PackageModel/ManifestSourceGeneration.swift b/Sources/PackageModel/ManifestSourceGeneration.swift index e6860202f9c..c7d7b00d1b9 100644 --- a/Sources/PackageModel/ManifestSourceGeneration.swift +++ b/Sources/PackageModel/ManifestSourceGeneration.swift @@ -416,6 +416,9 @@ fileprivate extension SourceCodeFragment { case .nuget(let names): let params = [SourceCodeFragment(strings: names)] self.init(enum: "nuget", subnodes: params) + case .pkg(let names): + let params = [SourceCodeFragment(strings: names)] + self.init(enum: "pkg", subnodes: params) } } diff --git a/Sources/PackageModel/Platform.swift b/Sources/PackageModel/Platform.swift index 509db8842d5..4f808aae187 100644 --- a/Sources/PackageModel/Platform.swift +++ b/Sources/PackageModel/Platform.swift @@ -49,6 +49,8 @@ public struct Platform: Equatable, Hashable, Codable, Sendable { public static let windows: Platform = Platform(name: "windows", oldestSupportedVersion: .unknown) public static let wasi: Platform = Platform(name: "wasi", oldestSupportedVersion: .unknown) public static let openbsd: Platform = Platform(name: "openbsd", oldestSupportedVersion: .unknown) + public static let freebsd: Platform = Platform(name: "freebsd", oldestSupportedVersion: .unknown) + } diff --git a/Sources/PackageModel/PlatformRegistry.swift b/Sources/PackageModel/PlatformRegistry.swift index aec3e04fcc6..70b6dd836dc 100644 --- a/Sources/PackageModel/PlatformRegistry.swift +++ b/Sources/PackageModel/PlatformRegistry.swift @@ -38,6 +38,7 @@ public struct PlatformRegistry { .macOS, .macCatalyst, .openbsd, + .freebsd, .tvOS, .visionOS, .wasi, diff --git a/Sources/SPMBuildCore/BinaryTarget+Extensions.swift b/Sources/SPMBuildCore/BinaryTarget+Extensions.swift index 15da2a1e3b0..088e7616325 100644 --- a/Sources/SPMBuildCore/BinaryTarget+Extensions.swift +++ b/Sources/SPMBuildCore/BinaryTarget+Extensions.swift @@ -99,7 +99,7 @@ extension Triple.OS { /// Returns a representation of the receiver that can be compared with platform strings declared in an XCFramework. fileprivate var asXCFrameworkPlatformString: String? { switch self { - case .darwin, .linux, .wasi, .win32, .openbsd, .noneOS: + case .darwin, .linux, .wasi, .win32, .openbsd, .freebsd, .noneOS: return nil // XCFrameworks do not support any of these platforms today. case .macosx: return "macos" diff --git a/Sources/SPMBuildCore/BuildParameters/BuildParameters.swift b/Sources/SPMBuildCore/BuildParameters/BuildParameters.swift index 90d3425c361..262f7f0f72b 100644 --- a/Sources/SPMBuildCore/BuildParameters/BuildParameters.swift +++ b/Sources/SPMBuildCore/BuildParameters/BuildParameters.swift @@ -115,6 +115,8 @@ public struct BuildParameters: Encodable { return .windows } else if self.triple.isOpenBSD() { return .openbsd + } else if self.triple.isFreeBSD() { + return .freebsd } else { return .linux } diff --git a/Sources/XCBuildSupport/PIFBuilder.swift b/Sources/XCBuildSupport/PIFBuilder.swift index 2dae7094dcf..1a799c0c490 100644 --- a/Sources/XCBuildSupport/PIFBuilder.swift +++ b/Sources/XCBuildSupport/PIFBuilder.swift @@ -1727,6 +1727,9 @@ extension [PackageCondition] { case .openbsd: result += PIF.PlatformFilter.openBSDFilters + case .freebsd: + result += PIF.PlatformFilter.freeBSDFilters + default: assertionFailure("Unhandled platform condition: \(condition)") } @@ -1789,6 +1792,11 @@ extension PIF.PlatformFilter { .init(platform: "openbsd"), ] + /// FreeBSD filters. + public static let freeBSDFilters: [PIF.PlatformFilter] = [ + .init(platform: "freebsd"), + ] + /// WebAssembly platform filters. public static let webAssemblyFilters: [PIF.PlatformFilter] = [ .init(platform: "wasi"), diff --git a/Tests/BasicsTests/Archiver/UniversalArchiverTests.swift b/Tests/BasicsTests/Archiver/UniversalArchiverTests.swift index 6c7c4249605..69e6bb76911 100644 --- a/Tests/BasicsTests/Archiver/UniversalArchiverTests.swift +++ b/Tests/BasicsTests/Archiver/UniversalArchiverTests.swift @@ -82,7 +82,7 @@ final class UniversalArchiverTests: XCTestCase { inputArchivePath = AbsolutePath(#file).parentDirectory .appending(components: "Inputs", "invalid_archive.zip") await XCTAssertAsyncThrowsError(try await archiver.extract(from: inputArchivePath, to: tmpdir)) { error in -#if os(Windows) +#if os(Windows) || os(FreeBSD) XCTAssertMatch((error as? StringError)?.description, .contains("Unrecognized archive format")) #else XCTAssertMatch((error as? StringError)?.description, .contains("End-of-central-directory signature not found")) diff --git a/Tests/BasicsTests/Archiver/ZipArchiverTests.swift b/Tests/BasicsTests/Archiver/ZipArchiverTests.swift index c8a5e113f0b..ef587452928 100644 --- a/Tests/BasicsTests/Archiver/ZipArchiverTests.swift +++ b/Tests/BasicsTests/Archiver/ZipArchiverTests.swift @@ -62,7 +62,8 @@ final class ZipArchiverTests: XCTestCase { let inputArchivePath = AbsolutePath(#file).parentDirectory .appending(components: "Inputs", "invalid_archive.zip") await XCTAssertAsyncThrowsError(try await archiver.extract(from: inputArchivePath, to: tmpdir)) { error in -#if os(Windows) +#if os(Windows) || os(FreeBSD) + // On FreeBSD, unzip (bsdunzip) is backed by libarchive XCTAssertMatch((error as? StringError)?.description, .contains("Unrecognized archive format")) #else XCTAssertMatch((error as? StringError)?.description, .contains("End-of-central-directory signature not found")) diff --git a/Tests/BuildTests/BuildPlanTests.swift b/Tests/BuildTests/BuildPlanTests.swift index c5d1814c8de..f7581571b9b 100644 --- a/Tests/BuildTests/BuildPlanTests.swift +++ b/Tests/BuildTests/BuildPlanTests.swift @@ -1681,6 +1681,20 @@ final class BuildPlanTests: XCTestCase { "-target", defaultTargetTriple, "-g", "-use-ld=lld", "-Xlinker", "-debug:dwarf", ]) + #elseif os(FreeBSD) + XCTAssertEqual(try result.buildProduct(for: "exe").linkArguments(), [ + result.plan.destinationBuildParameters.toolchain.swiftCompilerPath.pathString, + "-lc++", + "-L", buildPath.pathString, + "-o", buildPath.appending(components: "exe").pathString, + "-module-name", "exe", + "-emit-executable", + "-Xlinker", "-rpath=$ORIGIN", + "@\(buildPath.appending(components: "exe.product", "Objects.LinkFileList"))", + "-runtime-compatibility-version", "none", + "-target", defaultTargetTriple, + "-g", + ]) #else XCTAssertEqual(try result.buildProduct(for: "exe").linkArguments(), [ result.plan.destinationBuildParameters.toolchain.swiftCompilerPath.pathString, @@ -2904,7 +2918,7 @@ final class BuildPlanTests: XCTestCase { result.checkTargetsCount(2) var linkArgs = try result.buildProduct(for: "exe").linkArguments() - #if os(macOS) + #if os(macOS) || os(FreeBSD) XCTAssertMatch(linkArgs, ["-lc++"]) #elseif !os(Windows) XCTAssertMatch(linkArgs, ["-lstdc++"]) @@ -3336,6 +3350,21 @@ final class BuildPlanTests: XCTestCase { "-g", "-use-ld=lld", "-Xlinker", "-debug:dwarf", ]) #else + #if os(FreeBSD) + XCTAssertEqual(try result.buildProduct(for: "lib").linkArguments(), [ + result.plan.destinationBuildParameters.toolchain.swiftCompilerPath.pathString, + "-lc++", + "-L", buildPath.pathString, + "-o", buildPath.appending(components: "liblib.so").pathString, + "-module-name", "lib", + "-emit-library", + "-Xlinker", "-rpath=$ORIGIN", + "@\(buildPath.appending(components: "lib.product", "Objects.LinkFileList"))", + "-runtime-compatibility-version", "none", + "-target", defaultTargetTriple, + "-g", + ]) + #else XCTAssertEqual(try result.buildProduct(for: "lib").linkArguments(), [ result.plan.destinationBuildParameters.toolchain.swiftCompilerPath.pathString, "-lstdc++", @@ -3349,6 +3378,7 @@ final class BuildPlanTests: XCTestCase { "-target", defaultTargetTriple, "-g", ]) + #endif XCTAssertEqual(try result.buildProduct(for: "exe").linkArguments(), [ result.plan.destinationBuildParameters.toolchain.swiftCompilerPath.pathString, @@ -3634,6 +3664,7 @@ final class BuildPlanTests: XCTestCase { .brew(["BTarget"]), .apt(["BTarget"]), .yum(["BTarget"]), + .pkg(["BTarget"]) ] ), ] diff --git a/Tests/PackageLoadingTests/PkgConfigTests.swift b/Tests/PackageLoadingTests/PkgConfigTests.swift index 1f37175b200..094b485b478 100644 --- a/Tests/PackageLoadingTests/PkgConfigTests.swift +++ b/Tests/PackageLoadingTests/PkgConfigTests.swift @@ -71,6 +71,8 @@ class PkgConfigTests: XCTestCase { XCTAssertEqual(names, ["libFoo-devel"]) case .nuget(let names)?: XCTAssertEqual(names, ["Foo"]) + case .pkg(let names)?: + XCTAssertEqual(names, ["Foo"]) case nil: XCTFail("Expected a provider here") } diff --git a/Utilities/bootstrap b/Utilities/bootstrap index 8a582d27657..af5befe55c3 100755 --- a/Utilities/bootstrap +++ b/Utilities/bootstrap @@ -858,6 +858,11 @@ def get_swiftpm_flags(args): build_flags.extend(["-Xcc", "-I/usr/local/include"]) build_flags.extend(["-Xlinker", "-L/usr/local/lib"]) + if '-freebsd' in args.build_target: + build_flags.extend(["-Xlinker", "-z", "-Xlinker", "origin"]) + build_flags.extend(["-Xcc", "-I/usr/local/include"]) + build_flags.extend(["-Xlinker", "-L/usr/local/lib"]) + # Don't use GNU strerror_r on Android. if '-android' in args.build_target: build_flags.extend(["-Xswiftc", "-Xcc", "-Xswiftc", "-U_GNU_SOURCE"])