GNU首先生成生成程序集,然后将它们编译为.o并链接

时间:2018-12-05 16:29:31

标签: gcc makefile gnu-make

datetime64[ns]

我想先生成汇编代码(.s),然后将汇编代码编译为对象(.o),然后链接它们。 但是上面的makefile代码似乎不起作用。什么是正确的代码?

1 个答案:

答案 0 :(得分:3)

问问题时,不起作用从来没有什么用处...如果它起作用了,您可能不会问问题! :-)相反,您应该始终显示您运行的命令和收到的输出(或者如果输出很长,则至少显示失败的部分)。请剪切并粘贴实际文本,而不是解释消息。另外,包括正在使用的make程序的版本(make --version和正在运行的平台通常也很有帮助。

幸运的是,这次我们可以在没有此信息的情况下解决问题:

此:

$(ASM):%.c
        gcc -S -o $@ $<

其中ASMa.s b.s c.s的不是模式规则,因为目标不包含模式字符%。这意味着先决条件%.c不会被当作模式,而是实际的文件名,%.c实际上不存在。

与此类似:

all: %.o

存在相同的问题:all是目标,因此这取决于名为%.o的文字文件,该文件不存在并且无法创建。

作为一般规则,每个创建目标的配方都必须创建您告知要实现的实际目标,因此此all规则是错误的,因为目标名称为all,但配方会创建目标目标test

最后,将程序命名为test是一个非常糟糕的主意,因为test是常见的UNIX程序,并且是内置的shell,因此如果您运行test,它将不会做正确的事情(如果您运行./test,它将起作用)。

您想让all取决于要构建的程序,例如mytest,而mytest应该取决于实际的.o文件:

all: mytest

mytest: $(SOURCE:.c=.o)
     gcc -o $@ $^

接下来,您需要定义一个模式规则,该规则知道如何从源文件创建程序集文件:

%.s : %.c
        gcc -S -o $@ $<

这就是您需要的其他模式规则:make会从中找出全部内容。

最后,make具有一个内置规则,该规则告诉它如何直接从源文件构建目标文件。最好摆脱这种情况,强迫make使用您的规则;将此添加到您的makefile中以将其删除:

%.o : %.c