cmake-generator-expressions(7)
- Введение
- Пробелы и кавычки
- Отладка
Введение
Выражения генератора оцениваются во время генерации системы сборки, чтобы получить информацию, специфичную для каждой конфигурации сборки. Они имеют вид $<...>. Например:
target_include_directories(tgt PRIVATE /opt/include/$<CXX_COMPILER_ID>)
Это будет расширено до /opt/include/GNU, /opt/include/Clang, и т.д., в зависимости от используемого C++ компилятора.
Выражения генератора допускаются в контексте многих свойств целевых объектов, таких как LINK_LIBRARIES, INCLUDE_DIRECTORIES, COMPILE_DEFINITIONS и другие. Они также могут использоваться при использовании команд для заполнения этих свойств, таких как target_link_libraries(), target_include_directories(), target_compile_definitions() и другие. Они позволяют условную компоновку, условные определения, используемые при компиляции, условные каталоги включения и многое другое. Условия могут быть основаны на конфигурации сборки, свойствах целевого объекта, информации о платформе или любой другой запрошиваемой информации.
Выражения генератора могут быть вложены:
target_compile_definitions(tgt PRIVATE $<$<VERSION_LESS:$<CXX_COMPILER_VERSION>,4.2.0>:OLD_COMPILER> )
Вышеприведенное расширится до OLD_COMPILER если CMAKE_CXX_COMPILER_VERSION меньше 4.2.0.
Пробелы и кавычки
Выражения генератора обычно анализируются после аргументов команды. Если выражение генератора содержит пробелы, новые строки, точки с запятой или другие символы, которые могут интерпретироваться как разделители аргументов команды, все выражение должно быть заключено в кавычки при передаче команде. В противном случае выражение может быть разделено, и оно больше не будет распознаваться как выражение генератора.
При использовании add_custom_command() или add_custom_target(), используйте параметры VERBATIM и COMMAND_EXPAND_LISTS для получения надельного разделения и цитирования аргументов.
# WRONG: Embedded space will be treated as an argument separator. # This ends up not being seen as a generator expression at all. add_custom_target(run_some_tool COMMAND some_tool -I$<JOIN:$<TARGET_PROPERTY:tgt,INCLUDE_DIRECTORIES>, -I> VERBATIM )
# Better, but still not robust. Quotes prevent the space from splitting the # expression. However, the tool will receive the expanded value as a single # argument. add_custom_target(run_some_tool COMMAND some_tool "-I$<JOIN:$<TARGET_PROPERTY:tgt,INCLUDE_DIRECTORIES>, -I>" VERBATIM )
# Nearly correct. Using a semicolon to separate arguments and adding the # COMMAND_EXPAND_LISTS option means that paths with spaces will be handled # correctly. Quoting the whole expression ensures it is seen as a generator # expression. But if the target property is empty, we will get a bare -I # with nothing after it. add_custom_target(run_some_tool COMMAND some_tool "-I$<JOIN:$<TARGET_PROPERTY:tgt,INCLUDE_DIRECTORIES>,;-I>" COMMAND_EXPAND_LISTS VERBATIM )
Использование переменных для построения более сложного выражения генератора также является хорошим способом уменьшить ошибки и улучшить читаемость. Приведенный выше пример можно дополнительно улучшить следующим образом:
# The $<BOOL:...> check prevents adding anything if the property is empty,
# assuming the property value cannot be one of CMake's false constants.
set(prop "$<TARGET_PROPERTY:tgt,INCLUDE_DIRECTORIES>")
add_custom_target(run_some_tool
COMMAND some_tool "$<$<BOOL:${prop}>:-I$<JOIN:${prop},;-I>>"
COMMAND_EXPAND_LISTS
VERBATIM
)
Частая ошибка заключается в попытке разбить выражение генератора на несколько строк с отступами:
# WRONG: New lines and spaces all treated as argument separators, so the
# generator expression is split and not recognized correctly.
target_compile_definitions(tgt PRIVATE
$<$<AND:
$<CXX_COMPILER_ID:GNU>,
$<VERSION_GREATER_EQUAL:$<CXX_COMPILER_VERSION>,5>
>:HAVE_5_OR_LATER>
)
Вместо этого используйте вспомогательные переменные с хорошо выбранными именами для построения понятного выражения:
set(is_gnu "$<CXX_COMPILER_ID:GNU>")
set(v5_or_later "$<VERSION_GREATER_EQUAL:$<CXX_COMPILER_VERSION>,5>")
set(meet_requirements "$<AND:${is_gnu},${v5_or_later}>")
target_compile_definitions(tgt PRIVATE
"$<${meet_requirements}:HAVE_5_OR_LATER>"
)
Отладка
Поскольку выражения генератора оцениваются во время генерации системы сборки, а не во время обработки файлов CMakeLists.txt, невозможно проверить их результат с помощью команды message(). Один из возможных способов создания сообщений отладки — добавление пользовательского целевого объекта:
add_custom_target(genexdebug COMMAND ${CMAKE_COMMAND} -E echo "$<...>")
После выполнения cmake, вы можете создать целевой объект genexdebug, чтобы напечатать результат выражения $<...> (т.е. выполнить команду cmake --build ... --target genexdebug).
Другой способ — запись сообщений отладки в файл с помощью file(GENERATE):
file(GENERATE OUTPUT filename CONTENT "$<...>")
Справочник по выражениям генератора
Примечание
Этот справочник отличается от большей части документации CMake тем, что опускает угловые скобки <...> вокруг заполнительных значений, таких как condition, string, target, и т.д. Это предотвращает возможность неправильной интерпретации этих заполнительных значений как выражений генератора.
Условные выражения
Фундаментальная категория выражений генератора связана с условной логикой. Поддерживаются две формы условных выражений генератора:
-
$<condition:true_string> -
Вычисляется как
true_stringеслиconditionравно1, или пустой строкой, еслиconditionоценивается как0. Любое другое значение дляconditionприводит к ошибке.
-
$<IF:condition,true_string,false_string> -
Новое в версии 3.8.
Вычисляется как
true_stringеслиconditionравно1, или какfalse_stringеслиconditionравно0. Любое другое значение дляconditionприводит к ошибке.
Обычно condition само по себе является выражением генератора. Например, следующее выражение расширяется до DEBUG_MODE при использовании конфигурации Debug, и до пустой строки во всех других конфигурациях:
$<$<CONFIG:Debug>:DEBUG_MODE>
Булевы значения condition кроме 1 или 0 могут обрабатываться с помощью выражения генератора $<BOOL:...>:
-
$<BOOL:string> -
Преобразует
stringв0или1. Вычисляется как0если выполняется хотя бы одно из следующих условий:-
stringпустое, -
string(независимо от регистра) равно0,FALSE,OFF,N,NO,IGNORE, илиNOTFOUND, или -
stringзаканчивается на-NOTFOUND(регистрозависимо).
В противном случае вычисляется как
1. -
Выражение генератора $<BOOL:...> часто используется, когда condition предоставляется переменной CMake:
$<$<BOOL:${HAVE_SOME_FEATURE}>:-DENABLE_SOME_FEATURE>
Логические операторы
Поддерживаются обычные логические операторы:
-
$<AND:conditions> -
где
conditions— это список булевых выражений через запятую, все из которых должны быть либо1, либо0. Все выражение вычисляется как1если все условия1. Если хотя бы одно условие0, все выражение вычисляется как0.
-
$<OR:conditions> -
где
conditions— это список логических выражений, разделённых запятыми. Все они должны вычисляться как1или0. Весь выражение вычисляется как1, если хотя бы одно изconditionsравно1. Если всеconditionsвычисляются как0, то всё выражение вычисляется как0.
-
$<NOT:condition> -
conditionдолжен быть0или1. Результат выражения —0еслиconditionравно1, иначе1.
Основные выражения сравнения
CMake поддерживает различные выражения генератора для сравнения объектов. В этом разделе рассматриваются основные и наиболее часто используемые типы сравнений. Другие более специфические типы сравнения описаны в отдельных разделах ниже.
Сравнения строк
-
$<STREQUAL:string1,string2> -
1еслиstring1иstring2равны, иначе0. Сравнение регистрозависимое. Для регистронезависимого сравнения комбинируйте с выражением генератора для преобразования строк. Например, следующее выражение вычисляется как1, если${foo}равно любому из значенийBAR,Bar,barи т. д.$<STREQUAL:$<UPPER_CASE:${foo}>,BAR>
-
$<EQUAL:value1,value2> -
1еслиvalue1иvalue2численно равны, иначе0.
Сравнения версий
-
$<VERSION_LESS:v1,v2> -
1еслиv1является версией меньшеv2, иначе0.
-
$<VERSION_GREATER:v1,v2> -
1еслиv1является версией большеv2, иначе0.
-
$<VERSION_EQUAL:v1,v2> -
1еслиv1имеет ту же версию, что иv2, иначе0.
-
$<VERSION_LESS_EQUAL:v1,v2> -
Добавлена в версии 3.7.
1еслиv1является версией меньше или равнойv2, иначе0.
-
$<VERSION_GREATER_EQUAL:v1,v2> -
Добавлена в версии 3.7.
1еслиv1является версией больше или равнойv2, иначе0.
Преобразования строк
-
$<LOWER_CASE:string> -
Содержимое
stringпреобразуется в нижний регистр.
-
$<UPPER_CASE:string> -
Содержимое
stringпреобразуется в верхний регистр.
-
$<MAKE_C_IDENTIFIER:...> -
Содержимое
...преобразуется в идентификатор C. Преобразование выполняется аналогично поведению командыstring(MAKE_C_IDENTIFIER).
Выражения списков
-
$<IN_LIST:string,list> -
Добавлена в версии 3.12.
1еслиstringявляется элементом в списке, разделённом точкой с запятойlist, иначе0. Используются регистрозависимые сравнения.
-
$<JOIN:list,string> -
Объединяет список, вставляя содержимое
stringмежду каждым элементом.
-
$<REMOVE_DUPLICATES:list> -
Добавлена в версии 3.15.
Удаляет дублирующиеся элементы в заданном списке
list. Относительный порядок элементов сохраняется, но если встречаются дубликаты, сохраняется только первый экземпляр.
-
$<FILTER:list,INCLUDE|EXCLUDE,regex> -
Добавлена в версии 3.15.
Включает или исключает элементы из списка
list, которые соответствуют регулярному выражениюregex.
Выражения путей
Большинство выражений в этом разделе тесно связаны с командой cmake_path(), предоставляя те же возможности, но в виде выражения генератора.
Для всех выражений генератора в этом разделе пути ожидаются в формате CMake. Выражение генератора $<PATH:CMAKE_PATH> может использоваться для преобразования системного пути в путь CMake-стиля.
Сравнения путей
-
$<PATH_EQUAL:path1,path2> -
Добавлена в версии 3.24.
Сравнивает лексические представления двух путей. Никакая нормализация путей не выполняется. Возвращает
1, если пути равны,0в противном случае.См. cmake_path(COMPARE) для получения дополнительной информации.
Запросы к путям
Эти выражения обеспечивают возможности генерации, эквивалентные параметрам запроса к командам Запрос команды cmake_path(). Все пути ожидаются в формате CMake.
-
$<PATH:HAS_*,path> -
Добавлена в версии 3.24.
Следующие операции возвращают
1, если указанный компонент пути присутствует,0в противном случае. См. Структура и терминология путей для значения каждого компонента пути.$<PATH:HAS_ROOT_NAME,path> $<PATH:HAS_ROOT_DIRECTORY,path> $<PATH:HAS_ROOT_PATH,path> $<PATH:HAS_FILENAME,path> $<PATH:HAS_EXTENSION,path> $<PATH:HAS_STEM,path> $<PATH:HAS_RELATIVE_PART,path> $<PATH:HAS_PARENT_PATH,path>
Обратите внимание на следующие частные случаи:
- Для
HAS_ROOT_PATH, истинный результат будет возвращён только в том случае, если хотя бы один изroot-nameилиroot-directoryне пуст. - Для
HAS_PARENT_PATH, корневой каталог также считается имеющим родительский каталог, который будет сам по себе. Результат истинный, за исключением случая, когда путь состоит только из имени файла.
- Для
- $<PATH:IS_ABSOLUTE,path>
-
Добавлена в версии 3.24.
Возвращает
1, если путь является абсолютным,0в противном случае.
- $<PATH:IS_RELATIVE,path>
-
Добавлена в версии 3.24.
Это вернёт противоположное значению
IS_ABSOLUTE.
- $<PATH:IS_PREFIX[,NORMALIZE],path,input>
-
Добавлена в версии 3.24.
Возвращает
1, еслиpathявляется префиксомinput,0в противном случае.Когда указан параметр
NORMALIZE,pathиinputнормализуются перед проверкой.
Декомпозиция путей
Эти выражения предоставляют возможности генерации, эквивалентные параметрам Декомпозиция команды cmake_path(). Все пути ожидаются в формате CMake.
- $<PATH:GET_*,...>
-
Добавлена в версии 3.24.
Следующие операции извлекают различные компоненты или группы компонентов из пути. См. Структура и терминология путей для значения каждого компонента пути.
$<PATH:GET_ROOT_NAME,path> $<PATH:GET_ROOT_DIRECTORY,path> $<PATH:GET_ROOT_PATH,path> $<PATH:GET_FILENAME,path> $<PATH:GET_EXTENSION[,LAST_ONLY],path> $<PATH:GET_STEM[,LAST_ONLY],path> $<PATH:GET_RELATIVE_PART,path> $<PATH:GET_PARENT_PATH,path>
Если запрашиваемый компонент отсутствует в пути, возвращается пустая строка.
Преобразования путей
Эти выражения предоставляют возможности генерации, эквивалентные параметрам Модификация и Генерация команды cmake_path(). Все пути ожидаются в формате CMake.
- $<PATH:CMAKE_PATH[,NORMALIZE],path>
-
Новая в версии 3.24.
Возвращает
path. Еслиpath— это путь операционной системы, он преобразуется в путь CMake со слешами вперёд (/). В Windows учитывается маркер длинного имени файла.При указании параметра
NORMALIZE, путь нормализуется после преобразования.
- $<PATH:APPEND,path,input,...>
-
Новая в версии 3.24.
Возвращает все аргументы
input, добавленные кpathс использованием/в качествеdirectory-separator. В зависимости отinput, значениеpathможет быть отброшено.См. cmake_path(APPEND) для получения более подробной информации.
- $<PATH:REMOVE_FILENAME,path>
-
Новая в версии 3.24.
Возвращает
pathс удалённой частью имени файла (как возвращается$<PATH:GET_FILENAME>). После удаления любые завершающиеdirectory-separatorостаются без изменений, если присутствуют.См. cmake_path(REMOVE_FILENAME) для получения более подробной информации.
- $<PATH:REPLACE_FILENAME,path,input>
-
Новая в версии 3.24.
Возвращает
pathс заменой компонента имени файла наinput. Еслиpathне имеет компонента имени файла (т.е.$<PATH:HAS_FILENAME>возвращает0),pathостаётся без изменений.См. cmake_path(REPLACE_FILENAME) для получения более подробной информации.
- $<PATH:REMOVE_EXTENSION[,LAST_ONLY],path>
-
Новая в версии 3.24.
Возвращает
pathс удалённым расширением, если таковое имеется.См. cmake_path(REMOVE_EXTENSION) для получения более подробной информации.
- $<PATH:REPLACE_EXTENSION[,LAST_ONLY],path,input>
-
Новая в версии 3.24.
Возвращает
pathс заменой расширения наinput, если таковое имеется.См. cmake_path(REPLACE_EXTENSION) для получения более подробной информации.
- $<PATH:NORMAL_PATH,path>
-
Новая в версии 3.24.
Возвращает
path, нормализованный в соответствии с этапами, описанными в Нормализация.
- $<PATH:RELATIVE_PATH,path,base_directory>
-
Новая в версии 3.24.
Возвращает
path, изменённый для того, чтобы сделать его относительным к аргументуbase_directory.См. cmake_path(RELATIVE_PATH) для получения более подробной информации.
- $<PATH:ABSOLUTE_PATH[,NORMALIZE],path,base_directory>
-
Новая в версии 3.24.
Возвращает
pathкак абсолютный. Еслиpath— относительный путь ($<PATH:IS_RELATIVE>возвращает1), он оценивается относительно указанного базового каталога, заданного аргументомbase_directory.При указании параметра
NORMALIZE, путь нормализуется после вычисления пути.См. cmake_path(ABSOLUTE_PATH) для получения более подробной информации.
Пути оболочки
-
$<SHELL_PATH:...> -
Новая в версии 3.4.
Содержимое
...преобразуется в стиль пути оболочки. Например, слеши преобразуются в обратные слеши в оболочках Windows, а буквы диска преобразуются в пути POSIX в оболочках MSYS....должен быть абсолютным путем.Новая в версии 3.14:
...может быть списком, разделённым точкой с запятой путей, в этом случае каждый путь преобразуется индивидуально, а список результатов генерируется с использованием разделителя путей оболочки (:на POSIX и;в Windows). Убедитесь, что аргумент, содержащий этот genex, заключён в двойные кавычки в коде CMake, чтобы;не разделял аргументы.
Выражения конфигурации
-
$<CONFIG> -
Имя конфигурации. Используйте его вместо устаревшего выражения генератора
CONFIGURATION.
- $<CONFIG:cfgs>
-
1, если config соответствует одному из элементов в списке, разделённом запятойcfgs, в противном случае0. Это сравнение не учитывает регистр. Сопоставление вMAP_IMPORTED_CONFIG_<CONFIG>также учитывается этим выражением при его оценке на свойстве целиIMPORTED.
-
$<OUTPUT_CONFIG:...> -
Новая в версии 3.20.
Действителен только в
add_custom_command()иadd_custom_target()в качестве внешнего выражения генератора в аргументе. С генераторомNinja Multi-Config, выражения генератора в...оцениваются с использованием "конфигурации вывода" пользовательской команды. С другими генераторами содержимое...оценивается обычно.
-
$<COMMAND_CONFIG:...> -
Новая в версии 3.20.
Действителен только в
add_custom_command()иadd_custom_target()в качестве внешнего выражения генератора в аргументе. С генераторомNinja Multi-Config, выражения генератора в...оцениваются с использованием "конфигурации команды" пользовательской команды. С другими генераторами содержимое...оценивается обычно.
Выражения инструментальной цепочки и языка
Платформа
-
$<PLATFORM_ID> -
Идентификатор платформы CMake текущей системы. Также см. переменную
CMAKE_SYSTEM_NAME.
- $<PLATFORM_ID:platform_ids>
-
где
platform_ids— список, разделённый запятыми.1если идентификатор платформы CMake соответствует одному из элементов вplatform_ids, в противном случае0. См. также переменнуюCMAKE_SYSTEM_NAME.
Версия компилятора
См. также переменную CMAKE_<LANG>_COMPILER_VERSION, которая тесно связана с выражениями в этом подразделе.
-
$<C_COMPILER_VERSION> -
Версия используемого компилятора C.
- $<C_COMPILER_VERSION:version>
-
1если версия компилятора C соответствуетversion, в противном случае0.
-
$<CXX_COMPILER_VERSION> -
Версия используемого компилятора CXX.
- $<CXX_COMPILER_VERSION:version>
-
1если версия компилятора CXX соответствуетversion, в противном случае0.
-
$<CUDA_COMPILER_VERSION> -
Новая в версии 3.15.
Версия используемого компилятора CUDA.
- $<CUDA_COMPILER_VERSION:version>
-
Новая в версии 3.15.
1если версия компилятора CXX соответствуетversion, в противном случае0.
-
$<OBJC_COMPILER_VERSION> -
Новая в версии 3.16.
Версия используемого компилятора OBJC.
- $<OBJC_COMPILER_VERSION:version>
-
Новая в версии 3.16.
1если версия компилятора OBJC соответствуетversion, в противном случае0.
-
$<OBJCXX_COMPILER_VERSION> -
Новая в версии 3.16.
Версия используемого компилятора OBJCXX.
- $<OBJCXX_COMPILER_VERSION:version>
-
Новая в версии 3.16.
1если версия компилятора OBJCXX соответствуетversion, в противном случае0.
-
$<Fortran_COMPILER_VERSION> -
Версия используемого компилятора Fortran.
- $<Fortran_COMPILER_VERSION:version>
-
1если версия компилятора Fortran соответствуетversion, в противном случае0.
-
$<HIP_COMPILER_VERSION> -
Новая в версии 3.21.
Версия используемого компилятора HIP.
- $<HIP_COMPILER_VERSION:version>
-
Новая в версии 3.21.
1если версия компилятора HIP соответствуетversion, в противном случае0.
-
$<ISPC_COMPILER_VERSION> -
Новая в версии 3.19.
Версия используемого компилятора ISPC.
- $<ISPC_COMPILER_VERSION:version>
-
Новая в версии 3.19.
1если версия компилятора ISPC соответствуетversion, в противном случае0.
Язык и идентификатор компилятора
См. также переменную CMAKE_<LANG>_COMPILER_ID, которая тесно связана с большинством выражений в этом подразделе.
-
$<C_COMPILER_ID> -
Идентификатор компилятора C, используемый CMake.
- $<C_COMPILER_ID:compiler_ids>
-
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора C CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<CXX_COMPILER_ID> -
Идентификатор компилятора CXX, используемый CMake.
- $<CXX_COMPILER_ID:compiler_ids>
-
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора CXX CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<CUDA_COMPILER_ID> -
Новая в версии 3.15.
Идентификатор компилятора CUDA, используемый CMake.
- $<CUDA_COMPILER_ID:compiler_ids>
-
Новая в версии 3.15.
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора CUDA CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<OBJC_COMPILER_ID> -
Новая в версии 3.16.
Идентификатор компилятора OBJC, используемый CMake.
- $<OBJC_COMPILER_ID:compiler_ids>
-
Новая в версии 3.16.
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора Objective-C CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<OBJCXX_COMPILER_ID> -
Новая в версии 3.16.
Идентификатор компилятора OBJCXX, используемый CMake.
- $<OBJCXX_COMPILER_ID:compiler_ids>
-
Новая в версии 3.16.
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора Objective-C++ CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<Fortran_COMPILER_ID> -
Идентификатор компилятора Fortran, используемый CMake.
- $<Fortran_COMPILER_ID:compiler_ids>
-
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора Fortran CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<HIP_COMPILER_ID> -
Новая в версии 3.21.
Идентификатор компилятора HIP, используемый CMake.
- $<HIP_COMPILER_ID:compiler_ids>
-
Новая в версии 3.21.
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора HIP CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<ISPC_COMPILER_ID> -
Новая в версии 3.19.
Идентификатор компилятора ISPC, используемый CMake.
- $<ISPC_COMPILER_ID:compiler_ids>
-
Новая в версии 3.19.
где
compiler_ids— список, разделённый запятыми.1если идентификатор компилятора ISPC CMake соответствует одному из элементов вcompiler_ids, в противном случае0.
-
$<COMPILE_LANGUAGE> -
Новое в версии 3.3.
Язык компиляции исходных файлов при оценке параметров компиляции. См. соответствующее логическое выражение
$<COMPILE_LANGUAGE:language>для примечаний о переносимости этого выражения генератора.
- $<COMPILE_LANGUAGE:languages>
-
Новое в версии 3.3.
1если язык, используемый для единицы компиляции, соответствует одному из элементов вlanguages, иначе0. Это выражение может использоваться для указания параметров компиляции, определений компиляции и каталогов заголовков для исходных файлов определённого языка в целевом объекте. Например:add_executable(myapp main.cpp foo.c bar.cpp zot.cu) target_compile_options(myapp PRIVATE $<$<COMPILE_LANGUAGE:CXX>:-fno-exceptions> ) target_compile_definitions(myapp PRIVATE $<$<COMPILE_LANGUAGE:CXX>:COMPILING_CXX> $<$<COMPILE_LANGUAGE:CUDA>:COMPILING_CUDA> ) target_include_directories(myapp PRIVATE $<$<COMPILE_LANGUAGE:CXX,CUDA>:/opt/foo/headers> )Это указывает на использование параметра компиляции
-fno-exceptions, определение компиляцииCOMPILING_CXXи каталог заголовковcxx_headersтолько для C++. (Проверки идентификаторов компилятора опущены). Также это указывает определение компиляцииCOMPILING_CUDAдля CUDA.Обратите внимание, что с генераторами Visual Studio и
Xcodeнет способа представить определения компиляции или каталоги заголовков для всего целевого объекта отдельно для языковCиCXX. Также с генераторами Visual Studio нет способа представить флаги целевого объекта отдельно для языковCиCXX. В этих генераторах выражения для исходных файлов C и C++ будут оцениваться с использованиемCXXесли есть исходные файлы C++, и в противном случае с использованиемC. Решение - создать отдельные библиотеки для каждого языка исходных файлов:add_library(myapp_c foo.c) add_library(myapp_cxx bar.cpp) target_compile_options(myapp_cxx PUBLIC -fno-exceptions) add_executable(myapp main.cpp) target_link_libraries(myapp myapp_c myapp_cxx)
-
$<COMPILE_LANG_AND_ID:language,compiler_ids> -
Новое в версии 3.15.
1если язык, используемый для единицы компиляции, соответствуетlanguageи идентификатор компилятора CMake для компилятораlanguageсоответствует одному из элементов вcompiler_ids, иначе0. Это выражение является сокращённой формой комбинации$<COMPILE_LANGUAGE:language>и$<LANG_COMPILER_ID:compiler_ids>. Это выражение может использоваться для указания параметров компиляции, определений компиляции и каталогов заголовков для исходных файлов определённого языка и компилятора в целевом объекте. Например:add_executable(myapp main.cpp foo.c bar.cpp zot.cu) target_compile_definitions(myapp PRIVATE $<$<COMPILE_LANG_AND_ID:CXX,AppleClang,Clang>:COMPILING_CXX_WITH_CLANG> $<$<COMPILE_LANG_AND_ID:CXX,Intel>:COMPILING_CXX_WITH_INTEL> $<$<COMPILE_LANG_AND_ID:C,Clang>:COMPILING_C_WITH_CLANG> )Это указывает на использование различных определений компиляции, основанных как на идентификаторе компилятора, так и на языке компиляции. В этом примере будет использоваться определение компиляции
COMPILING_CXX_WITH_CLANGкогда Clang является компилятором C++, иCOMPILING_CXX_WITH_INTELкогда Intel является компилятором C++. Аналогично, когда компилятор C является Clang, он увидит только определениеCOMPILING_C_WITH_CLANG.Без выражения генератора
COMPILE_LANG_AND_IDта же логика выражалась бы как:target_compile_definitions(myapp PRIVATE $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CXX_COMPILER_ID:AppleClang,Clang>>:COMPILING_CXX_WITH_CLANG> $<$<AND:$<COMPILE_LANGUAGE:CXX>,$<CXX_COMPILER_ID:Intel>>:COMPILING_CXX_WITH_INTEL> $<$<AND:$<COMPILE_LANGUAGE:C>,$<C_COMPILER_ID:Clang>>:COMPILING_C_WITH_CLANG> )
Compile Features
-
$<COMPILE_FEATURES:features> -
Новое в версии 3.1.
где
features- это список, разделённый запятыми. Принимает значение1если всеfeaturesдоступны для целевого объекта 'head', и0в противном случае. Если это выражение используется при оценке реализации связи целевого объекта, и если какая-либо зависимость транзитивно увеличивает требуемыеC_STANDARDилиCXX_STANDARDдля целевого объекта 'head', будет выдано сообщение об ошибке. См. руководствоcmake-compile-features(7)для получения информации о функциях компиляции и списка поддерживаемых компиляторов.
Linker Language And ID
-
$<LINK_LANGUAGE> -
Новое в версии 3.18.
Язык компоновки целевого объекта при оценке параметров компоновки. См. соответствующее логическое выражение
$<LINK_LANGUAGE:languages>для примечаний о переносимости этого выражения генератора.Примечание
Это выражение генератора не поддерживается свойствами библиотек компоновки для предотвращения побочных эффектов из-за двойной оценки этих свойств.
- $<LINK_LANGUAGE:languages>
-
Новое в версии 3.18.
1если язык, используемый для шага компоновки, соответствует одному из элементов вlanguages, иначе0. Это выражение может использоваться для указания библиотек компоновки, параметров компоновки, каталогов компоновки и зависимостей компоновки для определённого языка в целевом объекте. Например:add_library(api_C ...) add_library(api_CXX ...) add_library(api INTERFACE) target_link_options(api INTERFACE $<$<LINK_LANGUAGE:C>:-opt_c> $<$<LINK_LANGUAGE:CXX>:-opt_cxx>) target_link_libraries(api INTERFACE $<$<LINK_LANGUAGE:C>:api_C> $<$<LINK_LANGUAGE:CXX>:api_CXX>) add_executable(myapp1 main.c) target_link_options(myapp1 PRIVATE api) add_executable(myapp2 main.cpp) target_link_options(myapp2 PRIVATE api)Это указывает на использование целевого объекта
apiдля компоновки целевых объектовmyapp1иmyapp2. На практике,myapp1будет компоноваться с целевым объектомapi_Cи параметром-opt_c, потому что он будет использоватьCв качестве языка компоновки. Иmyapp2будет компоноваться сapi_CXXи параметром-opt_cxx, потому чтоCXXбудет языком компоновки.Примечание
Для определения языка компоновки целевого объекта необходимо собрать, транзитивно, все целевые объекты, которые будут компоноваться с ним. Таким образом, для свойств библиотек компоновки будет выполнена двойная оценка. При первой оценке выражения
$<LINK_LANGUAGE:..>всегда возвращают0. Вычисленный язык компоновки после этого первого прохода будет использован для второго прохода. Для предотвращения несоответствий необходимо, чтобы второй проход не изменял язык компоновки. Кроме того, для предотвращения неожиданных побочных эффектов необходимо указывать полные сущности в качестве части выражения$<LINK_LANGUAGE:..>. Например:add_library(lib STATIC file.cxx) add_library(libother STATIC file.c) # bad usage add_executable(myapp1 main.c) target_link_libraries(myapp1 PRIVATE lib$<$<LINK_LANGUAGE:C>:other>) # correct usage add_executable(myapp2 main.c) target_link_libraries(myapp2 PRIVATE $<$<LINK_LANGUAGE:C>:libother>)
В этом примере для
myapp1, первый проход неожиданно определит, что языком компоновки являетсяCXX, так как вычисление выражения генератора будет пустой строкой, поэтомуmyapp1будет зависеть от целевого объектаlib, который являетсяC++. Напротив, дляmyapp2, первая оценка дастCв качестве языка компоновки, поэтому второй проход правильно добавит целевой объектlibotherв качестве зависимости компоновки.
-
$<LINK_LANG_AND_ID:language,compiler_ids> -
Новое в версии 3.18.
1если язык, используемый для шага компоновки, соответствуетlanguageи идентификатор компилятора CMake для линкера языка соответствует одному из элементов вcompiler_ids, иначе0. Это выражение является сокращённой формой комбинации$<LINK_LANGUAGE:language>и$<LANG_COMPILER_ID:compiler_ids>. Это выражение может использоваться для указания библиотек компоновки, параметров компоновки, каталогов компоновки и зависимостей компоновки для определённого языка и компилятора в целевом объекте. Например:add_library(libC_Clang ...) add_library(libCXX_Clang ...) add_library(libC_Intel ...) add_library(libCXX_Intel ...) add_executable(myapp main.c) if (CXX_CONFIG) target_sources(myapp PRIVATE file.cxx) endif() target_link_libraries(myapp PRIVATE $<$<LINK_LANG_AND_ID:CXX,Clang,AppleClang>:libCXX_Clang> $<$<LINK_LANG_AND_ID:C,Clang,AppleClang>:libC_Clang> $<$<LINK_LANG_AND_ID:CXX,Intel>:libCXX_Intel> $<$<LINK_LANG_AND_ID:C,Intel>:libC_Intel>)Это указывает на использование различных библиотек компоновки, основанных как на идентификаторе компилятора, так и на языке компоновки. В этом примере целевой объект
libCXX_Clangбудет зависимостью компоновки, когдаClangилиAppleClangявляется линкеромCXX, иlibCXX_IntelкогдаIntelявляется линкеромCXX. Аналогично, когдаCлинкером являетсяClangилиAppleClang, целевой объектlibC_Clangбудет добавлен в качестве зависимости компоновки иlibC_IntelкогдаIntelявляется линкеромC.См. примечание, относящееся к
$<LINK_LANGUAGE:language>для ограничений использования этого выражения генератора.
Link Features
-
$<LINK_LIBRARY:feature,library-list>
-
Новое в версии 3.24.
Укажите набор библиотек для связи с целевым объектом, а также
feature, который предоставляет информацию о том, как их следует связать. Например:add_library(lib1 STATIC ...) add_library(lib2 ...) target_link_libraries(lib2 PRIVATE "$<LINK_LIBRARY:WHOLE_ARCHIVE,lib1>")
Это указывает, что
lib2должен связаться сlib1и использовать функциюWHOLE_ARCHIVEпри этом.Имена функций чувствительны к регистру и могут содержать только буквы, цифры и символы подчеркивания. Имена функций, определенные в верхнем регистре, зарезервированы для собственных встроенных функций CMake. Предопределённые встроенные функции библиотек:
-
DEFAULT -
Эта функция соответствует стандартной связи, по сути, эквивалентна отсутствию любой функции. Она обычно используется только с целевыми свойствами
LINK_LIBRARY_OVERRIDEиLINK_LIBRARY_OVERRIDE_<LIBRARY>. -
WHOLE_ARCHIVE -
Вынужденное включение всех членов статической библиотеки. Эта функция поддерживается только для следующих платформ с указанными ограничениями:
- Linux.
- Все варианты BSD.
- SunOS.
- Все варианты Apple. Библиотека должна быть указана как имя целевого объекта CMake, имя файла библиотеки (например,
libfoo.a) или путь к файлу библиотеки (например,/path/to/libfoo.a). Из-за ограничения Apple Linker, она не может быть указана как простое имя библиотеки, какfoo, гдеfooне является целевым объектом CMake. - Windows. При использовании MSVC или аналогичной инструментальной цепочки, версия MSVC должна быть больше 1900.
- Cygwin.
- MSYS.
-
FRAMEWORK -
Этот параметр сообщает Linker искать указанный фреймворк, используя параметр Linker
-framework. Он может использоваться только на платформах Apple и только с Linker, понимающим используемый параметр (т. е. Linker, поставляемый с Xcode, или совместимый с ним).Фреймворк может быть указан как целевой объект фреймворка CMake, простое имя фреймворка или путь к файлу. Если указан целевой объект, у этого объекта должно быть установлено целевое свойство
FRAMEWORKв значение true. Для пути к файлу, если он содержит часть каталога, этот каталог будет добавлен в путь поиска фреймворков.add_library(lib SHARED ...) target_link_libraries(lib PRIVATE "$<LINK_LIBRARY:FRAMEWORK,/path/to/my_framework>") # The constructed linker command line will contain: # -F/path/to -framework my_framework
Пути к файлам должны соответствовать одному из следующих шаблонов (
*- это символ подстановки, а необязательные части показаны как[...]):[/path/to/]FwName[.framework][/path/to/]FwName.framework/FwName[/path/to/]FwName.framework/Versions/*/FwName
Обратите внимание, что CMake распознает и автоматически обрабатывает целевые объекты фреймворка, даже без использования выражения
$<LINK_LIBRARY:FRAMEWORK,...>. Выражение генератора всё ещё может быть использовано с целевым объектом CMake, если проект хочет быть явным в этом вопросе, но это не обязательно. Командная строка Linker может иметь некоторые различия между использованием выражения генератора или без него, но конечный результат должен быть одинаковым. С другой стороны, если указан путь к файлу, CMake будет автоматически распознавать некоторые пути, но не все случаи. Проект может использовать$<LINK_LIBRARY:FRAMEWORK,...>для путей к файлам, чтобы ожидаемое поведение было ясным. -
NEEDED_FRAMEWORK -
Это аналогично функции
FRAMEWORK, за исключением того, что это вынуждает Linker связаться с фреймворком даже если из него не используются какие-либо символы. Он использует параметр-needed_frameworkи имеет те же ограничения Linker, что иFRAMEWORK. -
REEXPORT_FRAMEWORK -
Это аналогично функции
FRAMEWORK, за исключением того, что это сообщает Linker, что фреймворк должен быть доступен клиентам, связывающимся с создаваемой библиотекой. Он использует параметр-reexport_frameworkи имеет те же ограничения Linker, что иFRAMEWORK. -
WEAK_FRAMEWORK -
Это аналогично функции
FRAMEWORK, за исключением того, что это вынуждает Linker пометить фреймворк и все ссылки на него как слабые импорты. Он использует параметр-weak_frameworkи имеет те же ограничения Linker, что иFRAMEWORK. -
NEEDED_LIBRARY -
Это аналогично функции
NEEDED_FRAMEWORK, за исключением того, что оно предназначено для использования с целевыми объектами или библиотеками, не являющимися фреймворками (только платформы Apple). Оно использует параметр-needed_libraryили-needed-lпо мере необходимости и имеет те же ограничения Linker, что иNEEDED_FRAMEWORK. -
REEXPORT_LIBRARY -
Это аналогично функции
REEXPORT_FRAMEWORK, за исключением того, что оно предназначено для использования с целевыми объектами или библиотеками, не являющимися фреймворками (только платформы Apple). Оно использует параметр-reexport_libraryили-reexport-lпо мере необходимости и имеет те же ограничения Linker, что иREEXPORT_FRAMEWORK. -
WEAK_LIBRARY -
Это аналогично функции
WEAK_FRAMEWORK, за исключением того, что оно предназначено для использования с целевыми объектами или библиотеками, не являющимися фреймворками (только платформы Apple). Оно использует параметр-weak_libraryили-weak-lпо мере необходимости и имеет те же ограничения Linker, что иWEAK_FRAMEWORK.
Встроенные и пользовательские функции библиотек определяются в терминах следующих переменных:
CMAKE_<LANG>_LINK_LIBRARY_USING_<FEATURE>_SUPPORTEDCMAKE_<LANG>_LINK_LIBRARY_USING_<FEATURE>CMAKE_LINK_LIBRARY_USING_<FEATURE>_SUPPORTEDCMAKE_LINK_LIBRARY_USING_<FEATURE>
Значение, используемое для каждой из этих переменных, - это значение, установленное в конце области каталога, в которой был создан целевой объект. Использование следующее:
- Если языковая переменная
CMAKE_<LANG>_LINK_LIBRARY_USING_<FEATURE>_SUPPORTEDимеет значение true, переменнаяfeatureдолжна быть определена соответствующей переменнойCMAKE_<LANG>_LINK_LIBRARY_USING_<FEATURE>. - Если какая-либо языковая поддержка
featureне поддерживается, то переменнаяCMAKE_LINK_LIBRARY_USING_<FEATURE>_SUPPORTEDдолжна иметь значение true, и переменнаяfeatureдолжна быть определена соответствующей переменнойCMAKE_LINK_LIBRARY_USING_<FEATURE>.
Следует отметить следующие ограничения:
library-listможет указывать целевые объекты или библиотеки CMake. Любой целевой объект CMake типа OBJECT или INTERFACE проигнорирует аспект функции выражения и вместо этого будет связан стандартным способом.- Выражение генератора
$<LINK_LIBRARY:...>может быть использовано только для указания связанных библиотек. На практике это означает, что оно может появляться в целевых свойствахLINK_LIBRARIES,INTERFACE_LINK_LIBRARIESиINTERFACE_LINK_LIBRARIES_DIRECT, и быть указано в командахtarget_link_libraries()иlink_libraries(). - Если выражение генератора
$<LINK_LIBRARY:...>появляется в свойствеINTERFACE_LINK_LIBRARIESцелевого объекта, оно будет включено в импортированный целевой объект, сгенерированный командойinstall(EXPORT). Ответственность по определению функции связи, используемой этим выражением, лежит на окружающей среде, использующей этот импорт. -
Каждый целевой объект или библиотека, участвующая в шаге связи, должны иметь не более одного типа функции библиотеки. Отсутствие функции также несовместимо со всеми другими функциями. Например:
add_library(lib1 ...) add_library(lib2 ...) add_library(lib3 ...) # lib1 will be associated with feature1 target_link_libraries(lib2 PUBLIC "$<LINK_LIBRARY:feature1,lib1>") # lib1 is being linked with no feature here. This conflicts with the # use of feature1 in the line above and would result in an error. target_link_libraries(lib3 PRIVATE lib1 lib2)
Когда невозможно использовать одну и ту же функцию на протяжении всего построения для данного целевого объекта или библиотеки, целевые свойства
LINK_LIBRARY_OVERRIDEиLINK_LIBRARY_OVERRIDE_<LIBRARY>могут быть использованы для разрешения таких несоответствий. - Выражение генератора
$<LINK_LIBRARY:...>не гарантирует, что список указанных целевых объектов и библиотек будет сохранён вместе. Для управления конструкциями, такими как--start-groupи--end-group, которые поддерживаются Linker GNUld, используйте выражение генератораLINK_GROUPвместо этого.
-
-
$<LINK_GROUP:feature,library-list> -
Новое в версии 3.24.
Укажите группу библиотек для связывания с целевым объектом, вместе с
feature, который определяет, как эта группа должна быть связана. Например:add_library(lib1 STATIC ...) add_library(lib2 ...) target_link_libraries(lib2 PRIVATE "$<LINK_GROUP:RESCAN,lib1,external>")
Это указывает, что
lib2должен быть связан сlib1иexternal, и что обе эти библиотеки должны быть включены в командной строке компоновщика в соответствии с определением функцииRESCAN.Имена функций чувствительны к регистру и могут содержать только буквы, цифры и символы подчеркивания. Имена функций, определенные в верхнем регистре, зарезервированы для собственных встроенных функций CMake. В настоящее время существует только одна предопределенная встроенная функция группы:
-
RESCAN -
Некоторые компоновщики работают только в один проход. Для таких компоновщиков циклические ссылки между библиотеками обычно приводят к неразрешенным символам. Эта функция указывает компоновщику многократно искать указанные статические библиотеки до тех пор, пока не будут созданы новые неразрешенные ссылки.
Обычно статическая библиотека ищется только один раз в порядке, в котором она указана в командной строке. Если символ в этой библиотеке необходим для разрешения неразрешенного символа, на который ссылается объект в библиотеке, которая появляется позже в командной строке, компоновщик не сможет разрешить эту ссылку. Группируя статические библиотеки с помощью функции
RESCAN, все они будут многократно просматриваться до тех пор, пока не будут разрешены все возможные ссылки. Это будет использовать такие параметры компоновщика, как--start-groupи--end-group, или на SunOS,-z rescan-startи-z rescan-end.Использование этой функции имеет значительную стоимость производительности. Лучше всего использовать ее только тогда, когда неизбежны циклические ссылки между двумя или более статическими библиотеками.
Эта функция доступна при использовании инструментальных цепочек, нацеленных на Linux, BSD и SunOS. Она также может быть использована при нацеливании на платформы Windows, если используется инструментальная цепочка GNU.
Встроенные и настраиваемые функции группы определяются в терминах следующих переменных:
CMAKE_<LANG>_LINK_GROUP_USING_<FEATURE>_SUPPORTEDCMAKE_<LANG>_LINK_GROUP_USING_<FEATURE>CMAKE_LINK_GROUP_USING_<FEATURE>_SUPPORTEDCMAKE_LINK_GROUP_USING_<FEATURE>
Значение, используемое для каждой из этих переменных, — это значение, установленное в конце области каталога, в которой был создан целевой объект. Использование выглядит следующим образом:
- Если языковая переменная
CMAKE_<LANG>_LINK_GROUP_USING_<FEATURE>_SUPPORTEDимеет значение true, то переменнаяfeatureдолжна быть определена соответствующей переменнойCMAKE_<LANG>_LINK_GROUP_USING_<FEATURE>. - Если для языка не поддерживается
feature, то переменнаяCMAKE_LINK_GROUP_USING_<FEATURE>_SUPPORTEDдолжна иметь значение true, а переменнаяfeatureдолжна быть определена соответствующей переменнойCMAKE_LINK_GROUP_USING_<FEATURE>.
Выражение генератора
LINK_GROUPсовместимо с выражением генератораLINK_LIBRARY. Библиотеки, участвующие в группе, могут быть указаны с помощью выражения генератораLINK_LIBRARY.Каждый целевой объект или внешняя библиотека, участвующая в шаге связывания, может быть частью нескольких групп, но только если все участвующие группы указывают один и тот же
feature. Такие группы не будут объединены в командной строке компоновщика, отдельные группы все равно будут сохранены. Смешивание различных функций групп для одного и того же целевого объекта или библиотеки запрещено.add_library(lib1 ...) add_library(lib2 ...) add_library(lib3 ...) add_library(lib4 ...) add_library(lib5 ...) target_link_libraries(lib3 PUBLIC "$<LINK_GROUP:feature1,lib1,lib2>") target_link_libraries(lib4 PRIVATE "$<LINK_GROUP:feature1,lib1,lib3>") # lib4 will be linked with the groups {lib1,lib2} and {lib1,lib3}. # Both groups specify the same feature, so this is fine. target_link_libraries(lib5 PRIVATE "$<LINK_GROUP:feature2,lib1,lib3>") # An error will be raised here because both lib1 and lib3 are part of two # groups with different features.Если целевой объект или внешняя библиотека участвует в шаге связывания как часть группы и также не входит в какую-либо группу, любое появление элемента связывания, не относящегося к группе, будет заменено группами, к которым он принадлежит.
add_library(lib1 ...) add_library(lib2 ...) add_library(lib3 ...) add_library(lib4 ...) target_link_libraries(lib3 PUBLIC lib1) target_link_libraries(lib4 PRIVATE lib3 "$<LINK_GROUP:feature1,lib1,lib2>") # lib4 will only be linked with lib3 and the group {lib1,lib2}Поскольку
lib1входит в группу, определенную дляlib4, эта группа затем применяется к использованиюlib1дляlib3. Конечный результат будет таким, как если бы отношение связывания дляlib3было указано как:target_link_libraries(lib3 PUBLIC "$<LINK_GROUP:feature1,lib1,lib2>")
Обратите внимание, что приоритет группы над элементом связывания, не относящимся к группе, может привести к циклическим зависимостям между группами. Если это произойдёт, возникает ошибка, так как циклические зависимости для групп недопустимы.
add_library(lib1A ...) add_library(lib1B ...) add_library(lib2A ...) add_library(lib2B ...) add_library(lib3 ...) # Non-group linking relationships, these are non-circular so far target_link_libraries(lib1A PUBLIC lib2A) target_link_libraries(lib2B PUBLIC lib1B) # The addition of these groups creates circular dependencies target_link_libraries(lib3 PRIVATE "$<LINK_GROUP:feat,lib1A,lib1B>" "$<LINK_GROUP:feat,lib2A,lib2B>" )
Из-за групп, определённых для
lib3, отношения связывания дляlib1Aиlib2Bфактически расширяются до эквивалента:target_link_libraries(lib1A PUBLIC "$<LINK_GROUP:feat,lib2A,lib2B>") target_link_libraries(lib2B PUBLIC "$<LINK_GROUP:feat,lib1A,lib1B>")
Это создает циклическую зависимость между группами:
lib1A --> lib2B --> lib1A.Также следует учитывать следующие ограничения:
library-listможет указывать целевые объекты или библиотеки CMake. Любой целевой объект CMake типа OBJECT или INTERFACE проигнорирует аспект функции выражения и вместо этого будет связан стандартным способом.- Выражение генератора
$<LINK_GROUP:...>может использоваться только для указания библиотек связывания. На практике это означает, что оно может появляться в свойствах целевого объектаLINK_LIBRARIES,INTERFACE_LINK_LIBRARIESиINTERFACE_LINK_LIBRARIES_DIRECT, и быть указанным в командахtarget_link_libraries()иlink_libraries(). - Если выражение генератора
$<LINK_GROUP:...>появляется в свойствеINTERFACE_LINK_LIBRARIESцелевого объекта, оно будет включено в импортированный целевой объект, сгенерированный командойinstall(EXPORT). Ответственность по определению функции связывания, используемой этим выражением, лежит на среде, потребляющей этот импорт.
-
Контекст связывания
-
$<LINK_ONLY:...> -
Новое в версии 3.1.
Содержимое
..., за исключением сбора Требований к использованию зависимостей, в этом случае это пустая строка. Это предназначено для использования в свойстве целевого объектаINTERFACE_LINK_LIBRARIES, обычно заполняемом командойtarget_link_libraries(), для указания частных зависимостей связывания без других требований к использованию.Новое в версии 3.24:
LINK_ONLYтакже может быть использовано в свойстве целевого объектаLINK_LIBRARIES. См. политикуCMP0131.
-
$<DEVICE_LINK:list> -
Новое в версии 3.18.
Возвращает список, если это этап связывания устройства, в противном случае пустой список. Этап связывания устройства контролируется свойствами
CUDA_SEPARABLE_COMPILATIONиCUDA_RESOLVE_DEVICE_SYMBOLSи политикойCMP0105. Это выражение может использоваться только для указания параметров связывания.
-
$<HOST_LINK:list> -
Новое в версии 3.18.
Возвращает список, если это обычная стадия линковки, в противном случае пустой список. Это выражение полезно в основном, когда также участвует стадия линковки устройства (см. выражение генератора
$<DEVICE_LINK:list>). Это выражение можно использовать только для указания параметров линковки.
Зависимые от целевых выражения
Эти запросы относятся к целевому tgt. Если не указано иное, это может быть любой артефакт выполнения, а именно:
- Целевой исполняемый файл, созданный с помощью
add_executable(). - Целевой общий модуль (
.so,.dllно не их.libимпортная библиотека) созданный с помощьюadd_library(). - Целевой статический модуль, созданный с помощью
add_library().
В дальнейшем фраза «имя файла целевого исполняемого файла» означает имя файла двоичного файла целевого исполняемого файла. Это следует отличать от фразы «имя целевого объекта», которая просто представляет собой строку tgt.
-
$<TARGET_EXISTS:tgt> -
Новое в версии 3.12.
1еслиtgtсуществует как целевой объект CMake, иначе0.
-
$<TARGET_NAME_IF_EXISTS:tgt> -
Новое в версии 3.12.
Имя целевого объекта
tgtесли целевой объект существует, в противном случае пустая строка.Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение.
-
$<TARGET_NAME:...> -
Помечает
...как имя целевого объекта. Это требуется при экспорте целевых объектов в несколько зависимых наборов экспорта....должно быть буквальным именем целевого объекта, оно не может содержать выражения генератора.
-
$<TARGET_PROPERTY:tgt,prop> -
Значение свойства
propдля целевого объектаtgt.Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение.
- $<TARGET_PROPERTY:prop>
-
Значение свойства
propдля целевого объекта, для которого вычисляется выражение. Обратите внимание, что для выражений генератора в Требования к использованию целевого объекта это целевой объект, использующий требование, а не целевой объект, определяющий требование.
-
$<TARGET_OBJECTS:tgt> -
Новое в версии 3.1.
Список объектов, полученных в результате построения
tgt. Это обычно используется для целевых объектов библиотека объектов.
-
$<TARGET_POLICY:policy> -
1еслиpolicyбылоNEWпри создании целевого объекта 'head', иначе0. Еслиpolicyне было установлено, будет выведено сообщение об ошибке для политики. Это выражение генератора работает только для подмножества политик.
-
$<TARGET_FILE:tgt> -
Полный путь к файлу двоичного файла целевого объекта.
Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение, если выражение не используется вadd_custom_command()илиadd_custom_target().
-
$<TARGET_FILE_BASE_NAME:tgt> -
Новое в версии 3.15.
Базовое имя
tgt, т.е.$<TARGET_FILE_NAME:tgt>без префикса и суффикса. Например, если имя файла целевого объекта —libbase.so, базовое имя —base.См. также свойства целевого объекта
OUTPUT_NAME,ARCHIVE_OUTPUT_NAME,LIBRARY_OUTPUT_NAMEиRUNTIME_OUTPUT_NAMEи их конфигурационно-специфичные вариантыOUTPUT_NAME_<CONFIG>,ARCHIVE_OUTPUT_NAME_<CONFIG>,LIBRARY_OUTPUT_NAME_<CONFIG>иRUNTIME_OUTPUT_NAME_<CONFIG>.Свойства целевого объекта
<CONFIG>_POSTFIXиDEBUG_POSTFIXтакже могут быть рассмотрены.Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение.
-
$<TARGET_FILE_PREFIX:tgt> -
Новое в версии 3.15.
Префикс имени файла целевого объекта (например,
lib).См. также свойство целевого объекта
PREFIX.Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение.
-
$<TARGET_FILE_SUFFIX:tgt> -
Новое в версии 3.15.
Суффикс имени файла целевого объекта (расширение, например,
.soили.exe).См. также свойство целевого объекта
SUFFIX.Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение.
-
$<TARGET_FILE_NAME:tgt> -
Имя файла целевого объекта.
Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение (см. политикуCMP0112).
-
$<TARGET_FILE_DIR:tgt> -
Директория файла двоичного файла целевого объекта.
Обратите внимание, что
tgtне добавляется в качестве зависимости от целевого объекта, для которого вычисляется это выражение (см. политикуCMP0112).
-
$<TARGET_LINKER_FILE:tgt> -
Файл, используемый при линковке с целевым объектом
tgt. Обычно это будет библиотека, которуюtgtпредставляет (.a,.lib,.so). Но для общего модуля на платформах DLL это будет импортная библиотека DLL, связанная с DLL.
-
$<TARGET_LINKER_FILE_BASE_NAME:tgt> -
Новое в версии 3.15.
Базовое имя файла, используемого для линковки целевого объекта
tgt, т.е.$<TARGET_LINKER_FILE_NAME:tgt>без префикса и суффикса. Например, если имя целевого файлаlibbase.a, то базовое имяbase.См. также свойства целевого объекта
OUTPUT_NAME,ARCHIVE_OUTPUT_NAMEиLIBRARY_OUTPUT_NAMEи их конфигурационно-специфичные вариантыOUTPUT_NAME_<CONFIG>,ARCHIVE_OUTPUT_NAME_<CONFIG>иLIBRARY_OUTPUT_NAME_<CONFIG>.Также можно учитывать свойства целевого объекта
<CONFIG>_POSTFIXиDEBUG_POSTFIX.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение.
-
$<TARGET_LINKER_FILE_PREFIX:tgt> -
Новое в версии 3.15.
Префикс имени файла, используемого для линковки целевого объекта
tgt.См. также свойства целевого объекта
PREFIXиIMPORT_PREFIX.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение.
-
$<TARGET_LINKER_FILE_SUFFIX:tgt> -
Новое в версии 3.15.
Суффикс имени файла, используемого для линковки, где
tgt— имя целевого объекта.Суффикс соответствует расширению файла (например, ".so" или ".lib").
См. также свойства целевого объекта
SUFFIXиIMPORT_SUFFIX.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение.
-
$<TARGET_LINKER_FILE_NAME:tgt> -
Имя файла, используемого для линковки целевого объекта
tgt.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_LINKER_FILE_DIR:tgt> -
Директория файла, используемого для линковки целевого объекта
tgt.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_SONAME_FILE:tgt> -
Файл с именем soname (
.so.3) гдеtgt- имя целевого объекта.
-
$<TARGET_SONAME_FILE_NAME:tgt> -
Имя файла с именем soname (
.so.3).Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_SONAME_FILE_DIR:tgt> -
Директория файла с именем soname (
.so.3).Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_PDB_FILE:tgt> -
Новое в версии 3.1.
Полный путь к файлу базы данных программы (.pdb), сгенерированной линковщиком, где
tgt- имя целевого объекта.См. также свойства целевого объекта
PDB_NAMEиPDB_OUTPUT_DIRECTORYи их конфигурационно-специфичные вариантыPDB_NAME_<CONFIG>иPDB_OUTPUT_DIRECTORY_<CONFIG>.
-
$<TARGET_PDB_FILE_BASE_NAME:tgt> -
Новое в версии 3.15.
Базовое имя файла базы данных программы (.pdb), сгенерированной линковщиком, где
tgt- имя целевого объекта.Базовое имя соответствует имени файла PDB целевого объекта (см.
$<TARGET_PDB_FILE_NAME:tgt>) без префикса и суффикса. Например, если имя целевого файлаbase.pdb, то базовое имяbase.См. также свойство целевого объекта
PDB_NAMEи его конфигурационно-специфичный вариантPDB_NAME_<CONFIG>.Также можно учитывать свойства целевого объекта
<CONFIG>_POSTFIXиDEBUG_POSTFIX.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение.
-
$<TARGET_PDB_FILE_NAME:tgt> -
Новое в версии 3.1.
Имя файла базы данных программы (.pdb), сгенерированной линковщиком.
Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_PDB_FILE_DIR:tgt> -
Новое в версии 3.1.
Директория файла базы данных программы (.pdb), сгенерированной линковщиком.
Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_BUNDLE_DIR:tgt> -
Новое в версии 3.9.
Полный путь к папке с пакетом (
/path/to/my.app,/path/to/my.framework, или/path/to/my.bundle), гдеtgt- имя целевого объекта.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_BUNDLE_DIR_NAME:tgt> -
Новое в версии 3.24.
Имя папки с пакетом (
my.app,my.framework, илиmy.bundle), гдеtgt- имя целевого объекта.Обратите внимание, что
tgtне добавляется в качестве зависимости целевого объекта, для которого вычисляется данное выражение (см. политикуCMP0112).
-
$<TARGET_BUNDLE_CONTENT_DIR:tgt> -
Новое в версии 3.9.
Полный путь к каталогу с содержимым пакета, где
tgt— имя целевого объекта. Для macOS SDK он ведет к/path/to/my.app/Contents,/path/to/my.framework, или/path/to/my.bundle/Contents. Для всех остальных SDK (например, iOS) он ведет к/path/to/my.app,/path/to/my.framework, или/path/to/my.bundleиз-за плоской структуры пакета.Обратите внимание, что
tgtне добавляется как зависимость целевого объекта, к которому применяется данное выражение (см. политикуCMP0112).
-
$<TARGET_RUNTIME_DLLS:tgt> -
Новое в версии 3.21.
Список DLL, от которых зависит целевой объект во время выполнения. Это определяется расположением всех
SHAREDцелевых объектов в транзитивных зависимостях целевого объекта. Использование этого генератора выражений для объектов, отличных от исполняемых файлов,SHAREDбиблиотек иMODULEбиблиотек, является ошибкой. В платформах, не поддерживающих DLL, это выражение всегда вычисляется как пустая строка.Это генераторское выражение может использоваться для копирования всех DLL, от которых зависит целевой объект, в каталог вывода с помощью пользовательской команды
POST_BUILD. Например:find_package(foo CONFIG REQUIRED) # package generated by install(EXPORT) add_executable(exe main.c) target_link_libraries(exe PRIVATE foo::foo foo::bar) add_custom_command(TARGET exe POST_BUILD COMMAND ${CMAKE_COMMAND} -E copy $<TARGET_RUNTIME_DLLS:exe> $<TARGET_FILE_DIR:exe> COMMAND_EXPAND_LISTS )Примечание
Импортированные целевые объекты поддерживаются только в том случае, если они знают расположение своих
.dllфайлов. ИмпортированнаяSHAREDбиблиотека должна иметь свойствоIMPORTED_LOCATIONустановленным на свой.dllфайл. Подробности см. в разделе add_library импортированные библиотеки. Многие модули Поиск модулей генерируют импортированные целевые объекты типаUNKNOWNи поэтому будут проигнорированы.
Выражения экспорта и установки
-
$<INSTALL_INTERFACE:...> -
Содержимое
...при экспорте свойства с помощьюinstall(EXPORT), в противном случае пустая строка.
-
$<BUILD_INTERFACE:...> -
Содержимое
...при экспорте свойства с помощьюexport()или при использовании целевого объекта другой целью в том же наборе инструментов сборки. В противном случае выводится пустая строка.
-
$<INSTALL_PREFIX> -
Содержимое префикса установки, когда целевой объект экспортирован через
install(EXPORT), или когда он вычисляется в свойствеINSTALL_NAME_DIRили аргументеINSTALL_NAME_DIRкомандыinstall(RUNTIME_DEPENDENCY_SET), в противном случае пустая строка.
Многоуровневая оценка выражений
-
$<GENEX_EVAL:expr> -
Новое в версии 3.12.
Содержимое
exprвычисляется как генераторское выражение в текущем контексте. Это позволяет использовать генераторские выражения, результаты которых являются генераторскими выражениями.
-
$<TARGET_GENEX_EVAL:tgt,expr> -
Новое в версии 3.12.
Содержимое
exprвычисляется как генераторское выражение в контексте целевого объектаtgt. Это позволяет использовать пользовательские свойства целевых объектов, которые сами содержат генераторские выражения.Возможность вычисления генераторских выражений очень полезна, когда требуется управлять пользовательскими свойствами, поддерживающими генераторские выражения. Например:
add_library(foo ...) set_property(TARGET foo PROPERTY CUSTOM_KEYS $<$<CONFIG:DEBUG>:FOO_EXTRA_THINGS> ) add_custom_target(printFooKeys COMMAND ${CMAKE_COMMAND} -E echo $<TARGET_PROPERTY:foo,CUSTOM_KEYS> )Эта упрощенная реализация пользовательской команды
printFooKeysневерна, потому что свойство целевого объектаCUSTOM_KEYSне вычисляется, и содержимое передается как есть (то есть$<$<CONFIG:DEBUG>:FOO_EXTRA_THINGS>).Для получения ожидаемого результата (то есть
FOO_EXTRA_THINGSесли config —Debug) необходимо вычислить результат$<TARGET_PROPERTY:foo,CUSTOM_KEYS>.add_custom_target(printFooKeys COMMAND ${CMAKE_COMMAND} -E echo $<TARGET_GENEX_EVAL:foo,$<TARGET_PROPERTY:foo,CUSTOM_KEYS>> )
Символы с экранированием
Эти выражения вычисляются как конкретные строковые литералы. Используйте их вместо фактического строкового литерала, когда необходимо предотвратить их специальное значение.
-
$<ANGLE-R> -
Литеральный
>. Используется, например, для сравнения строк, содержащих>.
-
$<COMMA> -
Литеральный
,. Используется, например, для сравнения строк, содержащих,.
-
$<SEMICOLON> -
Литеральный
;. Используется для предотвращения расширения списка в аргументе с;.
Устаревшие выражения
-
$<CONFIGURATION> -
Имя конфигурации. Устарело с CMake 3.0. Используйте
CONFIGвместо него.
© 2000–2022 Kitware, Inc. and Contributors
Licensed under the BSD 3-clause License.
https://cmake.org/cmake/help/v3.24/manual/cmake-generator-expressions.7.html