假设我有一个文件将TARGET
定义转换为FEATURE
定义:
// File options.h
#ifdef TARGET_A
#define FEATURE_X
#endif
#ifdef TARGET_B
#define FEATURE_Y
#endif
struct foo {
int a;
int b;
};
我有一堆文件ifdef
'ed FEATURE
定义:
// File foo.c
#include "options.h"
#ifdef FEATURE_X
int x;
#endif
#ifdef FEATURE_Y
int y;
#endif
然后,我如何预处理foo.c
以便处理include语句,但是将其保存在文件中?
类似的东西:
$ some-pre-process-tool -DTARGET_A -I. -o foo.pp.c foo.c
$ cat foo.pp.c
// File foo.c
#include "options.h"
int x;
$
答案 0 :(得分:2)
首先,为什么要在预处理代码中保留#include
?您是打算再次通过预处理器运行它,还是在阅读结果时有用?
您可以使用gcc标志-Wp,-dI
获得所需内容。此处记录了-dI
:https://gcc.gnu.org/onlinedocs/gcc/Preprocessor-Options.html#index-dI-1113
请注意,输出文件还会包含您所包含文件中的#include
及其所有子#include
。
答案 1 :(得分:0)
有更好的方法可以做到这一点 - 但我最终编写了一个小包装脚本来处理来自cpp
的输出
#!/usr/bin/env ruby
# File: pp.rb
f = open("| cpp -C -dI #{ARGV.join(" ")}")
# First line
f.gets =~ /"([^"]+)"/
file = $1
ll = []
# Skip "invisible" includes
while l = f.gets
if l =~ /^#\s*1\s*"#{file}"$/
ll = []
else
ll.push l
end
end
inc = false
skip = false
skip_line = nil
ll.each do |l|
if inc and l =~ /^#\s*(\d+)\s*"#{file}"$/
inc = false
skip = true
skip_line = $1.to_i
elsif skip and l =~ /^#\s*(\d+)\s*"#{file}"/
inc = false
if $1.to_i == skip_line + 1
skip = false
end
elsif skip
inc = false
elsif l =~ /\s*#\s*include/
puts l
inc = true
elsif l =~ /^#\s*(\d+)\s*"#{file}"/
else
inc = false
puts l
end
end
我可以像这样调用:
$ ./pp.rb -DTARGET_A -I. foo.c > foo.pp.c
$ cat foo.pp.c
// File foo.c
#include "options.h"
int x;
答案 2 :(得分:-1)
我担心预处理文件只能在char或字符串文字内部以及辅助行记录的开头包含#
。