Spec-Zone.ru › CMake 3.21

cmake-language(7)

  • Организация

    • Директории
    • Скрипты
    • Модули
  • Синтаксис

    • Кодировка
    • Файлы исходного кода
    • Вызовы команд
    • Аргументы команд

      • Аргумент в квадратных скобках
      • Аргумент в кавычках
      • Незаданный аргумент
    • Последовательности экранирования
    • Ссылки на переменные
    • Комментарии

      • Комментарий в квадратных скобках
      • Комментарий в строке
  • Управляющие структуры

    • Условные блоки
    • Циклы
    • Определения команд
  • Переменные
  • Переменные среды
  • Списки

Организация

Файлы входных данных CMake написаны на языке "CMake Language" в файлах исходного кода, названных CMakeLists.txt или заканчивающихся на .cmake расширение имени файла.

Файлы исходного кода CMake Language в проекте организованы в:

  • Директории (CMakeLists.txt),
  • Скрипты (<script>.cmake), и
  • Модули (<module>.cmake).

Директории

При обработке CMake проекта исходного дерева, точкой входа является файл исходного кода, называемый CMakeLists.txt в корневой директории исходного кода. Этот файл может содержать всю спецификацию сборки или использовать команду add_subdirectory() для добавления поддиректорий к сборке. Каждая поддиректория, добавленная командой, также должна содержать файл CMakeLists.txt в качестве точки входа в эту директорию. Для каждой исходной директории, файл CMakeLists.txt которой обрабатывается CMake, генерируется соответствующая директория в дереве сборки, которая служит в качестве рабочей и выходной директории по умолчанию.

Скрипты

Индивидуальный файл исходного кода <script>.cmake может быть обработан в режиме скрипта, используя утилиту командной строки cmake(1) с опцией -P. Режим скрипта просто выполняет команды в данном файле исходного кода CMake Language и не генерирует систему сборки. Он не позволяет использовать команды CMake, которые определяют цели сборки или действия.

Модули

Код CMake Language в директориях Директориях или скриптах Скриптах может использовать команду include() для загрузки файла исходного кода <module>.cmake в контексте включающего кода. Смотрите страницу справочника cmake-modules(7) для документации по модулям, включенным в дистрибутив CMake. Деревья исходного кода проектов также могут предоставлять собственные модули и указывать их расположение(я) в переменной CMAKE_MODULE_PATH.

Синтаксис

Кодировка

Файл исходного кода CMake Language может быть написан в тексте 7-битного ASCII для максимальной портативности на всех поддерживаемых платформах. Новые строки могут быть закодированы как \n или \r\n, но будут преобразованы в \n при чтении файлов-входов.

Обратите внимание, что реализация 8-битная, поэтому файлы исходного кода могут быть закодированы в UTF-8 на платформах с системами API, поддерживающими эту кодировку. Кроме того, CMake 3.2 и выше поддерживают файлы исходного кода, закодированные в UTF-8 в Windows (используя UTF-16 для вызова системных API). Кроме того, CMake 3.0 и выше допускают ведущий UTF-8 Byte-Order Mark в файлах исходного кода.

Файлы исходного кода

Файл исходного кода CMake Language состоит из нуля или более Вызовов команд, разделенных новыми строками и, необязательно, пробелами и Комментариями:

file         ::=  file_element*
file_element ::=  command_invocation line_ending |
                  (bracket_comment|space)* line_ending
line_ending  ::=  line_comment? newline
space        ::=  <match '[ \t]+'>
newline      ::=  <match '\n'>

Обратите внимание, что любая строка файла исходного кода, не находящаяся внутри Аргументов команд или Комментария в квадратных скобках, может оканчиваться Комментарий в строке.

Вызовы команд

Вызов команды — это имя, за которым следуют заключенные в скобки аргументы, разделенные пробелами:

command_invocation  ::=  space* identifier space* '(' arguments ')'
identifier          ::=  <match '[A-Za-z_][A-Za-z0-9_]*'>
arguments           ::=  argument? separated_arguments*
separated_arguments ::=  separation+ argument? |
                         separation* '(' arguments ')'
separation          ::=  space | line_ending

Например:

add_executable(hello world.c)

Имена команд нечувствительны к регистру. Вложенные незакрытые скобки в аргументах должны быть сбалансированы. Каждый ( или ) передаётся вызову команды как литеральный Незаданный аргумент. Это может использоваться в вызовах команды if() для заключения условий. Например:

if(FALSE AND (FALSE OR TRUE)) # evaluates to FALSE

Примечание

Версии CMake до 3.0 требуют, чтобы идентификаторы имен команд содержали не менее 2 символов.

