GCC included header (using `-include`) changes not detected by CMake
我正在观察奇怪的CMake行为。如果我的项目具有通过ADD_COMPILE_OPTIONS(-include inc.h)命令使用-include inc.h包含到所有源的头文件,则更改为从未检测到的头。这意味着我可以更改标题,但是CMake绝不会尝试重新编译main.cpp。难道我做错了什么?这是CMake的错误吗?任何解决方法?
CMakeLists.txt
1 2 3 4 5 6 7 8 9 10
| CMAKE_MINIMUM_REQUIRED(VERSION 3.12)
PROJECT(include_test)
SET(CMAKE_CXX_STANDARD 17)
INCLUDE_DIRECTORIES(.)
ADD_COMPILE_OPTIONS(
-include inc.h
)
ADD_EXECUTABLE(include_test main.cpp) |
main.cpp
1 2 3 4 5 6 7 8 9
| #include <iostream>
int main()
{
foo a;
std::cout << a.bar << std::endl;
return 0;
} |
inc.h
1 2 3 4 5
| struct foo
{
int bar = 1;
double baz = 3;
}; |
EDIT001:
正如@Oliv建议的那样,当尝试使用SET_SOURCE_FILES_PROPERTIES(main.cpp PROPERTY OBJECT_DEPENDS inc.h)之类的东西时当然不会起作用,因为依赖关系应该是目标而不是cpp所依赖的文件,因此我添加了以下内容:
1 2 3 4 5 6
| ADD_CUSTOM_TARGET(HeaderChanged
DEPENDS
inc.h
COMMENT"Checking if include file has changed")
SET_SOURCE_FILES_PROPERTIES(main.cpp PROPERTY OBJECT_DEPENDS HeaderChanged) |
尽管存在HeaderChanged目标,但仍会导致make[2]: *** No rule to make target 'HeaderChanged', needed by 'CMakeFiles/include_test.dir/main.cpp.o'. Stop.
- 只是不使用-include?
-
我认为在您的特定示例中,inc.h不被识别为项目源文件或头文件,因为您没有在main.cpp中明确包含它。因此,每次触摸inc.h时,都应清洁并重新清洁。
-
@AlanBirtles,它是现有状态,我无法更改
-
@GergelyNyiri很明显,如果CMake在这种情况下没有任何特殊处理,为什么它不起作用。问题是现在可以做什么。
-
如果您不能更改compile选项,则可以为包含它的每个文件将inc.h添加到OBJECT_DEPENDS源文件属性。
-
另一种选择是制作一个脚本,该脚本在每个inc.h被修改时,每个touch源文件都将更改它们的最后修改时间。在Linux上这很容易,在其他系统上我不知道。
-
OBJECT_DEPENDS听起来不错,请检查一下。另一方面,触摸文件非常丑陋。
-
@Olive,它没有用,问题已更新
-
OBJECT_DEPENDS应该可以工作,尚不清楚您所说的依赖关系应该是目标,而不是cpp所依赖的文件。
-
@ n.m。完整命令应该如何? SET_SOURCE_FILES_PROPERTIES(main.cpp PROPERTY OBJECT_DEPENDS inc.h)之类的东西?
-
是的,完全是这样。
-
@ n.m。然后我得到***没有规则将目标设置为" inc.h"
-
这意味着make会看到正确的规则,但找不到文件。您应该指定inc.h的有效路径。
-
@ n.m。你是对的!奇怪的事情," inc.h"或" ./inc.h"都不起作用。不明白为什么,所有东西都在同一个目录中。执行CMake时的当前目录是CMAKE_CURRENT_BINARY_DIR而不是CMAKE_CURRENT_LIST_DIR吗?
在EDIT0001上:您可能需要指定inc.h的完整路径,以便Makefile知道在哪里找到它(因为您很可能是在源代码之外进行构建),即:
SET_SOURCE_FILES_PROPERTIES(main.cpp PROPERTIES OBJECT_DEPENDS ${CMAKE_CURRENT_LIST_DIR}/inc.h)
还请注意,OBJECT_DEPENDS解决方案不适用于Visual Studio(标志-include也不适用)。但是在Visual Studio中,添加ADD_COMPILE_OPTIONS(/FIinc.h)就足够了,它将自动检测对inc.h的更改。
- 如果我使用VS,我不会遇到上述问题:)现在不在办公室,明天再检查
-
如预期般运作。谢谢!