12

-D CMAKE_C_COMPILER是我用来选择我的编译器的。但是,如果我有打开/关闭的 CMake 选项USEIPHONEFLAG,我需要这样做-DUSEIPHONEFLAG=1-D USEIPHONEFLAG=1但不起作用。我想知道-DCMake 中的空间是如何工作的。

4

1 回答 1

20

不幸的是,CMake 的命令行解析不是很一致或健壮。

这个问题可能取决于您传递参数的顺序。

在内部,CMake 对命令行参数进行两次迭代。它第一次寻找非缓存参数并跳过任何以-D. 任何不适合正确参数列表的内容都被假定为 CMakeLists.txt 文件(或目录,或 CMakeCache.txt)的路径。

它假设只有一条路径通过,并且没有做任何事情来验证该假设。问题就在这里。如果你通过了-D Foo=1-D则被视为一个完整的参数并被跳过,并被Foo=1视为一条路径。

在通过 args 的第二次迭代中,它现在获取 via 给出的值-D,但在这次运行中,它正确处理-D. 所以它知道-D Foo=1设置Foo1.

因此,命令行中路径的位置在这里非常重要。

cmake -D Foo=1 MyProject/CMakeLists.txt  # --> Works
cmake MyProject/CMakeLists.txt -D Foo=1  # --> Fails

为了使事情进一步复杂化,您可以将空格括在引号中并让 CMake 解析它,但变量名随后包含空格并且在 CMakeLists 文件中不可用。

cmake MyProject/CMakeLists.txt "-D Foo=1"  # --> Defines the unusable var ${ Foo}

另一个不一致的地方是其他命令行标志可以使用或不使用空格(例如-G),而其他命令行标志需要空格(例如-E)。

我自己的建议是始终避免在标志后添加空格,除非需要。我想总是最后通过路径也会有所帮助,尽管如果您不添加额外的空格,则不需要这样做。

于 2013-06-19T02:26:21.280 回答