Версии CMake до 2.8.12 молчаливо принимают Незаданный аргумент или Аргумент в кавычках сразу после Аргумента в кавычках и не разделенные пробелами. Для совместимости CMake 2.8.12 и выше принимают такой код, но выдают предупреждение.

Аргументы команд

Существует три типа аргументов в Вызовах команд:

argument ::=  bracket_argument | quoted_argument | unquoted_argument

Аргумент в квадратных скобках

Аргумент в квадратных скобках, вдохновленный синтаксисом длинных скобок Lua, заключает содержимое в открывающие и закрывающие "скобки" одинаковой длины:

bracket_argument ::=  bracket_open bracket_content bracket_close
bracket_open     ::=  '[' '='* '['
bracket_content  ::=  <any text not containing a bracket_close with
                       the same number of '=' as the bracket_open>
bracket_close    ::=  ']' '='* ']'

Открывающая скобка записывается как [ , за которой следуют ноль или более = , а затем [. Соответствующая закрывающая скобка записывается как ] , за которой следует то же количество = , а затем ]. Скобки не вложены. Для содержащихся скобок всегда можно выбрать уникальную длину.

Содержимое аргумента в квадратных скобках состоит из всего текста между открывающей и закрывающей скобками, за исключением того, что одна новая строка сразу после открывающей скобки, если она есть, игнорируется. Никакой оценки заключённого содержимого, такого как Последовательности экранирования или Ссылки на переменные, не выполняется. Аргумент в квадратных скобках всегда передаётся вызову команды как ровно один аргумент.

Например:

message([=[
This is the first line in a bracket argument with bracket length 1.
No \-escape sequences or ${variable} references are evaluated.
This is always one argument even though it contains a ; character.
The text does not end on a closing bracket of length 0 like ]].
It does end in a closing bracket of length 1.
]=])

Примечание

Версии CMake до 3.0 не поддерживают аргументы в квадратных скобках. Они интерпретируют открывающую скобку как начало Незаданного аргумента.

Аргумент в кавычках

Аргумент в кавычках заключает содержимое между открывающими и закрывающими двойными кавычками:

quoted_argument     ::=  '"' quoted_element* '"'
quoted_element      ::=  <any character except '\' or '"'> |
                         escape_sequence |
                         quoted_continuation
quoted_continuation ::=  '\' newline

Содержимое аргумента в кавычках состоит из всего текста между открывающей и закрывающей кавычками. Оба Последовательности экранирования и Ссылки на переменные оцениваются. Аргумент в кавычках всегда передаётся вызову команды как ровно один аргумент.

Например:

