Spec-Zone.ru › CMake 3.13

macro

Начать запись макроса для последующего вызова в качестве команды:

macro(<name> [arg1 [arg2 [arg3 ...]]])
  COMMAND1(ARGS ...)
  COMMAND2(ARGS ...)
  ...
endmacro(<name>)

Определите макрос с именем <name>, принимающий аргументы с именами arg1, arg2, arg3, (…). Команды, перечисленные после макроса, но перед соответствующим endmacro(), не будут вызваны до тех пор, пока макрос не будет вызван. При вызове команды, записанные в макросе, сначала изменяются путем подстановки формальных параметров (${arg1}) с переданными аргументами, а затем вызываются как обычные команды. В дополнение к ссылке на формальные параметры, вы можете ссылаться на значения ${ARGC}, которые будут установлены в количество переданных в функцию аргументов, а также на ${ARGV0}, ${ARGV1}, ${ARGV2}, …, которые будут содержать фактические значения переданных аргументов. Это облегчает создание макросов с необязательными аргументами. Кроме того, ${ARGV} содержит список всех переданных макросу аргументов, а ${ARGN} — список аргументов, которые идут после последнего ожидаемого аргумента. Ссылка на ${ARGV#} аргументов сверх ${ARGC} имеет неопределённое поведение. Проверка того, что ${ARGC} больше, чем #, является единственным способом гарантировать, что ${ARGV#} был передан в функцию в качестве дополнительного аргумента.

См. документацию команды cmake_policy() для поведения политик внутри макросов.

Особенности аргументов макроса

Обратите внимание, что параметры макроса и значения, такие как ARGN, не являются переменными в обычном смысле CMake. Они являются строковыми подстановками, аналогично тому, как это делает препроцессор C с макросом. Поэтому вы НЕ сможете использовать команды, такие как:

if(ARGV1) # ARGV1 is not a variable
if(DEFINED ARGV2) # ARGV2 is not a variable
if(ARGC GREATER 2) # ARGC is not a variable
foreach(loop_var IN LISTS ARGN) # ARGN is not a variable

В первом случае можно использовать if(${ARGV1}). Во втором и третьем случаях правильный способ проверить, был ли необязательный аргумент передан макросу, — использовать if(${ARGC} GREATER 2). В последнем случае можно использовать foreach(loop_var ${ARGN}), но это пропустит пустые аргументы. Если вам нужно их включить, вы можете использовать:

set(list_var "${ARGN}")
foreach(loop_var IN LISTS list_var)

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

macro(_BAR)
  foreach(arg IN LISTS ARGN)
    [...]
  endforeach()
endmacro()

function(_FOO)
  _bar(x y z)
endfunction()

_foo(a b c)

Будет перебирать a;b;c и не x;y;z, как можно было бы ожидать. Если вам нужны настоящие переменные CMake и/или лучший контроль области видимости CMake, обратите внимание на команду function.

© 2000–2019 Kitware, Inc. and Contributors
Licensed under the BSD 3-clause License.
https://cmake.org/cmake/help/v3.13/command/macro.html

Spec-Zone.ru

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