Failing to build a swift toolchain when including XCTest

Currently trying to locally build a toolchain on my Mac. Currently my steps are the following:

mkdir swift-project
cd swift-project
git clone git@github.com:swiftlang/swift.git swift
cd swift
utils/update-checkout --clone-with-ssh
git checkout swift-DEVELOPMENT-SNAPSHOT-2024-10-27-a
utils/update-checkout --tag swift-DEVELOPMENT-SNAPSHOT-2024-10-27-a
brew install cmake ninja sccache
time utils/build-script --swift-darwin-supported-archs "$(uname -m)" --skip-build-benchmarks --libcxx --assertions --swiftpm --skip-clean-swiftpm --skip-test-swiftpm --swift-driver --skip-clean-swift-driver --skip-test-early-swift-driver --skip-test-swift-driver --build-swift-static-sdk-overlay --skip-test-osx --llbuild --skip-clean-llbuild --lldb --no-llvm-include-tests --install-all --skip-ios --skip-watchos --skip-tvos --skip-clean-llbuild --skip-xros --skip-build-benchmarks --skip-clean-foundation --foundation --release-debuginfo --swift-disable-dead-stripping --distcc false

This completes successfully. The issue I'm running into when I try and add the flags: --xctest --skip-clean-xctest
Where it fails with the following error:

swift-project/swift-corelibs-xctest/Sources/XCTest/Public/XCTestMain.swift:21:23: error: no such module 'SwiftFoundation'
    @_exported import SwiftFoundation
                      ^

What am I missing here that could cause this?

With the swift-foundation re-core that landed in Swift 6, the swift-corelibs-foundation project no longer has a way to build for macOS (it never truly built for macOS but rather had a project just for ease of testing and built as SwiftFoundation, but we've decided to remove that since it's unmaintained and led to some confusion). In fact, you'll likely see something in your build log indicating that even though you passed --foundation, that Foundation is actually being skipped and not actually built. As a result of that, XCTest cannot build on macOS either (since it depended on the old SwiftFoundation pseudo-module), and for similar reasons it shouldn't be necessary - the XCTest used on macOS always has to be the XCTest from Xcode/the OS rather than the toolchain anyways, so I don't believe building XCTest on macOS really has a great purpose nowadays.

Is there something in particular you're trying to accomplish here?

cc @grynspan

1 Like

Ah this is super helpful information thanks! Do I understand correctly then that the Foundation (since it's skipped) is the one from Xcode/the OS. as well? Just out of curiosity how would one then do a custom build of foundation? Or is that simply by directly building and importing the swift package now?
As for what I was trying to achieve, I was just trying to build a "full" toolchain and since I was planning on running some tests with this new toolchain as well I just expected I'd need to add XCTest for that to work for me.
Thanks for the context really appreciated!

Yep, on macOS (or any Apple Platform) Foundation always comes from the OS. Since all of the other libraries/frameworks in the OS use the Foundation from the OS and there can only be one Foundation in a given process (otherwise chaos ensues :slight_smile:) the one Foundation must be the one from the OS. So building a "full" toolchain on macOS wouldn't build Foundation, since Foundation for macOS isn't part of the toolchain.

If you want to build Foundation yourself for testing purposes, it depends on which part of Foundation you want to build:

swift-foundation: This is the repo where most active development of Foundation is happening, and where all of the code shared between the Foundation.framework on macOS and the Foundation module on non-Darwin platforms lives. To build this, you can either build a full toolchain on Linux/Windows (which will build this repo), or you can build it as a standalone project via SwiftPM (either via Xcode or via swift build). This project does build for macOS since its source code is shared with the Foundation.framework build on macOS, so building on macOS does have some meaning and it allows for easy development on macOS.

swift-corelibs-foundation: This serves as a code base for somewhat legacy (but still supported) types that is not shared between Apple platforms and open source platforms. Since the source code is not shared, this project cannot be built for macOS. To test/build this project, you can only build it for Linux or Windows (which can be done via a docker container or VM on a Mac). This project builds as part of the toolchain, but can also be built as a standalone project via SwiftPM too (note however that building as a standalone project is a little tricky, especially on Windows where it requires pre-building dependencies like libxml/curl manually, but on Linux it should "just work" with a nightly snapshot docker container).

Jonathan might be able to elaborate further on XCTest's setup if you feel you need to test changes to that framework.

2 Likes

No this is perfect! It was mainly just something I assumed I needed but this makes it super clear how these parts fit together thanks!

1 Like