CMake の INTERFACE_SYSTEM_INCLUDE_DIRECTORIES とは?

2024-04-02

CMake の Properties: Targets における INTERFACE_SYSTEM_INCLUDE_DIRECTORIES の解説

INTERFACE_SYSTEM_INCLUDE_DIRECTORIES は、CMake のターゲットプロパティの一つであり、他のターゲットがこのターゲットを依存関係として使用する際に、コンパイル時に自動的に追加されるシステムヘッダーディレクトリを指定します。これは、ターゲットが提供するインターフェースの一部として公開されるヘッダーファイルへのパスを指定するために使用されます。

主なポイント

  • INTERFACE_SYSTEM_INCLUDE_DIRECTORIES は、ターゲットのインターフェースにのみ影響を与えます。つまり、このターゲットを直接ビルドする際には使用されません。
  • システムヘッダーディレクトリは、コンパイラによって自動的に検索されるため、target_include_directories() コマンドで指定する必要はありません。
  • 複数のターゲットで同じシステムヘッダーディレクトリを共有する必要がある場合は、INTERFACE_SYSTEM_INCLUDE_DIRECTORIES を使用することで重複を避けることができます。
  • このプロパティは、PUBLIC または INTERFACE キーワードと共に使用できます。

詳細

  • PUBLIC キーワードは、このターゲットを依存関係として使用するすべてのターゲットにヘッダーディレクトリを公開することを意味します。
  • INTERFACE キーワードは、このターゲットを直接ビルドするターゲットにはヘッダーディレクトリを公開せず、このターゲットを依存関係として使用するターゲットにのみ公開することを意味します。
  • 複数のディレクトリを指定する場合は、 ; で区切ります。
  • 相対パスは、ターゲットのソースディレクトリからの相対パスとして解釈されます。
  • 絶対パスは、そのまま使用されます。

add_library(mylib INTERFACE)

target_include_directories(mylib PUBLIC "include")

set_target_properties(mylib PROPERTIES
  INTERFACE_SYSTEM_INCLUDE_DIRECTORIES "/usr/include/mylib")

この例では、mylib ターゲットは include ディレクトリ内のヘッダーファイルを公開します。また、mylib ターゲットを依存関係として使用するターゲットは、/usr/include/mylib ディレクトリ内のシステムヘッダーファイルも自動的に使用することができます。



CMake の INTERFACE_SYSTEM_INCLUDE_DIRECTORIES のサンプルコード

基本的な例

add_library(mylib INTERFACE)

target_include_directories(mylib PUBLIC "include")

set_target_properties(mylib PROPERTIES
  INTERFACE_SYSTEM_INCLUDE_DIRECTORIES "/usr/include/mylib")

複数のディレクトリを指定する例

add_library(mylib INTERFACE)

target_include_directories(mylib PUBLIC "include1" "include2")

set_target_properties(mylib PROPERTIES
  INTERFACE_SYSTEM_INCLUDE_DIRECTORIES "/usr/include/mylib1" "/usr/include/mylib2")

この例では、mylib ターゲットは include1include2 ディレクトリ内のヘッダーファイルを公開します。また、mylib ターゲットを依存関係として使用するターゲットは、/usr/include/mylib1/usr/include/mylib2 ディレクトリ内のシステムヘッダーファイルも自動的に使用することができます。

相対パスを使用する例

add_library(mylib INTERFACE)

target_include_directories(mylib PUBLIC ".")

set_target_properties(mylib PROPERTIES
  INTERFACE_SYSTEM_INCLUDE_DIRECTORIES "../include")

この例では、mylib ターゲットは現在のディレクトリ内のヘッダーファイルを公開します。また、mylib ターゲットを依存関係として使用するターゲットは、../include ディレクトリ内のシステムヘッダーファイルも自動的に使用することができます。

PUBLIC と INTERFACE キーワードの違い

add_library(mylib1 INTERFACE)
add_library(mylib2 INTERFACE)

target_include_directories(mylib1 PUBLIC "include")

set_target_properties(mylib2 PROPERTIES
  INTERFACE_SYSTEM_INCLUDE_DIRECTORIES "/usr/include/mylib")

add_executable(myexe)

target_link_libraries(myexe mylib1 mylib2)

この例では、myexemylib1mylib2



CMake でシステムヘッダーディレクトリを指定する他の方法

target_include_directories() コマンドは、ターゲットのビルド時に使用されるヘッダーディレクトリを指定します。これは、ターゲットが提供するインターフェースの一部として公開されるヘッダーファイルだけでなく、ターゲット自身が使用するヘッダーファイルも指定するために使用できます。

add_library(mylib)

target_include_directories(mylib PUBLIC "include")

target_link_libraries(mylib "/usr/lib/mylib.so")

この例では、mylib ターゲットは include ディレクトリ内のヘッダーファイルを使用します。また、mylib ターゲットは /usr/lib/mylib.so ライブラリにリンクされます。

find_package() コマンドは、特定のライブラリまたはフレームワークのヘッダーファイルとライブラリファイルを自動的に検出します。

find_package(Pkg REQUIRED)

target_include_directories(mylib PUBLIC ${Pkg_INCLUDE_DIRS})

target_link_libraries(mylib ${Pkg_LIBRARIES})

この例では、Pkg というライブラリまたはフレームワークが自動的に検出されます。mylib ターゲットは、Pkg_INCLUDE_DIRS 変数に格納されているヘッダーファイルを使用し、Pkg_LIBRARIES 変数に格納されているライブラリファイルにリンクされます。

環境変数

