Skip to content

iOSシミュレーターと実機のアーキテクチャ競合エラーの解決方法

問題の概要

Xcode 12以降でプロジェクトをビルドする際、以下のエラーが発生することがあります:

building for iOS Simulator, but linking in object file built for iOS, for architecture 'arm64'

このエラーは、iOSシミュレーター用にビルドしているにもかかわらず、iOS実機用(arm64アーキテクチャ)でビルドされたオブジェクトファイルがリンクされていることを示しています。特に、以下の状況で発生しやすいです:

  • Apple Silicon(M1/M2チップ)搭載Macでの開発
  • レガシーなサードパーティライブラリの使用
  • CocoaPodsを使用したプロジェクト
  • 混在言語プロジェクト(Objective-CとSwiftの両方を含む)

根本原因の理解

プラットフォームとアーキテクチャ

iOS開発では、2つの主要なプラットフォームとアーキテクチャの組み合わせがあります:

  • iOS実機プラットフォーム (generic/platform=iOS)
    • arm64アーキテクチャ
  • iOSシミュレータープラットフォーム (generic/platform=iOS Simulator)
    • Intel Mac: x86_64アーキテクチャ
    • Apple Silicon Mac: arm64アーキテクチャ

デバッグビルドとリリースビルドの違い

  • デバッグビルド: 開発速度優先のため、選択したターゲットのプラットフォームとアーキテクチャのみビルド
  • リリースビルド: 完全な正確性を優先し、すべてのプラットフォームとアーキテクチャの組み合わせをビルド

解決方法

方法1: ベンダーに更新を依頼(推奨)

サードパーティライブラリが原因の場合、以下の手順を推奨します:

bash
# 1. ライブラリのベンダーにApple Silicon対応のXCFrameworkを依頼
# 2. ソースコードがある場合は、XCFrameworkとして再ビルド

XCFrameworkの作成方法:

bash
xcodebuild -create-xcframework \
  -framework ./ios-arm64/MyFramework.framework \
  -framework ./ios-arm64_x86_64-simulator/MyFramework.framework \
  -output ./MyFramework.xcframework

方法2: 一時的な回避策

ベンダーからの更新がすぐに得られない場合の一時的な対処法:

プロジェクト設定の変更

  1. ターゲットのビルド設定で以下を設定:
    • Build Active Architecture OnlyYES(デバッグ時)
    • Excluded ArchitecturesAny iOS Simulator SDKarm64を追加

Excluded Architectures設定

Podfileの変更

ruby
# Podfileの最後に追加
post_install do |installer|
  installer.pods_project.build_configurations.each do |config|
    config.build_settings["EXCLUDED_ARCHS[sdk=iphonesimulator*]"] = "arm64"
  end
end

WARNING

注意:この方法は一時的な回避策です。Apple Silicon搭載MacでRosettaなしのシミュレーター実行ができなくなります。

方法3: Rosettaシミュレーターの使用

Apple Silicon Macで一時的に問題を回避する方法:

  1. Product → Destination → Destination Architectures → Show Bothを選択
  2. Rosetta対応のシミュレーターを選択して実行

Rosettaシミュレーターの選択

方法4: 手動でのアーキテクチャ変換

事前コンパイル済みフレームワークがある場合:

  1. XCFrameworkConverterを使用
  2. 以下のコマンドで変換:
bash
# インストール
brew install xcframework-converter

# 変換実行
xcframework-converter --input LegacyFramework.framework --output ConvertedFramework.xcframework

ベストプラクティス

アーキテクチャの確認方法

bash
# バイナリのアーキテクチャ確認
lipo -info /path/to/framework/binary

# 詳細な情報確認(推奨)
dyld_info /path/to/framework/binary

XCFrameworkの構造理解

正常なXCFrameworkの構造:

MyFramework.xcframework/
├── Info.plist
├── ios-arm64/
│   └── MyFramework.framework
└── ios-arm64_x86_64-simulator/
    └── MyFramework.framework

トラブルシューティング

クリーンビルドの実行

設定変更後は必ずクリーンビルドを実行:

  • Product → Clean Build Folder (⌘ + ⇧ + K)

全てのターゲットを確認

エラーが解消しない場合、以下の全ての設定を確認:

  • メインプロジェクトターゲット
  • Podプロジェクトターゲット
  • 個々のPodターゲット

Podsプロジェクトの設定確認

デプロイメントターゲットの調整

ruby
# Podfileに追加
post_install do |installer|
  installer.pods_project.targets.each do |target|
    target.build_configurations.each do |config|
      config.build_settings.delete 'IPHONEOS_DEPLOYMENT_TARGET'
    end
  end
end

結論

iOSシミュレーターと実機のアーキテクチャ競合問題は、Apple Silicon搭載Macの登場により顕在化しました。長期的な解決策は、サードパーティライブラリをXCFramework形式に更新することです。一時的な回避策としてアーキテクチャの除外やRosettaの使用がありますが、これらは本来の解決策ではないことに注意してください。

プロジェクトの互換性を確保するためには、全ての依存関係のアーキテクチャサポート状況を定期的に確認し、最新の開発環境に適応させることを推奨します。