Swift のソースファイルを Xcode で開けるようにする
Swift プログラミング
普段から使って慣れてる Xcode を使って、オープンソース化された Swift のコードを眺められるようにしてみました。
そんな頃合いにちょうどコードを見てみたい箇所が出てきたのですけど、普段から Xcode ばかりに頼っていると、ターミナルでファイルを探して眺めるのもなかなか億劫でした。
幸い Swift リポジトリでは Xcode でソースファイルを開くための Xcode プロジェクトファイルを作成できるようになっていたので、早速 Xcode で Swift のコードを開ける環境を作ってみました。
Swift ソースコードを取得する
そのために、まずは Swift のソースコードを取得します。
今回は ~/source/Swift
みたいなフォルダーを作って、ターミナルでその中へ移動し、ソースコードの取得などの作業を行うことにします。
cd ~/source/Swift
最新の Xcode は既にインストールしてあるので、Swift リポジトリに記載のある通り、次のようにしてソースコードを取得しました。
git clone https://github.com/apple/swift.git swift
git clone https://github.com/apple/swift-llvm.git llvm
git clone https://github.com/apple/swift-clang.git clang
git clone https://github.com/apple/swift-lldb.git lldb
git clone https://github.com/apple/swift-cmark.git cmark
git clone https://github.com/apple/swift-llbuild.git llbuild
git clone https://github.com/apple/swift-package-manager.git swiftpm
git clone https://github.com/apple/swift-corelibs-xctest.git
git clone https://github.com/apple/swift-corelibs-foundation.git
これで Swift に関連するソースコードを取得できた様子です。
CMake をインストールする
せっかくなので、その他のビルドに必要なものも用意しておきます。
Swift のビルドには CMake というツールが必要になるようなので、これの Mac OS X 用を Installing | CMake からダウンロードしてインストールすることにします。
dmg 形式のものをダウンロードしてマウントすると、OS X のアプリとして CMake が手に入ります。
これを普段のアプリと同じように /Applications
フォルダーにインストールします。そしてターミナルで次のコマンドを実行して CMake をターミナルからもすぐに使えるようにしておきます。
export PATH=/Applications/CMake.app/Contents/bin:$PATH
ターミナルを起動した時にいつでも CMake を使えるように、先ほど実行した export
コマンドを ~/.bash_profile
などの起動時に読み込まれるスクリプト内に記載しておくと良さそうです。
Xcode プロジェクトを生成する
ここまで出来たら、あとは次のコマンドを実行して Xcode プロジェクトファイルを作成できました。
./swift/utils/build-script -X --skip-build -- --reconfigure
こうすると、今回用意したフォルダーの直下に build
というフォルダーが出来上がり、その中にさらに Xcode-DebugAssert
というフォルダーが作成されます。
そしてその中身を見ると、幾つかのフォルダーが作られているのが目に止まります。
これらが今回の操作で出来上がったファイルで、このそれぞれに Xcode のプロジェクトファイルが用意されています。たとえば Swift のソースコードを開きたければ swift-macosx-x86_64
フォルダー内の Swift.xcodeproj
を開きます。
初めてプロジェクトを開いたときに Autocreate Schemes
というダイアログメッセージが表示されます。今のところは Xcode で Swift をビルドできない(敢えてエラーにしている)ようなので、作らなくても問題はなさそうです。ただ、静的ライブラリまでは Xcode でもビルドできる様子なので、それをしたいような場合は作っておくと楽かもしれません。
足りないファイルを生成する
これで Xcode で開けるようになりましたけど、実際にコードを見てみると幾つか足りないファイルが出てきます。
それらのファイルは Swift のビルドを行ったときには生成されます。Xcode では今のところ Swift を完全にビルドするところまではできないのでなくても支障はないかもしれませんけど、せっかくならそれらのファイルも揃えておきたいところです。
次で紹介する方法の他にも、ターミナルから手っ取り早く ./swift/utils/build-script -X
を実行することでも大丈夫な様子でした。この場合、最後にビルドエラーで終わりますけど、この時 This Xcode project is configured for IDE use only and cannot build Swift.
というメッセージが表示されるので、これは Xcode で Swift をビルドしないように敢えて処理を止めている様子が窺えます。
cmark 周りを整える
Xcode から必要なファイルを揃える方法は、まずは Swift ではなく cmark-macosx-x86_64
を開きます。
そうすると中に cmark.xcodeproj
という Xcode プロジェクトファイルがあるのでこれを開きます。
そうすると最初に開いた1回だけ Autocreate Schemes
というダイアログメッセージが表示されるので、ここでは
を押して作っておきます。
これで cmark プロジェクトが開かれました。
そうしたら ALL_BUILD
スキームを選択してビルドを行います。
こうすることで cmark のプロジェクトがビルドされました。
具体的には、この操作を行うことで build/Xcode-DebugAssert/cmark-macosx-x86_64/CMakeScripts/
内のさまざまな Makefile が実行される様子でした。
llvm 周りを整える
そうすると、もうひとつの llvm-macosx-x86_64
内の Xcode プロジェクトがビルドできるようになるみたいなので、それを開きます。
そして ALL_BUILD
スキームを選択してビルドを行うことで、最初の手順だけでは揃わなかった幾つかのファイルが自動的に生成される様子でした。
具体的には、たとえば build/Xcode-DebugAssert/llvm-macosx-x86_64/include/llvm/IR/CMakeScripts/intrinsics_gen_cmakeRulesBuildPhase.makeDebug
といった Makefile を使って llvm/include/llvm/IR/Intrinsics.td
から llvm/IR/Intrinsics.gen
を生成する、みたいなことが行われるようです。
準備完了
これで Xcode を使って Swift のソースコードを Xcode で眺める準備がきっと整いました。
Xcode での Swift 自体のビルドは今は制限がかけられているので、もしかするとまだ足りないファイルがあるかもしれませんけど、もしそれが必要になったときはターミナルから Swift を完全ビルドすれば生成されるはずです。
ソースコードの場所
今回の作業によって build
フォルダーに Xcode-DebugAssert
というフォルダーが出来上がってそこに Xcode プロジェクトが生成されたわけですけれど、ソースコード自体はそこに写されたわけでないようです。
Xcode で開けるソースコードは、もともとの swift
フォルダーとか llvm
フォルダーとかに保存されているものをリファレンス参照でプロジェクト内に登録されている様子でした。
静的ライブラリについての余談
また Xcode でも libswiftSILGen.a
など、幾つかの静的ライブラリはビルドできるようなので、それをビルドしたいようなときにも便利に使えるかもしれません。
なお、どこかのプロジェクトでそんな静的ライブラリを取り込みたいようなときは、ざっくり調べる限りでは Library Search Paths
で次のパスを参照できるようにしておくと良さそうでした。
build/Xcode-DebugAssert/swift-macosx-x86_64/$(CONFIGURATION)/lib/
また、ヘッダーファイルは使いたいものによって場所が様々ですけど、例えば swift/include
とか llbuild/include
とか swift/tools/SourceKit/lib
みたいなように、必要に応じてそんなあたりを Header Search Paths
に登録しておくと上手く探せそうな感じがしました。