C_INCLUDE_PATHCPLUS_INCLUDE_PATH などの環境変数を使用して、システムヘッダーディレクトリを指定することができます。

set(ENV{C_INCLUDE_PATH} "/usr/include")
set(ENV{CPLUS_INCLUDE_PATH} "/usr/include/c++")

add_library(mylib)

この例では、mylib ターゲットは /usr/include/usr/include/c++ ディレクトリ内のシステムヘッダーファイルを使用します。

手動でヘッダーファイルを指定する

ソースファイルに直接ヘッダーファイルのパスを指定することができます。

#include "/usr/include/mylib.h"

int main() {
  // ...
}

この例では、main.c ファイルは /usr/include/mylib.h ヘッダーファイルを直接インクルードします。

  • ターゲットが提供するインターフェースの一部として公開されるヘッダーファイルには、INTERFACE_SYSTEM_INCLUDE_DIRECTORIES を使用するのがおすすめです。
  • ターゲット自身が使用するヘッダーファイルには、target_include_directories() コマンドを使用するのがおすすめです。
  • 特定のライブラリまたはフレームワークのヘッダーファイルとライブラリファイルを自動的に検出したい場合は、find_package() コマンドを使用するのがおすすめです。
  • 環境変数は、すべてのターゲットに適用されるため、慎重に使用해야します。
  • 手動でヘッダーファイルを指定するのは、最後の手段として使用するのがおすすめです。

CMake でシステムヘッダーディレクトリを指定するには、いくつかの方法があります。どの方法を使用するべきかは、状況によって異なります。




CMake: find_library()とtarget_link_directories()の連携

target_link_directories()コマンドは、CMakeプロジェクト内のターゲットに対して、リンカがライブラリを検索するディレクトリを指定するために使用されます。これは、ターゲットがリンクするライブラリが標準の検索パスに存在しない場合に特に重要です。



CMakeコマンド mark_as_advanced() の詳細解説

mark_as_advanced() は、CMakeプロジェクトで特定のキャッシュ変数を "詳細設定" としてマークするために使用されるコマンドです。このコマンドによって、GUI ツールでこれらの変数はデフォルトでは表示されなくなり、ユーザーは "詳細設定" オプションを有効にするまで編集できなくなります。


CMake で変数を削除する3つの方法:unset() 以外にも使えるテクニック

<variable_name> は、削除したい変数の名前です。変数の名前は、文字、数字、下線(_)で構成され、先頭に数字以外のアクティブ文字が来る必要があります。変数の削除この例では、MY_VAR という変数を作成し、"Hello, world!" という値を設定します。その後、unset() コマンドを使用して MY_VAR を削除します。2番目の message() コマンドは、MY_VAR が削除されたことを確認するために使用されます。


CMakeのCommandsにおけるuse_mangled_mesa()

use_mangled_mesa() は CMake の Commands における関数で、Mesa ライブラリの mangled シンボル名を解決するために使用されます。Mesa は OpenGL の実装であり、古いバージョンの Mesa ではシンボル名が mangled されるため、use_mangled_mesa() を使用してこれらのシンボル名を解決する必要があります。


C++標準ライブラリ、テンプレートエンジン、シェルスクリプト... string()コマンドの代替方法を徹底比較

CMakeのstring()コマンドは、文字列処理を行うための強力なツールです。C++のstd::stringのような機能に加え、CMake特有の便利な機能も備えています。主な機能文字列の連結、分割、置換、比較大文字・小文字変換部分文字列の抽出



C言語コンパイラとCMakeの連携を強化! CMAKE_C_KNOWN_FEATURES で開発効率アップ

CMAKE_C_KNOWN_FEATURESは、CMakeのグローバルスコーププロパティであり、C言語コンパイラで利用可能なC言語機能のリストを格納します。このプロパティは、ターゲットのコンパイル時に特定の機能を有効化/無効化するために使用できます。


FindwxWindowsモジュールでwxWidgetsを簡単に使う

FindwxWindows は、CMake のモジュールの一つで、wxWidgets ライブラリをプロジェクトに簡単に統合するために使用されます。wxWidgets は、クロスプラットフォームの GUI ツールキットであり、Windows、Mac OS X、Linux などの様々なプラットフォームで動作する GUI アプリケーション開発を可能にします。


CMake の IMPORTED_LINK_INTERFACE_MULTIPLICITY プロパティに関するサンプルコード

IMPORTED_LINK_INTERFACE_MULTIPLICITY プロパティは、CMake の "Properties: Targets" において、インポートされた静的ライブラリのサイクルにおける繰り返しカウントを設定するために使用されます。これは、LINK_INTERFACE_MULTIPLICITY プロパティのインポートターゲット版です。


【初心者向け】CMakeでテストを実行する3つのステップ: ctest_test() コマンドから始める

引数:<test_name>: 実行するテストの名前。ワイルドカードを使用して、名前パターンに一致する複数のテストを選択できます。[OPTIONAL arguments]: テストの実行方法を制御するオプション引数。ctest_test()コマンドには、テストの実行方法を細かく制御するための様々なオプション引数が用意されています。以下に、よく使用されるオプション引数をいくつか紹介します。


Android NDK でのクロスコンパイルを成功させる CMAKE_LANG_ANDROID_TOOLCHAIN_SUFFIX 設定方法

例:ホストプラットフォームがx86_64-linux-gnuの場合、CMAKE_LANG_ANDROID_TOOLCHAIN_SUFFIXは-x86_64になります。ホストプラットフォームがarmv7-linux-androideabiの場合、CMAKE_LANG_ANDROID_TOOLCHAIN_SUFFIXは-armになります。