1

所以我必须创建一个生成下面描述的应用程序的生成文件,并确保每个生成的文件都有自己的规则。

对于 makefile:第一个工具是 flex,它接受一个名为的文件spec.l并生成一个名为lex.yy.c. 另一个名为 bison 的工具需要一个文件calledspec.y并将生成该文件spec.tab.c。如果使用指令调用 bison -vd,它还将生成一个名为的文件spec.tab.h(编译 lex.yy.c 时需要该文件)。这两个 C 文件可以编译成目标文件,然后与 yacc (-ly) 和 lex (-ll) 库链接在一起以生成编译器 ( a.out。如果您只是从 spec 开始,您描述的 makefile 必须生成以下命令.l 和 spec.y:

flex spec.l
bison -vd spec.y
gcc -c lex.yy.c
gcc -c spec.tab.c
gcc spec.tab.o lex.yy.o -ly -ll

我不知道从哪里开始解决这个问题

编辑:到目前为止我所拥有的

compiler: spec.tab.o lex.yy.o
gcc spec.tab.o lex.yy.o -ly –ll
lex.yy.c: spec.l
flex spec.l
spec.tab.c: spec.y
bison -vd spec.y
spec.tab.o: spec.tab.c
gcc -c spec.tab.c
lex.yy.o: lex.yy.c spec.tab.h
gcc –c lex.yy.c
clean:
rm –f *.c *.o a.out
4

1 回答 1

2

你必须告诉 make 关于依赖关系。例如,lex.yy.c取决于 spec.l:

lex.yy.c: spec.l
    flex spec.l

第一行说lex.yy.c取决于spec.l. 第二个告诉如何生成更新版本的lex.yy.c何时spec.l更新。我们几乎在其他文件中重复了这种模式。在 的情况下calledspec.y,我们有两个从相同的输入/命令产生的结果。至少使用 GNU make,您可以像这样指定:

spec.tab.c spec.tab.h: calledspec.y
    bison -vd calledspec.y

然后,您几乎重复了头文件和 C 文件上.o(或.obj等)文件的依赖关系的过程:

lex.yy.o: lex.yy.c spec.tab.h
   $(cc) -c lex.yy.c

最后一点:除非您另外指定,否则 make 将构建 makefile 中指定的第一个目标,因此您通常希望首先将其与最终可执行文件一起安排,然后再安排其他目标:

parser: lex.yy.o y.tab.o
    $(cc) -o parser lex.yy.o y.tab.o

lex.yy.o: lex.yy.c spec.tab.h
    $(cc) -c lex.yy.c

等等。但这仅适用于目标,不适用于宏,因此您通常会看到以下内容:

cflags = -O2

...在 make 文件的开头。然后调用编译器的行将使用它,例如:

lex.yy.o: lex.yy.c spec.tab.h
    $(cc) $(cflags) -c lex.yy.c

并且当它被执行时,cflags宏将被扩展,所以被执行的命令是gcc -O2 -c lex.yy.c(并且它预定义cc了它通常期望使用的编译器的名称,所以微软的 make 将它设置为cl, GNUgcc等)

于 2012-11-30T05:08:52.730 回答