読者です 読者をやめる 読者になる 読者になる

プログラミングメモ

ソフトウェア開発に関する技術メモ。

「サイド バイ サイド構成が正しくないため、アプリケーションを開始できませんでした。」

作成したアプリケーション(.exe)を、開発環境とは別のマシンで起動させたら、以下のメッセージが表示された。この場合の調査方法について。

  • ダイアログボックス

このアプリケーションのサイド バイ サイド構成が正しくないため、アプリケーションを開始できませんでした。詳細については、アプリケーションのイベントログを参照してください。

  • イベントログ (アプリケーション)

"C:\foo\bar.exe" のアクティブ化コンテキストの生成に失敗しました。
従属アセンブリ Microsoft.VC80.CRT,processorArchitecture="x86",
publicKeyToken="1fc8b3b9a1e18e3b",type="win32",version="8.0.50727.4053"
が見つかりませんでした。 詳細な診断を行うには sxstrace.exe を実行してください。

サイドバイサイド アセンブリ(side-by-side assembly)

DLL, COM, Windowクラス, type libraries(??), interfaces(??)のグループ。

個々のサイドバイサイドアセンブリには名前とバージョンが付いている。
アプリケーションは自分が必要とするサイドバイサイドアセンブリの名前、バージョンを、そのアプリケーションの「マニフェスト(manifest)」に書いておくと、アプリケーション実行時にそのサイドバイサイドアセンブリがOSによって読み込まれる。

マニフェストは、サイドバイサイドアセンブリも持っており、そこにはサイドバイサイドアセンブリを構成するファイルや、サイドバイサイドアセンブリの依存関係が記述されている。




問題のexeでどのアセンブリ(ライブラリ)を必要としているのか?

マニフェストは.exeに埋め込まれている場合と、.exeと同じフォルダに〜.exe.manifestという名前で存在する場合とがある。マニフェストXMLで記述されており、後者の場合はエディタで参照できる。

前者の場合のマニフェストの確認方法:

  • Visual Studioの[ファイル]-[ファイルを開く]で問題のexeを選択。exeのリソースが表示される。
  • リソースの[RT_MANIFEST] の 「1[英語(米国)]」を選択して表示。(exeでなくてDLLの場合は1ではなく2になる?)

マニフェストは以下のような内容。

<assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
  <dependency>
    <dependentAssembly>
      <assemblyIdentity type="win32" name="Microsoft.VC80.CRT" version="8.0.50727.762" processorArchitecture="x86" publicKeyToken="1fc8b3b9a1e18e3b"></assemblyIdentity>
    </dependentAssembly>
  </dependency>
</assembly>

この例の場合、x86用のMicrosoft.VC80.CRTのバージョン8.0.50727.762が必要だと言っている。

そのサイドバイサイドアセンブリは、問題が発生したマシンに存在するのか?

上記の例の場合、以下のファイルがあるか確認。

C:\Windows\WinSxS\Manifests\
x86_microsoft.vc80.crt_1fc8b3b9a1e18e3b_8.0.50727.762_
none_10b2f55f9bffb8f8.manifest

  ※「1fc8b3b9a1e18e3b」の部分はマニフェストのpublicKeyTokenと一致している模様
  ※「none_10b2f55f9bffb8f8」の部分は規則が不明。

このファイルが無ければマシンに存在しないと判断してよさそう。

別のバージョンのアセンブリで置き換えるように「リダイレクト」する仕組みもあるらしい。この場合、リダイレクト先は以下のファイルで設定されるらしい。

C:\Windows\WinSxS\Policies\x86_policy.8.0.Microsoft.VC80.CRT_
1fc8b3b9a1e18e3b_????\8.0.50727.762.policy

マシンに存在しなかった場合の対処

インストーラを作成する以外の解決方法について。

Visual C++ 再頒布可能パッケージをインストール (必要なサイドバイサイドアセンブリがCランタイムライブラリの場合)

MSDN 配置方法の選択

.exeと同じフォルダに置く(プライベート アセンブリとしての配置)

MSDN 方法:XCopyを使用して配置する

静的にリンクする

Cランタイムライブラリについては、プロジェクトのプロパティの[C/C++]-[コード生成]-[ランタイムライブラリ]で(/MDの代わりに)/MTを選ぶ。

要求するバージョンを下げる? (問題のマシンにそのサイドバイサイドアセンブリはあるが、より古いバージョンしか存在しない場合)

マニフェストはexeのビルド時にVisual Studioによって自動生成されるが、その環境で利用可能な最新のバージョンのサイドバイサイドアセンブリを要求するようにマニフェストが生成されているように見える。このため、より古いバージョンのサイドバイサイドアセンブリしかインストールされていない環境にそのexeを持っていくと、冒頭のエラーメッセージが出る。要求するバージョンを下げれば問題は解決するが、その標準的な方法が不明。ひとつの方法としては、マニフェストを〜.exe.manifestに外出しにし、テキストエディタで書き換えればよい。