获取编译器默认包含路径到生成文件中

Getting the compiler default include path into a makefile

我可以运行一个shell命令从编译器获取默认包含路径(并附加-I):

arm-none-eabi-gcc -xc -E  -Wp,-v  /dev/null 2>&1 | sed -En '/#include <...> search starts here:/,/End of search list./{//!p;};' | sed 's/^ /-I/'

我正在尝试将其添加到 Makefile 中:

PROJECT_INC = $(shell arm-none-eabi-gcc -xc -E  -Wp,-v /dev/null 2>&1 | sed -En "/#include <...> search starts here:/,/End of search list./{//!p;}" | sed "s/^ /-I/")

然后我得到一个错误:

Makefile:104: *** unterminated call to function `shell': missing `)'.  Stop.

我尝试改用反引号,但没有用。尝试对 sed 命令使用单引号或双引号。我在SO上能找到的类似问题,大部分都是跟命令中有$的时候展开有关,不过这里应该不是问题。

如果我砍下命令:

PROJECT_INC = $(shell arm-none-eabi-gcc -xc -E  -Wp,-v /dev/null 2>&1  )

然后好像是在减输出。 shell 会 return

ignoring duplicate directory "/Users/mjeanson/miniconda3/envs/project/bin/../lib/gcc/../../lib/gcc/arm-none-eabi/8.3.1/include"
ignoring nonexistent directory "/Users/mjeanson/miniconda3/envs/project/bin/../arm-none-eabi/usr/local/include"
ignoring duplicate directory "/Users/mjeanson/miniconda3/envs/project/bin/../lib/gcc/../../lib/gcc/arm-none-eabi/8.3.1/include-fixed"
ignoring duplicate directory "/Users/mjeanson/miniconda3/envs/project/bin/../lib/gcc/../../lib/gcc/arm-none-eabi/8.3.1/../../../../arm-none-eabi/include"
ignoring nonexistent directory "/Users/mjeanson/miniconda3/envs/project/bin/../arm-none-eabi/usr/include"
#include "..." search starts here:
#include <...> search starts here:
 /Users/mjeanson/miniconda3/envs/project/bin/../lib/gcc/arm-none-eabi/8.3.1/include
 /Users/mjeanson/miniconda3/envs/project/bin/../lib/gcc/arm-none-eabi/8.3.1/include-fixed
 /Users/mjeanson/miniconda3/envs/project/bin/../lib/gcc/arm-none-eabi/8.3.1/../../../../arm-none-eabi/include
End of search list.
# 1 "/dev/null"
# 1 "<built-in>"
# 1 "<command-line>"
# 1 "/dev/null"

运行 this 在 Makefile 中,它会从以 #include 开头的第一行开始丢弃,否则它会起作用。不确定在 sed 命令的管道工作正常后这是否仍然是一个问题(?)

如果这是相关的(并且在上面的代码片段中还不明显),我的环境正在使用交叉编译器 (arm-none-eabi-gcc) 并且在 conda 环境和所有 运行宁在 Mac.

我认为这无关紧要,但我需要这样做的原因是我可以使用一些静态分析工具。编译代码本身时,我不需要添加默认的包含路径。

奖励:我尝试将 sed 命令合并为一个,但不知道该怎么做...

发现问题...sed 命令中的“#”字符导致了问题并导致 make 将后面的所有内容都视为注释。

对于后代来说,固定命令要容易得多,因为包含路径以 ' ':

arm-none-eabi-gcc -xc -E  -Wp,-v  /dev/null 2>&1 | sed -En '/^ /s/^ /-I/p'

GNU Make 中宏扩展的语法非常具体(make 的,而不是 shell),通常不考虑 shell 元字符,如 ".

你已经包含了其中的几个,这意味着要制作的东西(例如 : 等)与它们对 shell 所做的不同。

您最好将完整的流水线写入 shell 脚本,然后在 Makefile 中使用 shell 脚本名称。

不要使用受 shell 引用保护的参数构建管道,因为 make 根本不关心引用。