「CMake パッケージガイドライン」の版間の差分

提供: ArchWiki
ナビゲーションに移動 検索に移動
(英語版から転載)
 
(→‎ヒントとヒントとテクニック‎: ビルド中の FetchContent のダウンロードを回避を翻訳して追加)
 
(同じ利用者による、間の13版が非表示)
5行目: 5行目:
 
{{Package Guidelines}}
 
{{Package Guidelines}}
   
  +
この文書は {{Pkg|cmake}} を使うソフトウェアの [[PKGBUILD]] を書くための標準とガイドラインをカバーしています。
This document covers standards and guidelines on writing [[PKGBUILD]]s for software that uses {{Pkg|cmake}}.
 
   
== Introduction ==
+
== はじめに ==
   
From the [https://cmake.org CMake web page]:
+
[https://cmake.org CMake web page] より
   
  +
CMake は、ソフトウェアをビルド、テスト、パッケージ化するために設計された、オープンソースでクロスプラットフォームのツールファミリーです。CMake は、プラットフォームやコンパイラに依存しないシンプルな設定ファイルを使ってソフトウェアのコンパイルプロセスを制御し、選択したコンパイラ環境で使用できるネイティブな makefile と workspaces を生成するために使用されます。
:CMake is an open-source, cross-platform family of tools designed to build, test and package software. CMake is used to control the software compilation process using simple platform and compiler independent configuration files, and generate native makefiles and workspaces that can be used in the compiler environment of your choice.
 
   
=== Typical usage ===
+
=== 典型的な使用方法 ===
   
  +
典型的な使い方は、{{ic|cmake}} コマンドを実行し、その後に building コマンドを実行することです。{{ic|cmake}} コマンドは通常、いくつかのパラメータを設定し、必要な依存関係をチェックしてビルドファイルを作成し、ソフトウェアを {{ic|make}} や {{ic|ninja}} といった他のツールでビルドできる状態にします。
The typical usage consists of running the {{ic|cmake}} command and after that execute the building command. The {{ic|cmake}} command usually sets some parameters, checks for the needed dependencies and creates the build files, letting the software ready to be built by other tools like {{ic|make}} and {{ic|ninja}}.
 
   
== CMake undesired behaviors ==
+
== CMakeの好ましくない動作について ==
   
  +
ビルドファイルを生成するための内部特性により、CMake が好ましくない動作をすることがあります。そのため、CMake ベースのソフトウェアのために [[PKGBUILD]] を書くときにはいくつかのステップに注意する必要があります。
Due to its own internal characteristics for generating the build files, sometimes CMake can behave in undesired ways. Being such, some steps should be noted when writing [[PKGBUILD]]s for CMake-based software.
 
   
  +
=== CMake はデフォルトのコンパイラ最適化フラグを自動的にオーバーライドすることがあります ===
=== CMake can automatically override the default compiler optimization flag ===
 
   
  +
CMake を {{ic|1=-DCMAKE_BUILD_TYPE=Release}} オプション付きで動かしている人をよく見かけます。上流のプロジェクトでは、ビルド手順にこのオプションをうっかり入れてしまうこともありますが、これは望ましくない振る舞いを生み出します。
It is very common to see people running CMake with the {{ic|1=-DCMAKE_BUILD_TYPE=Release}} option. Some upstream projects even inadvertently include this option in their building instructions, but this produces an undesired behavior.
 
   
Each build type causes CMake to automatically append a set of flags to {{ic|CFLAGS}} and {{ic|CXXFLAGS}}. When using the common {{ic|Release}} build type, it automatically appends the {{ic|-O3}}[https://github.com/Kitware/CMake/blob/v3.17.0/Modules/Compiler/GNU.cmake#L58] compiler optimization flag, and this overrides the default Arch Linux flag which currently is {{ic|-O2}} (defined in the [[Makepkg#Configuration|makepkg configuration file]]). This is undesired, as it deviates from the Arch Linux targeted optimization level.
+
それぞれのビルドタイプは CMake に自動的に {{ic|CFLAGS}} {{ic|CXXFLAGS}} にフラグのセットを追加させます。一般的な {{ic|Release}} ビルドタイプを使うときは、自動的に {{ic|-O3}} [https://github.com/Kitware/CMake/blob/v3.17.0/Modules/Compiler/GNU.cmake#L58] コンパイラ最適化フラグを追加し、これは現在 Arch Linux のデフォルトフラグである {{ic|-O2}} よりも優先されます。(設定ファイル [[Makepkg#Configuration|makepkg configuration file]] で定義されています) これは Arch Linux が目標とする最適化レベルから逸脱しているので望ましくありません。
   
==== Notes about {{ic|-O3}} ====
+
==== {{ic|-O3}} に関する注意事項 ====
   
  +
{{ic|-O3}} を使用したからといって、ソフトウェアのパフォーマンスが向上することを保証するものではなく、時にはプログラムの動作が遅くなることもあります。また、状況によってはソフトウェアを壊してしまうこともあります。Arch Linux の開発者がターゲット最適化レベルとして {{ic|-O2}} を選択したのには理由があり、私たちはそれに従うべきでしょう。あなたが何をしているかを正確に分かっている場合、またはアップストリームが {{ic|-O3}} が必要であると明示的・暗示的に言っている場合以外は、私たちのパッケージで使用するのは避けるべきです。
Using {{ic|-O3}} does not guarantee that the software will perform better, and sometimes it can even slow down the program. It can also break software in some situations. There is a good reason why the Arch Linux developers choose {{ic|-O2}} as the target optimization level and we should stick with it. Unless you know exactly what you are doing, or if upstream explicitly tells or implies that {{ic|-O3}} is needed, we should avoid using it in our packages.
 
   
  +
==== 自動最適化フラグオーバーライドの修正 ====
==== Fixing the automatic optimization flag override ====
 
   
  +
100%保証された方法で修正することは、CMake の柔軟性により、簡単な問題ではありません。すべてのケースに適用できる標準的な解決策は存在しないことに注意してください。ここでは、考えられる解決策と、守るべきポイントについて説明します。
Fixing this in a 100% guaranteed way is not a simple question due to CMake flexibility. Please note that there is no standard solution that can be applied to all cases. This section will discuss possible solutions and some points that should be observed.
 
   
  +
CMake のデフォルトのビルドタイプは {{ic|None}} であり、デフォルトでは {{ic|CFLAGS}} と {{ic|CXXFLAGS}} にフラグを付加しないため、 {{ic|CMAKE_BUILD_TYPE}} オプションを使用しないだけでもデフォルトが {{ic|None}} となり動作することがあります。しかし、多くのソフトウェアプロジェクトでは、ビルドタイプを自動的に {{ic|Release}} に設定するため、このオプションを省略しても問題が解決する保証はないことに注意してください。コマンドラインで {{ic|CMAKE_BUILD_TYPE}} が設定されていない場合、CMake ファイルで (または他のタイプで) 設定します。
The default CMake build type is {{ic|None}} and it does not append any flags to {{ic|CFLAGS}} and {{ic|CXXFLAGS}} by default, so simply omitting the usage of the {{ic|CMAKE_BUILD_TYPE}} option can work as it will default to {{ic|None}}. But note that omitting this option is not guaranteed to fix the problem, as many software projects automatically set the build type to {{ic|Release}} (or other type) in the CMake files if {{ic|CMAKE_BUILD_TYPE}} is not set at command line.
 
   
Since the default {{ic|None}} build type does not append any flags to {{ic|CFLAGS}} and {{ic|CXXFLAGS}} by default, using the {{ic|1=-DCMAKE_BUILD_TYPE=None}} option can also work. Generally speaking, using the {{ic|1=-DCMAKE_BUILD_TYPE=None}} option is better than omitting the usage of {{ic|CMAKE_BUILD_TYPE}}. It will cover the case when upstream automatically sets the build type to {{ic|Release}} when {{ic|CMAKE_BUILD_TYPE}} is omitted, it will not append any flags by default and it is uncommon to see software setting undesired flags for the {{ic|None}} build type.
+
デフォルトの {{ic|None}} ビルドタイプは {{ic|CFLAGS}} {{ic|CXXFLAGS}} にフラグを付加しないので、 {{ic|1=-DCMAKE_BUILD_TYPE=None}} オプションも使用可能です。一般的には {{ic|1=-DCMAKE_BUILD_TYPE=None}} オプションを使う方が {{ic|CMAKE_BUILD_TYPE}} を省略するよりも良いと言われています。これは {{ic|CMAKE_BUILD_TYPE}} が省略されたときにアップストリームが自動的にビルドタイプを {{ic|Release}} に設定する場合をカバーするもので、デフォルトではフラグは付加されず、ビルドタイプ {{ic|None}} に好ましくないフラグを設定するソフトウェアはまず見当たりません。
   
  +
しかし、残念ながら {{ic|1=-DCMAKE_BUILD_TYPE=None}} を使えば解決するというような単純なものではありません。{{ic|-O3}} の問題を解決するために {{ic|None}} のビルドタイプを使用する場合、別の問題に陥る可能性があります。多くのソフトウェアプロジェクトでは、CMake ファイルで {{ic|Release}} ビルドタイプに必要なコンパイラフラグを定義するのが一般的です (例えば、{{ic|CMAKE_C_FLAGS_RELEASE}} と {{ic|CMAKE_CXX_FLAGS_RELEASE}} を設定するようなものです) CMake 変数)このようなソフトウェアは、これらの上流で定義されたフラグを使用せずにコンパイルすると、{{ic|None}} ビルドタイプを使用した場合、壊れたり動作がおかしくなったりする可能性があります。フラグが足りないかどうかを判断するには、CMakeファイルを見る必要がありますし {{ic|1=make VERBOSE=1}} の出力を {{ic|None}} と {{ic|Release}} ビルドタイプで比較することができます。もし、{{ic|None}} ビルドタイプで上流で定義されたフラグが見落とされた場合はどうすればいいのでしょうか?なぜなら、{{ic|Release}} ビルドタイプを使用すると、望ましくない {{ic|-O3}} フラグを使用する可能性があり、{{ic|None}} ビルドタイプを使用すると、いくつかの必要な上流定義フラグを見逃す可能性があるからです。この状況を解決する標準的な方法はありませんので、ケースバイケースで分析する必要があります。もし上流が {{ic|Release}} ビルドタイプに対して {{ic|-O2}} を定義しているなら、 {{ic|1=-DCMAKE_BUILD_TYPE=Release}} を使用することができます。(後述) それ以外の場合は、CMake ファイルにパッチを当てることで解決できるかもしれません。
But unfortunately, things are not that simple like only using {{ic|1=-DCMAKE_BUILD_TYPE=None}} to fix this. When using the {{ic|None}} build type to fix the {{ic|-O3}} issue, one may fall into another problem. It is a common practice for many software projects to define some required compiler flags for the {{ic|Release}} build type in the CMake files (for example, like setting the {{ic|CMAKE_C_FLAGS_RELEASE}} and {{ic|CMAKE_CXX_FLAGS_RELEASE}} CMake variables). Such software may break or misbehave when compiled without these upstream defined flags if you use the {{ic|None}} build type. In order to determine if you are missing some flags you will need to look at the CMake files, or you can compare the output of {{ic|1=make VERBOSE=1}} for the {{ic|None}} and {{ic|Release}} build types. What to do if the {{ic|None}} build type causes some upstream defined flags to be missed? In this case you may be at the middle of two problematic situations, because if you use the {{ic|Release}} build type you may be using the undesired {{ic|-O3}} flag, and if you use the {{ic|None}} build type you will miss some required upstream defined flags. There is no standard way of solving this situation and it should be analyzed on a case-by-case basis. If upstream defines {{ic|-O2}} for the {{ic|Release}} build type, you can use {{ic|1=-DCMAKE_BUILD_TYPE=Release}} (see bellow). Otherwise, patching the CMake files may be a solution.
 
   
  +
いくつかのソフトウェアプロジェクトでは CMake ファイルに {{ic|-O2}} を {{ic|Release}} ビルドタイプとしてハードコードしています。
Some few software projects hardcode {{ic|-O2}} for the {{ic|Release}} build type in their CMake files, and thus {{ic|1=-DCMAKE_BUILD_TYPE=Release}} can be safely set in this case if you are sure that {{ic|-O2}} is the optimization level being used.
 
   
 
{{Warning|
 
{{Warning|
  +
* ビルドタイプが {{ic|None}} の場合、一部のソフトウェアが壊れる可能性があります。ビルドタイプが {{ic|None}} の場合、ソフトウェアが壊れたり、機能が失われたりしてないかテストしてください。
* Some software may break when using the {{ic|None}} build type. Test the software when using the {{ic|None}} build type to check if it will break or lose functionality.
 
  +
* ソフトウェアによっては、ビルドタイプが {{ic|Release}} でないと動作しないものがあります。実験とテストが必要です。
* Some software may work only with the {{ic|Release}} build type. You will need to experiment and test the software.
 
 
}}
 
}}
   
=== Verifying the fixes ===
+
=== 修正内容の確認 ===
   
  +
ビルドツールの冗長モードを有効にすることで、CMakeで修正内容が正しく使用されているかどうかを確認することができます。例えば、{{ic|make}} を使っている場合。(CMakeのデフォルトです) に {{ic|1=VERBOSE=1}} を追加することで実行できます ({{ic|1=make VERBOSE=1}} のように。) これにより、実行中のコンパイラコマンドを {{ic|make}} が出力するようになります。これで [[makepkg]] を実行し、コンパイラが {{ic|1=-D_FORTIFY_SOURCE=2}} と {{ic|-O2}} フラグを使っているか出力を確認することができます。各コマンドラインで複数の最適化フラグが表示されている場合、その行の最後のフラグがコンパイラによって使用されます({{ic|-O2}} が有効になるためには、最後の最適化フラグが必要です。)
You can verify if the fixes are being correctly used by CMake by enabling the verbose mode of the build tool. For example, when using {{ic|make}} (which is the CMake default), this can be done by adding {{ic|1=VERBOSE=1}} to it (like {{ic|1=make VERBOSE=1}}). This will enable {{ic|make}} to output the compiler commands that are being executed. You can then run [[makepkg]] and examine the output to see if the compiler is using the {{ic|1=-D_FORTIFY_SOURCE=2}} and {{ic|-O2}} flags. If multiple optimization flags are being displayed in each command line, the last flag in the line will be the one used by the compiler (it means that {{ic|-O2}} needs to be the last optimization flag in order to be effective).
 
   
== Prefix and library install directories ==
+
== Prefix とライブラリのインストール先 ==
   
The standard Arch Linux {{ic|/usr}} prefix can be specified by the {{ic|1=-DCMAKE_INSTALL_PREFIX=/usr}} CMake option. This is usually needed because a lot of software defaults to install files into the {{ic|/usr/local}} prefix.
+
Arch Linux 標準の {{ic|/usr}} Prefix {{ic|1=-DCMAKE_INSTALL_PREFIX=/usr}} CMake のオプションで指定できます。多くのソフトウェアがデフォルトでファイルを {{ic|/usr/local}} という Prefix にインストールするため、これは通常必要です。
   
  +
一部のアップストリームプロジェクトは、ライブラリを {{ic|/usr/lib64}} ディレクトリにインストールするように CMake ファイルを設定します。この場合、{{ic|1=-DCMAKE_INSTALL_LIBDIR=lib}} CMake オプションを使用して、ライブラリのインストールディレクトリを {{ic|/usr/lib}} に正しく設定できます。
Some upstream projects set their CMake files to install libraries into the {{ic|/usr/lib64}} directory. If this is the case, you can correctly set the library installation directory to {{ic|/usr/lib}} by using the {{ic|1=-DCMAKE_INSTALL_LIBDIR=lib}} CMake option.
 
   
  +
== ヒントとヒントとテクニック‎ ==
== Tips and tricks ==
 
   
=== Specifying directories ===
+
=== ディレクトリの指定 ===
   
  +
CMake バージョン 3.13 以降、ビルドディレクトリを自動的に作成する {{ic|-B}} オプションが用意されています。これにより、分離された {{ic|mkdir}} によるビルドディレクトリの作成が不要になりました。(または {{ic|install}}) コマンドを使用します。{{ic|-S}} オプションはソースディレクトリ ({{ic|CMakeLists.txt}} ファイルを検索する場所) を指定し、 {{ic|cmake}} を実行する前にソースツリーに {{ic|cd}} する必要をなくしました。この2つのオプションを組み合わせると、ビルドとソースのディレクトリを指定する便利な方法となります。例えば、''foo'' という名前のプログラムをビルドする場合。
Since CMake version 3.13, there is a {{ic|-B}} option that automatically creates the build directory. This avoids the creation of the build directory by a separated {{ic|mkdir}} (or {{ic|install}}) command. The {{ic|-S}} option specifies the source directory (where to search for a {{ic|CMakeLists.txt}} file) and avoids the need of {{ic|cd}}'ing into the source tree before executing {{ic|cmake}}. Combined together, these two options are a convenient way to specify the build and the source directories. For example, for building a program named ''foo'':
 
   
 
{{hc|1=PKGBUILD|2=
 
{{hc|1=PKGBUILD|2=
71行目: 71行目:
 
}}
 
}}
   
  +
=== 不要な出力の可能性を低減する===
=== Reducing possible unneeded output ===
 
   
  +
{{ic|-Wno-dev}} を使用します。CMake オプションは、{{ic|CMakeLists.txt}} ファイルを書いた上流プロジェクトの開発者のみを対象とした警告の出力を抑止します。これらの警告を削除することで、CMake の出力がスムーズになり、それを調べる負担が軽減されます。一般的なルールとして、これらの警告は通常パッケージャが安全に無視できるものです。
The {{ic|-Wno-dev}} CMake option will suppress the output of some warnings that are meant only for the upstream project developers who write the {{ic|CMakeLists.txt}} files. Removing these warnings makes the CMake output smoother and reduces the burden on examining it. As a general rule, these warnings usually can be safely ignored by packagers.
 
   
=== Removing insecure {{ic|RPATH}} references from binaries ===
+
=== バイナリから安全でない {{ic|RPATH}} 参照を削除する ===
   
  +
作成されたバイナリが {{ic|RPATH}} に安全でない参照を含むことがあります。これはビルドされたパッケージに対して [[Namcap]] を実行することで確認でき、修正されるべきセキュリティ問題であることがわかります。この問題は、{{ic|1=CMAKE_SKIP_INSTALL_RPATH=YES}} を使用することで修正できる可能性が高いです。または {{ic|1=CMAKE_SKIP_RPATH=YES}} CMake のオプションです。両方を使って実験し、問題のソフトウェアで何がうまくいくかを見る必要があります(両方のオプションを使うことは必要ありません。)
Sometimes the resulting binaries can contain insecure references in {{ic|RPATH}}. This can be verified by running [[Namcap]] on the built package and consists in a security issue that should be fixed. There is a good chance to fix this by using the {{ic|1=CMAKE_SKIP_INSTALL_RPATH=YES}} '''or''' {{ic|1=CMAKE_SKIP_RPATH=YES}} CMake options. You need to experiment with both and see what will work in the software in question (using both options is not needed).
 
   
=== Getting all available CMake options ===
+
=== 利用可能な全てのCMakeオプションの取得 ===
   
  +
ソフトウェアプロジェクトで利用可能なすべての「見える」CMakeオプションを取得するには、ソースツリーで {{ic|cmake -LAH}} を実行します(メインの {{ic|CMakeLists.txt}} ファイルがあるところです)。
For getting all "visible" CMake options that are available for a software project, execute {{ic|cmake -LAH}} in the source tree (where the main {{ic|CMakeLists.txt}} file is located).
 
   
  +
もし、後で参照するために出力を保存したい場合は、ファイルにリダイレクトすることができます。
If you want to save the output for later reference, you can redirect it to a file:
 
   
 
$ cmake -LAH >options.txt 2>&1
 
$ cmake -LAH >options.txt 2>&1
   
  +
=== ビルド中の FetchContent のダウンロードを回避 ===
== Template ==
 
   
  +
CMake は、ビルド時に追加のリソースまたはサブプロジェクトを取得できるようにする [https://cmake.org/cmake/help/latest/module/FetchContent.html FetchContent] モジュールを提供します。ただし、理想的には、すべてのソースは {{ic|sources}} 配列で指定されているため、ビルド前に [[makepkg]] によってフェッチされる必要があります。これは、オプション [https://cmake.org/cmake/help/latest/module/FetchContent.html#variable:FETCHCONTENT_SOURCE_DIR_%3CuppercaseName%3E FETCHCONTENT_SOURCE_DIR_<uppercaseName>] を使用して実行できます。これにより、ファイルへのパスを指定できます。それ以外の場合は取得されます。さらに、[https://cmake.org/cmake/help/latest/module/FetchContent.html#variable:FETCHCONTENT_FULLY_DISCONNECTED FETCHCONTENT_FULLY_DISCONNECTED=ON] を使用すると、{{ic|FetchContent}} 宣言を見逃しても、ビルド中にすべてのダウンロードをスキップすることができます。
Here is a general template for the {{ic|build()}} function that serves as a starting point for CMake-based packages. Supposing the package is named ''foo'', it is C and C++ based and that it does not define any required compiler flags for the {{ic|Release}} build type in the CMake files.
 
   
  +
==== 例 ====
{{Note|The check function will only work if projects use {{ic|enable_testing()}} and/or {{ic|add_test()}} functionality in {{ic|CMakeFiles.txt}}.}}
 
  +
  +
プロジェクトがリソース {{ic|foo}} を取得すると仮定します。
  +
  +
{{hc|CMakeLists.txt|<nowiki>
  +
FetchContent_Declare(
  +
foo
  +
URL https://example.com/foo.tar.gz
  +
URL_HASH SHA256=cf051bf611a94884ba5e4c2d03932d14e83875c5b77f0fdf55c404cad0e4a6e6
  +
)
  +
FetchContent_MakeAvailable(foo)
  +
</nowiki>}}
  +
  +
次に、ビルド中にダウンロードする代わりに、このリソースを {{ic|sources}} 配列に追加し、ビルド ファイルの生成時に宣言できます。
  +
  +
{{hc|PKGBUILD|<nowiki>
  +
sources=(
  +
...
  +
"https://example.com/foo.tar.gz"
  +
)
  +
  +
sha256sums=(
  +
...
  +
"cf051bf611a94884ba5e4c2d03932d14e83875c5b77f0fdf55c404cad0e4a6e6"
  +
)
  +
</nowiki>}}
  +
  +
$ cmake -B build -S "$pkgname-$pkgver" -DFETCHCONTENT_FULLY_DISCONNECTED=ON -DFETCHCONTENT_SOURCE_DIR_FOO="$srcdir/foo"
  +
  +
== テンプレート ==
  +
  +
ここでは、CMake ベースのパッケージの出発点となる {{ic|build()}} 関数の一般的なテンプレートについて説明します。パッケージの名前は ''foo'' で、C および C++ ベースであり、CMake ファイルの中で {{ic|Release}} ビルドタイプに必要なコンパイラフラグを定義していないと仮定します。
  +
  +
{{Note|このチェック機能は {{ic|enable_testing()}} と {{ic|add_test()}} が {{ic|CMakeFiles.txt}}}} で使われている場合のみ働きます。
   
 
{{hc|1=PKGBUILD|2=
 
{{hc|1=PKGBUILD|2=
112行目: 145行目:
 
}}
 
}}
   
Do not forget to place {{Pkg|cmake}} in [[makedepends]].
+
{{Pkg|cmake}} [[PKGBUILD#makedepends|makedepends]] に配置することを忘れないでください。
   
== Example packages ==
+
== パッケージの例 ==
   
 
* {{Pkg|i2pd}}
 
* {{Pkg|i2pd}}
 
* {{Pkg|libmysofa}}
 
* {{Pkg|libmysofa}}
   
== See also ==
+
== 参照 ==
   
* [https://cmake.org/documentation/ CMake documentation]
+
* [https://cmake.org/documentation/ CMake ドキュメント]
* [https://cmake.org/cmake/help/latest/ Documentation reference for the latest version]
+
* [https://cmake.org/cmake/help/latest/ 最新バージョンのドキュメントリファレンス]
* [[Wikipedia:CMake|Wikipedia article]]
+
* [[Wikipedia:ja:CMake|CMake Wikipedia]]
 
* {{man|1|cmake}}
 
* {{man|1|cmake}}

2023年10月30日 (月) 03:47時点における最新版

この文書は cmake を使うソフトウェアの PKGBUILD を書くための標準とガイドラインをカバーしています。

はじめに

CMake web page より

CMake は、ソフトウェアをビルド、テスト、パッケージ化するために設計された、オープンソースでクロスプラットフォームのツールファミリーです。CMake は、プラットフォームやコンパイラに依存しないシンプルな設定ファイルを使ってソフトウェアのコンパイルプロセスを制御し、選択したコンパイラ環境で使用できるネイティブな makefile と workspaces を生成するために使用されます。

典型的な使用方法

典型的な使い方は、cmake コマンドを実行し、その後に building コマンドを実行することです。cmake コマンドは通常、いくつかのパラメータを設定し、必要な依存関係をチェックしてビルドファイルを作成し、ソフトウェアを makeninja といった他のツールでビルドできる状態にします。

CMakeの好ましくない動作について

ビルドファイルを生成するための内部特性により、CMake が好ましくない動作をすることがあります。そのため、CMake ベースのソフトウェアのために PKGBUILD を書くときにはいくつかのステップに注意する必要があります。

CMake はデフォルトのコンパイラ最適化フラグを自動的にオーバーライドすることがあります

CMake を -DCMAKE_BUILD_TYPE=Release オプション付きで動かしている人をよく見かけます。上流のプロジェクトでは、ビルド手順にこのオプションをうっかり入れてしまうこともありますが、これは望ましくない振る舞いを生み出します。

それぞれのビルドタイプは CMake に自動的に CFLAGSCXXFLAGS にフラグのセットを追加させます。一般的な Release ビルドタイプを使うときは、自動的に -O3 [1] コンパイラ最適化フラグを追加し、これは現在 Arch Linux のデフォルトフラグである -O2 よりも優先されます。(設定ファイル makepkg configuration file で定義されています) これは Arch Linux が目標とする最適化レベルから逸脱しているので望ましくありません。

-O3 に関する注意事項

-O3 を使用したからといって、ソフトウェアのパフォーマンスが向上することを保証するものではなく、時にはプログラムの動作が遅くなることもあります。また、状況によってはソフトウェアを壊してしまうこともあります。Arch Linux の開発者がターゲット最適化レベルとして -O2 を選択したのには理由があり、私たちはそれに従うべきでしょう。あなたが何をしているかを正確に分かっている場合、またはアップストリームが -O3 が必要であると明示的・暗示的に言っている場合以外は、私たちのパッケージで使用するのは避けるべきです。

自動最適化フラグオーバーライドの修正

100%保証された方法で修正することは、CMake の柔軟性により、簡単な問題ではありません。すべてのケースに適用できる標準的な解決策は存在しないことに注意してください。ここでは、考えられる解決策と、守るべきポイントについて説明します。

CMake のデフォルトのビルドタイプは None であり、デフォルトでは CFLAGSCXXFLAGS にフラグを付加しないため、 CMAKE_BUILD_TYPE オプションを使用しないだけでもデフォルトが None となり動作することがあります。しかし、多くのソフトウェアプロジェクトでは、ビルドタイプを自動的に Release に設定するため、このオプションを省略しても問題が解決する保証はないことに注意してください。コマンドラインで CMAKE_BUILD_TYPE が設定されていない場合、CMake ファイルで (または他のタイプで) 設定します。

デフォルトの None ビルドタイプは CFLAGSCXXFLAGS にフラグを付加しないので、 -DCMAKE_BUILD_TYPE=None オプションも使用可能です。一般的には -DCMAKE_BUILD_TYPE=None オプションを使う方が CMAKE_BUILD_TYPE を省略するよりも良いと言われています。これは CMAKE_BUILD_TYPE が省略されたときにアップストリームが自動的にビルドタイプを Release に設定する場合をカバーするもので、デフォルトではフラグは付加されず、ビルドタイプ None に好ましくないフラグを設定するソフトウェアはまず見当たりません。

しかし、残念ながら -DCMAKE_BUILD_TYPE=None を使えば解決するというような単純なものではありません。-O3 の問題を解決するために None のビルドタイプを使用する場合、別の問題に陥る可能性があります。多くのソフトウェアプロジェクトでは、CMake ファイルで Release ビルドタイプに必要なコンパイラフラグを定義するのが一般的です (例えば、CMAKE_C_FLAGS_RELEASECMAKE_CXX_FLAGS_RELEASE を設定するようなものです) CMake 変数)このようなソフトウェアは、これらの上流で定義されたフラグを使用せずにコンパイルすると、None ビルドタイプを使用した場合、壊れたり動作がおかしくなったりする可能性があります。フラグが足りないかどうかを判断するには、CMakeファイルを見る必要がありますし make VERBOSE=1 の出力を NoneRelease ビルドタイプで比較することができます。もし、None ビルドタイプで上流で定義されたフラグが見落とされた場合はどうすればいいのでしょうか?なぜなら、Release ビルドタイプを使用すると、望ましくない -O3 フラグを使用する可能性があり、None ビルドタイプを使用すると、いくつかの必要な上流定義フラグを見逃す可能性があるからです。この状況を解決する標準的な方法はありませんので、ケースバイケースで分析する必要があります。もし上流が Release ビルドタイプに対して -O2 を定義しているなら、 -DCMAKE_BUILD_TYPE=Release を使用することができます。(後述) それ以外の場合は、CMake ファイルにパッチを当てることで解決できるかもしれません。

いくつかのソフトウェアプロジェクトでは CMake ファイルに -O2Release ビルドタイプとしてハードコードしています。

警告:
  • ビルドタイプが None の場合、一部のソフトウェアが壊れる可能性があります。ビルドタイプが None の場合、ソフトウェアが壊れたり、機能が失われたりしてないかテストしてください。
  • ソフトウェアによっては、ビルドタイプが Release でないと動作しないものがあります。実験とテストが必要です。

修正内容の確認

ビルドツールの冗長モードを有効にすることで、CMakeで修正内容が正しく使用されているかどうかを確認することができます。例えば、make を使っている場合。(CMakeのデフォルトです) に VERBOSE=1 を追加することで実行できます (make VERBOSE=1 のように。) これにより、実行中のコンパイラコマンドを make が出力するようになります。これで makepkg を実行し、コンパイラが -D_FORTIFY_SOURCE=2-O2 フラグを使っているか出力を確認することができます。各コマンドラインで複数の最適化フラグが表示されている場合、その行の最後のフラグがコンパイラによって使用されます(-O2 が有効になるためには、最後の最適化フラグが必要です。)

Prefix とライブラリのインストール先

Arch Linux 標準の /usr Prefix は -DCMAKE_INSTALL_PREFIX=/usr CMake のオプションで指定できます。多くのソフトウェアがデフォルトでファイルを /usr/local という Prefix にインストールするため、これは通常必要です。

一部のアップストリームプロジェクトは、ライブラリを /usr/lib64 ディレクトリにインストールするように CMake ファイルを設定します。この場合、-DCMAKE_INSTALL_LIBDIR=lib CMake オプションを使用して、ライブラリのインストールディレクトリを /usr/lib に正しく設定できます。

ヒントとヒントとテクニック‎

ディレクトリの指定

CMake バージョン 3.13 以降、ビルドディレクトリを自動的に作成する -B オプションが用意されています。これにより、分離された mkdir によるビルドディレクトリの作成が不要になりました。(または install) コマンドを使用します。-S オプションはソースディレクトリ (CMakeLists.txt ファイルを検索する場所) を指定し、 cmake を実行する前にソースツリーに cd する必要をなくしました。この2つのオプションを組み合わせると、ビルドとソースのディレクトリを指定する便利な方法となります。例えば、foo という名前のプログラムをビルドする場合。

PKGBUILD
build() {
    cmake -B build -S "foo-${pkgver}" [other_cmake_options]
    cmake --build build
}

不要な出力の可能性を低減する

-Wno-dev を使用します。CMake オプションは、CMakeLists.txt ファイルを書いた上流プロジェクトの開発者のみを対象とした警告の出力を抑止します。これらの警告を削除することで、CMake の出力がスムーズになり、それを調べる負担が軽減されます。一般的なルールとして、これらの警告は通常パッケージャが安全に無視できるものです。

バイナリから安全でない RPATH 参照を削除する

作成されたバイナリが RPATH に安全でない参照を含むことがあります。これはビルドされたパッケージに対して Namcap を実行することで確認でき、修正されるべきセキュリティ問題であることがわかります。この問題は、CMAKE_SKIP_INSTALL_RPATH=YES を使用することで修正できる可能性が高いです。または CMAKE_SKIP_RPATH=YES CMake のオプションです。両方を使って実験し、問題のソフトウェアで何がうまくいくかを見る必要があります(両方のオプションを使うことは必要ありません。)

利用可能な全てのCMakeオプションの取得

ソフトウェアプロジェクトで利用可能なすべての「見える」CMakeオプションを取得するには、ソースツリーで cmake -LAH を実行します(メインの CMakeLists.txt ファイルがあるところです)。

もし、後で参照するために出力を保存したい場合は、ファイルにリダイレクトすることができます。

$ cmake -LAH >options.txt 2>&1

ビルド中の FetchContent のダウンロードを回避

CMake は、ビルド時に追加のリソースまたはサブプロジェクトを取得できるようにする FetchContent モジュールを提供します。ただし、理想的には、すべてのソースは sources 配列で指定されているため、ビルド前に makepkg によってフェッチされる必要があります。これは、オプション FETCHCONTENT_SOURCE_DIR_<uppercaseName> を使用して実行できます。これにより、ファイルへのパスを指定できます。それ以外の場合は取得されます。さらに、FETCHCONTENT_FULLY_DISCONNECTED=ON を使用すると、FetchContent 宣言を見逃しても、ビルド中にすべてのダウンロードをスキップすることができます。

プロジェクトがリソース foo を取得すると仮定します。

CMakeLists.txt
FetchContent_Declare(
    foo
    URL https://example.com/foo.tar.gz
    URL_HASH SHA256=cf051bf611a94884ba5e4c2d03932d14e83875c5b77f0fdf55c404cad0e4a6e6
)
FetchContent_MakeAvailable(foo)

次に、ビルド中にダウンロードする代わりに、このリソースを sources 配列に追加し、ビルド ファイルの生成時に宣言できます。

PKGBUILD
sources=(
    ...
    "https://example.com/foo.tar.gz"
)

sha256sums=(
    ...
    "cf051bf611a94884ba5e4c2d03932d14e83875c5b77f0fdf55c404cad0e4a6e6"
)
$ cmake -B build -S "$pkgname-$pkgver" -DFETCHCONTENT_FULLY_DISCONNECTED=ON -DFETCHCONTENT_SOURCE_DIR_FOO="$srcdir/foo"

テンプレート

ここでは、CMake ベースのパッケージの出発点となる build() 関数の一般的なテンプレートについて説明します。パッケージの名前は foo で、C および C++ ベースであり、CMake ファイルの中で Release ビルドタイプに必要なコンパイラフラグを定義していないと仮定します。

ノート: このチェック機能は enable_testing()add_test()CMakeFiles.txt

で使われている場合のみ働きます。

PKGBUILD
build() {
    cmake -B build -S "foo-${pkgver}" \
        -DCMAKE_BUILD_TYPE='None' \
        -DCMAKE_INSTALL_PREFIX='/usr' \
        -Wno-dev
    cmake --build build
}

check() {
    cd build
    ctest --output-on-failure
}

package() {
    DESTDIR="$pkgdir" cmake --install build
}

cmakemakedepends に配置することを忘れないでください。

パッケージの例

参照