message("This is a quoted argument containing multiple lines.
This is always one argument even though it contains a ; character.
Both \\-escape sequences and ${variable} references are evaluated.
The text does not end on an escaped double-quote like \".
It does end in an unescaped double quote.
")

Конечный \ в любой строке, заканчивающейся нечётным количеством обратных слэшей, обрабатывается как продолжение строки и игнорируется вместе с последующим символом новой строки. Например:

message("\
This is the first line of a quoted argument. \
In fact it is the only line but since it is long \
the source code uses line continuation.\
")

Примечание

Версии CMake до 3.0 не поддерживают продолжение с \. Они сообщают об ошибках в аргументах в кавычках, содержащих строки, заканчивающиеся нечётным количеством \ символов.

Незаданный аргумент

Незаданный аргумент не заключён в какой-либо синтаксис цитирования. Он не может содержать пробелы, (, ), #, ", или \ за исключением случаев, когда они экранированы обратным слэшем:

unquoted_argument ::=  unquoted_element+ | unquoted_legacy
unquoted_element  ::=  <any character except whitespace or one of '()#"\'> |
                       escape_sequence
unquoted_legacy   ::=  <see note in text>

Содержимое незаданного аргумента состоит из всего текста в непрерывном блоке разрешённых или экранированных символов. Оба Последовательности экранирования и Ссылки на переменные оцениваются. Результирующее значение делится таким же образом, как Списки делятся на элементы. Каждый ненулевой элемент передаётся вызову команды как аргумент. Таким образом, незаданный аргумент может быть передан вызову команды как ноль или более аргументов.

Например:

foreach(arg
    NoSpace
    Escaped\ Space
    This;Divides;Into;Five;Arguments
    Escaped\;Semicolon
    )
  message("${arg}")
endforeach()

Примечание

Для поддержки устаревшего кода CMake, не заключённые в кавычки аргументы также могут содержать двойные кавычки ("...", возможно, заключающие горизонтальные пробелы), и ссылки на переменные в стиле make ($(MAKEVAR)).

Неэкранированные двойные кавычки должны быть сбалансированы, не могут появляться в начале не заключённого в кавычки аргумента и рассматриваются как часть содержимого. Например, не заключённые в кавычки аргументы -Da="b c", -Da=$(v), и a" "b"c"d интерпретируются буквально. Вместо этого они могут быть записаны как аргументы в кавычках "-Da=\"b c\"", "-Da=$(v)", и "a\" \"b\"c\"d", соответственно.

Ссылки в стиле make рассматриваются буквально как часть содержимого и не подвергаются расширению переменных. Они обрабатываются как часть одного аргумента (а не как отдельные $, (, MAKEVAR, и ) аргументов).

Вышеупомянутое "unquoted_legacy" производство представляет такие аргументы. Мы не рекомендуем использовать устаревшие не заключённые в кавычки аргументы в новом коде. Вместо этого используйте аргумент в кавычках или аргумент в квадратных скобках для представления содержимого.

Последовательности экранирования

Последовательность экранирования - это \ за которым следует один символ:

escape_sequence  ::=  escape_identity | escape_encoded | escape_semicolon
escape_identity  ::=  '\' <match '[^A-Za-z0-9;]'>
escape_encoded   ::=  '\t' | '\r' | '\n'
escape_semicolon ::=  '\;'

\ за которым следует не буквенно-цифровой символ, просто кодирует буквальный символ без его интерпретации как синтаксиса. \t, \r, или \n кодируют соответственно символ табуляции, возврата каретки или новой строки. \; вне любых ссылок на переменные кодирует себя, но может использоваться в не заключенном в кавычки аргументе, чтобы закодировать ; без разделения значения аргумента на нем. \; внутри ссылок на переменные кодирует буквальный символ ;. (См. также политику CMP0053 документацию для исторических соображений.)

Ссылки на переменные

Ссылка на переменную имеет вид ${<variable>} и вычисляется внутри аргумента в кавычках или не заключённого в кавычки аргумента. Ссылка на переменную заменяется значением переменной или пустой строкой, если переменная не задана. Ссылки на переменные могут быть вложены и вычисляются изнутри наружу, например, ${outer_${inner_variable}_variable}.

Буквальные ссылки на переменные могут состоять из буквенно-цифровых символов, символов /_.+-, и последовательностей экранирования. Вложенные ссылки могут использоваться для вычисления переменных любого имени. См. также политику CMP0053 документацию для исторических соображений и причин, по которым $ также технически разрешен, но не рекомендуется.

Раздел Переменные документирует область имен переменных и то, как устанавливаются их значения.

Ссылка на переменную среды имеет вид $ENV{<variable>}. См. раздел Переменные среды для получения дополнительной информации.

Ссылка на переменную кеша имеет вид $CACHE{<variable>}. См. CACHE для получения дополнительной информации.

Команда if() имеет специальный синтаксис условия, который позволяет использовать ссылки на переменные в сокращенной форме <variable> вместо ${<variable>}. Однако переменные среды и кеша всегда должны ссылаться как $ENV{<variable>} или $CACHE{<variable>}.

Комментарии

Комментарий начинается с символа #, который не находится внутри аргумента в квадратных скобках, аргумента в кавычках или экранирован с \ как частью не заключенного в кавычки аргумента. Существуют два типа комментариев: комментарий в квадратных скобках и комментарий в строке.

Комментарий в квадратных скобках

# сразу после bracket_open образует комментарий в квадратных скобках, состоящий из всего содержимого скобок:

bracket_comment ::=  '#' bracket_argument

Например:

#[[This is a bracket comment.
It runs until the close bracket.]]
message("First Argument\n" #[[Bracket Comment]] "Second Argument")

Примечание

Версии CMake, предшествующие 3.0, не поддерживают комментарии в квадратных скобках. Они интерпретируют открывающую # как начало комментария в строке.

Комментарий в строке

# не сразу после bracket_open образует комментарий в строке, который продолжается до конца строки:

line_comment ::=  '#' <any text not starting in a bracket_open
                       and not containing a newline>

Например:

# This is a line comment.
message("First Argument\n" # This is a line comment :)
        "Second Argument") # This is a line comment.

Структуры управления

Условные блоки

Команды if()/elseif()/else()/endif() ограничивают блоки кода, которые должны выполняться условно.

Циклы

Команды foreach()/endforeach() и while()/endwhile() ограничивают блоки кода, которые должны выполняться в цикле. Внутри таких блоков команда break() может быть использована для преждевременного завершения цикла, а команда continue() может быть использована для немедленного перехода к следующей итерации.

Определения команд

Команды macro()/endmacro() и function()/endfunction() ограничивают блоки кода, которые должны записываться для последующего вызова как команды.

Переменные

Переменные - это базовая единица хранения в языке CMake. Их значения всегда являются строками, хотя некоторые команды могут интерпретировать строки как значения других типов. Команды set() и unset() явно устанавливают или сбрасывают переменную, но и другие команды имеют семантику, которая также изменяет переменные. Имена переменных чувствительны к регистру и могут состоять практически из любого текста, но мы рекомендуем использовать имена, состоящие только из буквенно-цифровых символов плюс _ и -.

Переменные имеют динамическую область действия. Каждое «установка» или «сброс» переменной создаёт связывание в текущей области действия:

Область действия функции

Определения команд, созданные командой function(), создают команды, которые при вызове обрабатывают записанные команды в новой области действия связывания переменных. Установка или сброс переменной связывается в этой области действия и виден для текущей функции и любых вложенных вызовов внутри неё, но не после возвращения из функции.

Область действия каталога

Каждый из каталогов в дереве исходных кодов имеет свои собственные связывания переменных. Перед обработкой файла CMakeLists.txt для каталога CMake копирует все связывания переменных, которые в данный момент определены в родительском каталоге, если таковые имеются, для инициализации новой области действия каталога. CMake скрипты, при обработке с cmake -P, связывают переменные в одной области действия «каталога».

Установка или сброс переменной, не находящейся внутри вызова функции, связывает переменную с текущей областью действия каталога.

Постоянный кеш

CMake хранит отдельный набор «переменных кеша» или «записей кеша», значения которых сохраняются между несколькими запусками в дереве сборки проекта. Записи кеша имеют изолированную область действия связывания, изменяемую только по явному запросу, например, опцией CACHE команд set() и unset().

При оценке ссылок на переменные, CMake сначала ищет привязку в стеке вызовов функций (если таковой имеется), а затем переходит к привязке в области текущего каталога (если таковая имеется). Если найдена привязка «set», используется её значение. Если найдена привязка «unset» или привязка вообще не найдена, CMake ищет запись в кэше. Если запись в кэше найдена, используется её значение. В противном случае ссылка на переменную оценивается как пустая строка. Синтаксис $CACHE{VAR} может использоваться для непосредственного поиска записей в кэше.

В руководстве cmake-variables(7) описаны многие переменные, предоставляемые CMake или имеющие значение для CMake при установке кодом проекта.

Примечание

CMake резервирует идентификаторы, которые:

  • начинаются с CMAKE_ (с прописными, строчными или смешанными регистрами), или
  • начинаются с _CMAKE_ (с прописными, строчными или смешанными регистрами), или
  • начинаются с _, за которым следует имя любой CMake Command.

Переменные среды

Переменные среды похожи на обычные переменные, но имеют следующие отличия:

Область действия

Переменные среды имеют глобальную область действия в процессе CMake. Они никогда не кэшируются.

Ссылки

Ссылки на переменные имеют вид $ENV{<variable>}.

Инициализация

Начальные значения переменных среды CMake — это значения вызывающего процесса. Значения можно изменить с помощью команд set() и unset(). Эти команды влияют только на выполняемый процесс CMake, а не на системную среду в целом. Изменённые значения не записываются обратно в вызывающий процесс, и они не видны последующим процессам сборки или тестирования.

В руководстве cmake-env-variables(7) описаны переменные среды, имеющие особое значение для CMake.

Списки

Хотя все значения в CMake хранятся как строки, строка может обрабатываться как список в определенных контекстах, например, во время оценки незаявленного аргумента. В таких контекстах строка разделяется на элементы списка путём разделения по символам ;, если за ними не следует неравное количество символов [ и ] и не предшествует им \. Последовательность \; не разделяет значение, а заменяется на ; в результирующем элементе.

Список элементов представляется как строка путём конкатенации элементов, разделённых ;. Например, команда set() сохраняет несколько значений в целевой переменной в виде списка:

set(srcs a.c b.c c.c) # sets "srcs" to "a.c;b.c;c.c"

Списки предназначены для простых случаев, таких как список исходных файлов, и не должны использоваться для сложных задач обработки данных. Большинство команд, которые создают списки, не экранируют символы ; в элементах списка, тем самым уплощая вложенные списки:

set(x a "b;c") # sets "x" to "a;b;c", not "a;b\;c"

© 2000–2021 Kitware, Inc. and Contributors
Licensed under the BSD 3-clause License.
https://cmake.org/cmake/help/v3.21/manual/cmake-language.7.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API