CMake:如何使execute_进程等待子目录完成?

CMake:如何使execute_进程等待子目录完成?,cmake,Cmake,我的部分源代码是由一个工具生成的,这个工具也是在我们的主项目下构建的,它有一个子目录add\u。我们使用execute\u进程命令来执行此工具。显然,如果在到达execute\u进程语句之前没有构建该工具,它将失败 我使用GLOB(文件(GLOB…)查找生成的源文件。我这样做是因为事先不可能知道生成了多少文件,也不可能知道它们的名称 如何强制cmake在执行过程之前等待编译子项目?对于execute\u进程,我需要类似dependens的属性,但此选项不可用 # This subproject

我的部分源代码是由一个工具生成的,这个工具也是在我们的主项目下构建的,它有一个子目录
add\u
。我们使用
execute\u进程
命令来执行此工具。显然,如果在到达
execute\u进程
语句之前没有构建该工具,它将失败

我使用GLOB(
文件(GLOB…
)查找生成的源文件。我这样做是因为事先不可能知道生成了多少文件,也不可能知道它们的名称

如何强制cmake在执行过程之前等待编译子项目?对于
execute\u进程
,我需要类似
dependens
的属性,但此选项不可用

# This subproject will source generator the tool
add_subdirectory(generator)


# I need something like: wait_for(generator)
execute_process(COMMAND generator ${CMAKE_SOURCE_DIR}/src)

file(GLOB GeneratedSources ${CMAKE_SOURCE_DIR}/src/*.cpp)
add_executable(mainprject.exe ${ProcessorSourceFiles}

Command
execute\u进程
配置阶段立即执行其命令。因此,在使用
add_executable
命令创建可执行文件后,无法对其进行安排:该可执行文件将仅在build阶段生成

您还需要在配置阶段构建子项目。例如,与

execute_process(COMMAND ${CMAKE_COMMAND}
    -S ${CMAKE_SOURCE_DIR}/generator
    -B ${CMAKE_BINARY_DIR}/generator
    -G ${CMAKE_GENERATOR}
    )

execute_process(COMMAND ${CMAKE_COMMAND}
    --build ${CMAKE_BINARY_DIR}/generator
    )
第一个命令调用
cmake
来配置位于
${cmake\u SOURCE\u DIR}/generator
目录下的“generator”项目。使用
-G
选项,我们在子项目中使用与主项目相同的CMake生成器

第二个命令构建该项目,因此它生成
generator
可执行文件

创建
生成器
可执行文件后,您可以将其用于项目:

execute_process(COMMAND ${CMAKE_BINARY_DIR}/generator/<...>/generator ${CMAKE_SOURCE_DIR}/src)
execute\u进程(命令${CMAKE\u BINARY\u DIR}/generator//generator${CMAKE\u SOURCE\u DIR}/src)

在这里,您需要将绝对路径传递给
生成器
可执行文件,作为命令的第一个参数:CMake不再具有
生成器
可执行目标,因此它不会自动替换其路径。

您需要使用目标依赖关系对此进行建模。工具“生成器”应为cmake目标。在这种情况下,请使用以下方法,而不是执行以下过程:

add_custom_target(generate_sources ALL COMMAND generator ${CMAKE_SOURCE_DIR}/src))
然后使用以下方法将目标依赖项添加到“生成器”:

这将确保运行该工具的目标“generate_sources”仅在编译目标“generator”之后的构建期间运行

以下为假,有关更多信息,请参阅评论:

使用“添加依赖项”将依赖项从“mainproject.exe”添加到“生成依赖项源”。现在,我从未测试过这一点,因此请恕我直言:根据上的条目,使用比3.12版本更新的CMake,您应该能够将file命令更改为:

file(GLOB GeneratedSources CONFIGURE_DEPENDS ${CMAKE_SOURCE_DIR}/src/*.cpp)

我将其解释为,如果目录发生更改,则在构建过程中会重新对文件进行全局化处理。

使用
add\u custom\u命令
,而不是
execute\u process
?@arrowd。因为我需要在运行命令
文件(GLOB…
之前执行该进程
add_custom_命令
不允许我这样做。您可以执行
file(GLOB…
并将其结果传递给
add_custom_命令
。如果在执行进程之前运行
file(GLOB…)
,目录
src
将为空。在搜索文件(
文件(GLOB…
)之前,我需要运行
execute\u process
)“我解释为,如果目录发生更改,这将在构建期间重新对文件进行全局化。”-在构建任何目标之前,将在构建开始时重新检查。所以,
CONFIGURE\u dependens
选项在构建了
generator
可执行文件之后,无法帮助重新运行GLOB。此选项用于捕获用户创建的新源文件。感谢您清除此选项。将编辑。那会使事情严重复杂化。。但是,在构建期间,我们将如何进行全球化呢?我的下一个最佳猜测是将cmake脚本作为执行cmake-P的自定义目标运行,让它执行全局匹配并将找到的文件写入文本文件。然后将可执行目标依赖于该文本文件并以某种方式读取文件名……”我的下一个最佳猜测是将cmake脚本作为自定义目标运行,执行
cmake-P
,让其执行全局匹配并将找到的文件写入文本文件。“-类似的方法可以工作,但只需“两步”场景:第一次构建将生成源文件,但创建可执行文件将失败;第二次构建将全局更新正确的源文件,因此将创建无错误的可执行文件。顺便说一句,第二次构建的全局绑定实际上是通过CONFIGURE_dependens选项实现的。
file(GLOB GeneratedSources CONFIGURE_DEPENDS ${CMAKE_SOURCE_DIR}/src/*.cpp)