Skip to content

Commit e8afe15

Browse files
committed
[docs] Improve the instructions for using Ninja with Xcode
1 parent a358701 commit e8afe15

File tree

1 file changed

+75
-25
lines changed

1 file changed

+75
-25
lines changed

docs/DevelopmentTips.md

Lines changed: 75 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -100,28 +100,78 @@ For example, to have `build-script` spawn only one link job at a time, we can in
100100
build-script --llvm-cmake-options=-DLLVM_PARALLEL_LINK_JOBS=1 --swift-cmake-options=-DSWIFT_PARALLEL_LINK_JOBS=1
101101
```
102102

103-
## Using ninja with Xcode
104-
105-
Although it's possible to build the swift compiler entirely with Xcode (`--xcode`), often it's better to build with _ninja_ and use Xcode for editing and debugging.
106-
This is very convenient because you get the benefits of the ninja build system and all the benefits of the Xcode IDE, like code completion, refactoring, debugging, etc.
107-
108-
To setup this environment a few steps are necessary:
109-
* Create a new workspace.
110-
* Create Xcode projects for LLVM and Swift with `utils/build-script --skip-build --xcode --skip-early-swift-driver`. Beside configuring, this needs to build a few LLVM files which are needed to configure the swift project.
111-
* Add the generated LLVM and Swift projects to your workspace. They can be found in the build directories `build/Xcode-DebugAssert/llvm-macosx-x86_64/LLVM.xcodeproj` and `build/Xcode-DebugAssert/swift-macosx-x86_64/Swift.xcodeproj`.
112-
* Add the `swift/SwiftCompilerSources` package to the workspace.
113-
* Create a new empty project `build-targets` (or however you want to name it) in the workspace, using the "External Build System" template.
114-
* For each compiler tool you want to build (`swift-frontend`, `sil-opt`, etc.), add an "External Build System" target to the `build-targets` project.
115-
* In the "Info" section of the target configuration, set:
116-
* the _Build Tool_ to the full path of the `ninja` command
117-
* the _Argument_ to the tool name (e.g. `swift-frontend`)
118-
* the _Directory_ to the ninja swift build directory, e.g. `/absolute/path/to/build/Ninja-DebugAssert/swift-macosx-x86_64`. For debugging to work, this has to be a debug build of course.
119-
* For each target, create a new scheme:
120-
* In the _Build_ section add the corresponding build target that you created before.
121-
* In the _Run/Info_ section select the built _Executable_ in the build directory (e.g. `/absolute/path/to/build/Ninja-DebugAssert/swift-macosx-x86_64/bin/swift-frontend`).
122-
* In the _Run/Arguments_ section you can set the command line arguments with which you want to run the compiler tool.
123-
* In the _Run/Options_ section you can set the working directory for debugging.
124-
125-
Now you are all set. You can build and debug like with a native Xcode project.
126-
127-
If the project structure changes, e.g. new source files are added or deleted, you just have to re-create the LLVM and Swift projects with `utils/build-script --skip-build --xcode --skip-early-swift-driver`.
103+
## Using Ninja with Xcode
104+
105+
Although it's possible to build the toolchain entirely with Xcode via `--xcode`,
106+
a more efficient and robust option is to integrate a Ninja build with Xcode.
107+
This is also convenient in that you can navigate, build, run, edit and debug in
108+
Xcode while retaining the option of using Ninja on the command line.
109+
110+
Assuming that you have already [built the toolchain via Ninja](#the-actual-build),
111+
several more steps are necessary to set up this environment:
112+
* Generate Xcode projects with `utils/build-script --skip-build --xcode --skip-early-swift-driver`.
113+
This will first build a few LLVM files that are needed to configure the
114+
projects.
115+
* Create a new Xcode workspace.
116+
* Add the generated Xcode projects or Swift packages that are relevant to your
117+
tasks to your workspace. All the Xcode projects can be found among the
118+
build artifacts in `build/Xcode-DebugAssert`. For example:
119+
* If you are aiming for the compiler, add `build/Xcode-DebugAssert/swift-macosx-*/Swift.xcodeproj`.
120+
This project also includes the standard library and runtime sources. If you
121+
need the parts of the compiler that are implemented in Swift itself, add the
122+
`swift/SwiftCompilerSources/Package.swift` package as well.
123+
* If you are aiming for just the standard library or runtime, add
124+
`build/Xcode-DebugAssert/swift-macosx-*/stdlib/Swift-stdlib.xcodeproj`.
125+
<!-- FIXME: Without this "hard" line break, the note doesn’t get properly spaced from the bullet -->
126+
<br />
127+
128+
> **Warning**
129+
> Adding both `Swift.xcodeproj` and `LLVM.xcodeproj` *might* slow down the IDE
130+
and is not recommended unless you know what you're doing.
131+
132+
In general, we encourage you to add only what you need. Keep in mind that none
133+
of the generated Xcode projects are required to build or run with this setup
134+
because we are using Ninja—an *external* build system; rather, they should be
135+
viewed as a means of leveraging the navigation, editing and debugging features
136+
of the IDE in relation to the source code they wrap.
137+
138+
* Create an empty Xcode project in the workspace, using the
139+
_External Build System_ template.
140+
* For a Ninja target that you want to build (e.g. `swift-frontend`), add a
141+
target to the empty project, using the _External Build System_ template.
142+
* In the _Info_ pane of the target settings, set
143+
* _Build Tool_ to the path of the `ninja` executable (the output of
144+
`which ninja` on the command line)
145+
* _Arguments_ to the Ninja target name (e.g. `swift-frontend`)
146+
* _Directory_ to the path of the build directory associated with the Ninja
147+
target. For Swift targets, including the standard library and runtime, you
148+
want `path/to/swift-project/build/Ninja-*/swift-macosx-*`
149+
* Add a scheme for the target. Be sure not to select a target from one the
150+
generated Xcode projects.
151+
* > **Note**
152+
> Ignore this step if the target associates to a non-executable Ninja target
153+
like `swift-stdlib`.
154+
155+
Adjust the _Run_ action settings of the scheme:
156+
* In the _Info_ pane, select the _Executable_ built by the Ninja target from
157+
the appropriate `bin` directory (e.g. `build/Ninja-*/swift-macosx-*/bin/swift-frontend`).
158+
* In the _Arguments_ pane, add the command line arguments that you want to
159+
pass to the executable on launch (e.g. `path/to/file.swift -typecheck` for
160+
`swift-frontend`).
161+
* You can optionally set the working directory for debugging in the
162+
_Options_ pane.
163+
* Configure as many more target-scheme pairs as you need.
164+
165+
Now you are all set! You can build, run and debug as with a native Xcode
166+
project. If an `update-checkout` routine or a structural change—such as when
167+
source files are added or deleted—happens to impact your editing experience,
168+
simply regenerate the Xcode projects.
169+
170+
> **Note**
171+
> * For debugging to *fully* work for a given component—say, the compiler—the
172+
`build-script` invocation for the Ninja build must be arranged to
173+
[build a debug variant of that component](#debugging-issues).
174+
> * Xcode's indexing can occasionally start slipping after switching to and back
175+
from a distant branch, resulting in a noticeable slowdown. To sort things
176+
out, close the workspace and delete the _Index_ directory from the
177+
workspace's derived data before reopening.

0 commit comments

Comments
 (0)