web-dev-qa-db-ja.com

アプリケーションにVisual C ++再頒布可能パッケージが必要な理由

私は簡単なC++ Visual Studioのアプリケーション。セットアッププロジェクトもあります。私の開発マシンではうまく機能しますが、ユーザーのマシンにこのアプリケーションをインストールする場合、Visual C++ Redistributable Package。私のアプリケーションがC++ Redistributable?標準C++ランタイムライブラリはWindowsに同梱されています。

46
JeB

onlyバージョンのCランタイムライブラリは、32ビットWindowsバージョンのほとんどでMicrosoftに同梱されており、msvcrt.dllです。このライブラリは、CおよびC++プログラムに必要なライブラリ関数の典型的なセットを提供します。これらには、文字列操作、メモリ割り当て、Cスタイルの入出力呼び出しなどが含まれます。

Visual Studio 6.0のコンパイラはこのライブラリにリンクしているため、VS 6.0で開発している場合、ほとんどのユーザーのマシンで問題が発生することはありません。

ただし、VS 2005、VS 2008、VS 2010、VS 2012、VS 2013、またはVS 2015で開発している場合、アプリケーションとともに追加のCランタイムライブラリを配布する必要があります。これは、Windowsに同梱されていないmsvcrt80.dllmsvcrt90.dllmsvcrt100.dllmsvcrt110.dllmsvcrt120.dllmsvcrt140.dllに対してコンパイラがリンクしているためです。 。

ソリューション:

  1. 考えられる解決策は、ランタイムライブラリと静的にリンクすることですが、アプリケーションに.exe.dllの両方がある場合、多くの問題を引き起こす可能性があります。 それをしないでください

    具体的には、 this answerの一部を引用できるようにします。

    DLLとEXEを作成する場合、/ MTの使用は危険です。プログラムでCRTの複数のコピーが作成されます。これは、VSのそれほど多くではなく、各CRTが独自のヒープを取得するVSの以前のバージョンでは特に問題でした。ただし、たとえば、「errno」変数が複数ある場合、実行時に問題が発生する可能性があります。このような損失を回避するために、/ MDを使用することを強くお勧めします。

  2. 別の解決策として、適切なMicrosoft Visual C++再頒布可能パッケージをユーザーのマシンにインストールする必要があります。

    セットアッププロジェクトの前提条件プロパティでこの要件を指定することで実行できます。

  3. また、適切な「 merge module 」をセットアッププロジェクトに含めることで、ランタイムdllを配布できます。この場合、適切な「ポリシーマージモジュール」を追加して、誤ったランタイムバージョンによって引き起こされるエラーを回避することを忘れないでください。

  4. 最後に、必要なDLLを、アプリケーションがインストールされているフォルダーと同じフォルダーに配置するだけです。

参考文献:

53
JeB

いくつかのコメントは「ランタイムライブラリと静的にリンクしますが、アプリケーションに.exeと.dllの両方がある場合、多くの問題を引き起こす可能性があります」と言っていますが、これは正しくありません。まず、DLLを静的にリンクしません! OBJとLIBを静的にリンクします。 LIBは静的ライブラリです。 DLLは動的ライブラリであり、LIB(静的)またはDLL(動的)の使用を選択できます。選ぶのはあなた次第です。唯一の欠点(DLLファン))は、1つのライブラリを更新する場合、コンパイルとリンクを再度行う必要があるということです。私が開発したソフトウェアは100%移植性があり(プリインストーラー時代の一般的な手順でしたが)、最終ユーザーは1つのフォルダーから別のフォルダー、または別のフォルダーに簡単にコピーできます。ハードドライブからフラッシュドライブへ(またはその逆)エラーメッセージ"DLLが見つかりません。"単に存在しません...決して。

一部の人々は、静的リンクを玩具ソフトウェアと考えています:間違っています! DBMS(Oracle、SQL Serverなど)または他の種類のアプリケーションに接続するフル機能のアプリケーションを作成できます。

7
user4377425