1. はじめに
私は、今まで主にファームウェア(時々Windows)の世界の住人で、最近FOSSの世界に飛び込みました。そして、dllが苦手です。単純なので静的リンクしたい人なのです。
そんな私が最近Qtを始めたのですが、公開されているQtのバイナリーは動的リンクでした。そこで、FOSSに慣れるついでに静的リンクのQt開発環境を用意しようと、ここの手順をベースにしてQtをビルドしました。
結果、うまいことできましたので、記憶が新しいうちにビルド手順をまとめてみました。
長くなりすぎたので2つに分けてます。
前のエントリーでQt5.4.0を準備してHallo Worldするところまで書きました。
このエントリーでQt5.4.0をビルドするところを書きます。
3. Qt5.4.0 64bitのビルド
3.1 必要なソフトウェアをインストールする
ソフトウェア | ダウンロードするファイル | インストール方法 |
---|---|---|
MinGW-w64 4.9.1 rev2 | x86_64-4.9.1-release-posix-seh-rt_v3-rev2.7z | N:\Qt\Toolsへ解凍後、mingw64フォルダをmingw491_64へリネーム |
QtBinPatcher 2.1.1 64bit | qtbinpatcher-2.1.1-win-x64.zip | N:\Qt\Tools\QtBinPatcherへ解凍 |
DirectX 9 SDK | DXSDK_Jun10.exe | DXSDK_Jun10.exeを起動。"Help Improve the DirectX SDK"はお好みで。他はデフォルトのまま。 |
ActivePerl 5.20.1(64bit) | ActivePerl-5.20.1.2000-MSWin32-x64-298557.msi | ActivePerl-5.20.1.2000-MSWin32-x64-298557.msiをインストール。オプションはデフォルトのまま。 |
Python 2.7.8 | python-2.7.8.msi | python-2.7.8.msiをインストール。"Add phthon.exe to Path"を選択する。他はデフォルトのまま。 |
全てインストール後、環境変数を反映するためPCを再起動します。
3.2 Qtのソースをダウンロードする
ここを参考にして、日本Qtユーザー会にあるQt5のリポジトリ(本家のミラー)をローカルへクローンし、Qt5.4.0をチェックアウトしました。
コマンド・プロンプトを起動してN:へ移動し、下記の手順で行います。
- cd \Qt5
- git clone git://git.qt-users.jp/qt/qt5.git qt5
- cd qt5
- git checkout 5.4.0
- perl init-repository --mirror git://git.qt-users.jp/
3.3 Qt5.4.0の動的リンク版をビルドする
下記コマンドにより、ビルドを構成(step 4.)し、ビルド(step 5.)します。フォルダ構成は1.3を想定しています。
- set PATH=N:\Qt\Tools\mingw491_64\bin;%PATH%
- set PATH=N:\Qt\Tools\QtCreator\bin;%PATH%
- cd \Qt5\Qt540x64g491shared
-
..\qt5\configure -developer-build -opensource -nomake examples -nomake tests
この時、"Do you accept the terms of the license?"と聞かれるので、"y"と答えます。 - jom
step 5.ではmingw32-makeでも可能ですが、jomを使った方が高速にビルドできます。(赤い彗星より速いですぞ。) Core™ i7-3820 3.60 GHzのパソコンで、mingw32-makeは約4時間かかりましたがjomなら約1時間でした。
jom.exeは、2.1のようにインストールするとN:\Qt\Tools\QtCreator\binに入ってます。
3.4 ビルドしたQt開発環境をインストールする
下記コマンドで、Qt開発環境として必要なファイルをN:\QtInstall\Qt5\qt-5.4.0-x64-mingw482r4-seh-sharedへ集めることができます。
- set PATH=N:\Qt\Tools\mingw491_64\bin;%PATH%
- set PATH=N:\Qt\Tools\QtCreator\bin;%PATH%
- set PATH=N:\Qt\Tools\QtBinPatcher;%PATH%
- set INSTALL_ROOT=\QtInstall
- cd \Qt5\Qt540x64g491shared
- jom install
- cd \QtInstall\Qt5\Qt540x64g491shared\qtbase
- qtbinpatcher
この手順はオプションです。ビルド・フォルダのQtを直接使うこともできます。
インストールを行うことでビルド環境から切り離されたQt開発環境を作れるので、ソースをスイッチしたりビルド・フォルダを削除したりしてもQtアプリを開発できることがメリットです。
3.5 QtCreatorとプロジェクトに設定し、Hello World
-
[ツール(T)]
→[オプション(O)...]
をクリックし[ビルドと実行]
を選択し、[Qt バージョン]
、[コンパイラ]
、[デバッガ]
の各タブを選択して[追加ボタン]
を押し、下表のように設定します。(名前は適当で良いです。)
タブ | 名前 | 設定 |
---|---|---|
コンパイラ | MinGW 4.9.1 64bit | N:\Qt\Tools\mingw491_64\bin\g++.exe |
デバッガ | MinGW 4.9.1 64bit | N:\Qt\Tools\mingw491_64\bin\gdb.exe |
Qt バージョン | Qt540x64g491shared | N:\Qt5Install\Qt5\Qt540x64g491shared\qtbase\bin\qmake.exe |
(もし、ビルド・フォルダのQtを直接使う場合は、Qt バージョンにN:\Qt5\Qt540x64g491shared\qtbase\bin\qmake.exeを指定して下さい。) |
-
[キット]
のタブを選択して[追加ボタン]
を押し、下表のように設定します。
欄 | 設定 |
---|---|
コンパイラ | MinGW 4.9.1 64bit |
デバッガ | MinGW 4.9.1 64bit |
Qt バージョン | Qt540x64g491shared |
以下はキットを設定した時の画面です。
- 64bit 動的リンクしたいプロジェクトにこのキットを追加して使います。
下は昨日のHello Worldプロジェクトへキットを追加しようとしている画面です。
- 最後に緑の三角ボタンを押してビルドし起動します。
Hello Worldが表示されれば勝ちです。Congratulations!!
3.6 Qt5.4.0の静的リンク版をビルドする
ちょっと工夫しないとgccのライブラリが動的リンクになります。
ここでは、gccのライブラリも含めて静的リンクする手順を説明します。
ここで説明する方法はmkspecsにフォルダを追加します。
この程度のことでmkspecsを増やすのはよくないようにも感じます。
Qtを静的リンクさせる時は常にgccのライブラリも静的リンクさせたかったのでこのようにしてみました。より適切な方法をご存知の方がいたら、是非教えて下さい。
まず、win32-g++staticをqt5へ追加します。
N:\Qt5\qt5\qtbase\mkspecs\win32-g++をまるごと、N:\Qt5\qt5\qtbase\mkspecs\win32-g++staticへコピーし、qmake.confファイルのQMAKE_LFLAGSを設定している行を次のように修正します。(gccのライブラリを静的リンクする指定です。)
QMAKE_LFLAGS = -static -static-libgcc -static-libstdc++
次に、ビルドを構成し、ビルドします。
手順は3.3とほぼ同じです。ビルド・フォルダとconfigureのパラメータに-staticが追加されている点が異なります。(step 3.とstep 4.が次のように変わります。step 5.jomの実行をお忘れなく。)
3. cd \Qt5\Qt540x64g491static
4. ..\qt5\configure -static -developer-build -opensource -nomake examples -nomake tests
3.7 ビルドしたQt開発環境をインストールする
手順は3.4とほぼ同じです。ビルド・フォルダに静的リンク版を指定します。(step 5.とstep 7.が次のように変わります。他の手順の実行もお忘れなく。)
5. cd \Qt5\Qt540x64g491static
7. cd \QtInstall\Qt5\Qt540x64g491static\qtbase
3.4と同じくこの手順もオプションです。
ただし、gccのライブラリを静的リンクしたい場合は、手順が少し変わります。
win32-g++staticをN:\Qt5\qt5\qtbase\mkspecs\win32-g++staticではなく、N:\Qt5\Qt540x64g491static\qtbase\mkspecs\win32-g++staticへ作ります。
また、N:\Qt5\qt5\qtbase\mkspecs\commonをまるごとN:\Qt5\Qt540x64g491static\qtbase\mkspecs\commonへコピーします。
これでgccライブラリを静的リンクできました。
3.8 QtCreatorとプロジェクトに設定し、Hello World
- 3.5と同様の手順で下記設定を行います。
タブ | 名前 | 設定 |
---|---|---|
Qt バージョン | Qt540x64g491static | N:\Qt5Install\Qt5\Qt540x64g491static\qtbase\bin\qmake.exe |
この時、「qmlsceneがインストールされていません。」という警告が表示されます。 | ||
Qtのソースを確認すると、N:\Qt5\qt5\qtdeclarative\tools\tools.proで静的リンクの時はqmlsceneをビルドしないように設定されています。Qtは静的リンクの時qmlsceneを意図的にビルドしていないようですので、このままにしておきます。 |
- 3.5と同様の手順でキット設定を行います。
欄 | 設定 |
---|---|
コンパイラ | MinGW 4.9.1 64bit |
デバッガ | MinGW 4.9.1 64bit |
Qt バージョン | Qt540x64g491static |
Qt mkspec | win32-g++static |
ここではキットに警告マークがつきます。キット名をポイントすると「コンパイラ・・・はQt バージョン・・・と互換性のあるコードを生成しない可能性があります。」との警告が表示されます。ABIの一部が異なっているようです。コンパイラはmsys、Qt バーションはunknownになってます。静的リンクなのでmsysは関係ない筈(違ったらごめん)なので、このままにしておきます。 |
なお、Qt mkspec欄を空欄にしておけば、gccライブラリは動的リンクされます。
- 64bit 静的リンクしたいプロジェクトにこのキットを追加します。
- 今度はトンカチマークを押してビルドします。
- そして、ビルド・フォルダのreleaseかdebugの下にできているHelloWorld.exeを起動します。
Hello Worldが表示されれば成功です。おめでとう!!
動的リンクでは約37MBytesだったのが、約25MBytesに減っています。\(^o^)/
4. おまけ(バッチ・ファイル)
GitHubのここにバッチ・ファイル群のリボジトリを登録しました。(リモート・リポジトリを使ってみたかったのですよ。)
内容はここまで説明してきた通りです。(ログ保存や多少のエラー対策を追加してます)
チェックアウトしたQt5フォルダごとN:\Qt5フォルダへ上書きコピーしてインストールします。
- N:\Qt5\Qt540x64g491shared等のビルド・フォルダにあるバッチ・ファイル
ビルド用のバッチ・ファイルです。
z_config.bat, z_build.bat, z_install.batの3つがあります。それぞれ名前の通りの処理を行います。(zは超合金の証です。キリッ) - toolsにあるバッチ・ファイル
- Clean.bat : ワーキングコピーの掃除後、tools\win32-g++staticを3.6の場所へコピーします。
- AllBuild.bat : 上記の動的リンクと静的リンクのQtの構成とビルドとインストールを連続実行します。なお、最初にClean.batを呼んでいますので、ご注意下さい。
また、tools内の他のバッチ・ファイルは直接呼び出さないで下さい。
なお、ドライブはN:でなくても全て同じドライブに入れておけば動作する筈です。\Qtと\QtInstallのフォルダ名を変更する時はバッチ・ファイルの修正が必要になります。\Qt5フォルダ名は恐らく変更しても大丈夫です。
5. インストール手順について
ここで書いたインストール手順ですが、Qt Projectの公式手順を見つける前にあれこれやっていて、見つけた方法です。(エヘッ)
jom installでファイルは集まるのですが、QtCreatorへの登録がうまく行かず、探している内にここの情報でqmake.exeに絶対パスが入っていてqmake -queryで見れることが判りました。早速、ダウンロードしたQtのqmake.exeでやってみると、確かにインストールしたパスが入っています! ということは、インストール中になんらかの方法で書き換えている筈なのです。
どんなツールなのか見つけるために、後述のqt-5.3.2-x64-mingw491r1-seh.exeをインストール中にタスクマネージャを睨んで見つけたのが、qtbinpatcherです。後は、グーグル先生に教えてもらってここを見つけました。
jom install自体はインストール・ファイルを集める公式手順ですし、QtBinPatcherはQt-x64で使われているツールですので、このインストール手順で間違いはないと思いますが、問題が潜んでいる可能性は有ります。ご用心あれ。
6. あとがき
実は、当初は安定版のQt5.3.2をターゲットにして、qt-5.3.2-x64-mingw491r1-seh.exeをインストールしたのですが、それでビルドしたQtQuickアプリは起動直後にクラッシュします。
QtQuickやQMLなどでグーグル先生にしつこくシツコク聞いてみたのですが解決のヒントが見つかりませんでした。32bit版では起きないし、qt-5.3.1-x64-mingw482r4-seh.exeでもおきないことが分かったのですが、相変わらずヒントが見つからないのです。
諦めて、先にQtをビルドできるようにしてから、Qtのソース・コードにデバッグ文を入れて追いかけたところ、下記現象が発生していました。
- qtbaseのsrc\3rdparty\angleの奥深くにあるShaderLnag.cppのShCompile()関数から、Compiler.cppのTCompiler::compile()を呼び出している。
- Compiler.cppのTCompiler::compile()は最後まで実行されるのだが、呼出元に戻らない。エーッ!
どうもスタックが壊れている様子です。ソンナバカナ!
ANGLEが関係していることが分かったのでangleprojectへ行って、あれこれ検索してここが見つかりました。このパッチをQtのソースに施すと、Qt 5.3.2でもQtQuickが落ちなくなりました!!
おっ、もしかするといきなり貢献できるかもっ? はりきってQt Bug Trackerへバグレポートしようとガイドラインに沿って準備している過程でここを見つけました。Qt5.4.0で既に修正されていました。(チッ)
でも、この活動を通じてFOSSにちょっと慣れたさっ!
7. 謝辞
Qt Projectの方々、および、各ビルドツールを提供されている方々、こんなに素晴らしいものを自由に使わせて頂け、最高の感謝を。ありがとう!そして、ありがとう!
また、日本Qtユーザー会の皆さん、[Qt のあれこれ (仮)]の朝木卓見さん、[理ろぐ]の理音 伊織さん、[Qt 5 の未来は明るいブログ]のTasuku Suzukiさん、および、Qt情報を日本語で公開されている方々、誠にありがとうございます。お陰様で安心して進めることができました。(やっぱ日本語の方がよく解るとですよ~。)
そして、最後までお付き合い頂いたあなたに。ありがとうございました。m(__)m
明日はmogurisoさんのQt for Tizenのビルド+αです。Tizenってなんだろう? ワクワクですっ。