使用 make,如何在程序集项目中使用 .c 文件防止这种行为?
Using make, how do I protect against this behavior with .c files in an assembly project?
我正在做一个超级简单的NASMx86_64汇编程序mytest.asm
BITS 64
GLOBAL _start
SECTION .text
_start:
mov rax, 60 ; 'exit' system call
mov rdi, 42 ; exit with error code 42
syscall
这个程序所做的就是以状态 42 退出。我为它制作了一个非常简单的 Makefile,
AS=nasm
ASFLAGS=-f elf64
.PHONY: all
all: mytest
%.o : %.asm
$(AS) $(ASFLAGS) -o "$@" "$<"
% : %.o
$(LD) $(LDFLAGS) -o "$@" "$<"
执行时,效果很好,
nasm -f elf64 -o "mytest.o" "mytest.asm"
ld -m elf_x86_64 -o "mytest" "mytest.o"
rm mytest.o
除非有与.c
同名的文件,例如这里mytest.c
// exits with status 66
int main () {
__asm__ (
"mov , %%rax\n\t"
"mov , %%rdi\n\t"
"syscall\n\t"
::: "%rax", "%rdi"
);
}
如果我 运行 make
使用以下文件,C 代码实际上会编译为 mytest
。
尴尬的是,$(LDARGS)
被发送到 $(CC)
而不是 $(LD)
。这对我来说似乎不安全,任何具有这种非常典型的 Makefile
的人都可以通过插入具有相同名称的 .c
文件来从代号生成可执行文件?
GNU Make 是否记录了此行为?
GNU Make 4.1
Built for x86_64-pc-linux-gnu
理想情况下,.c
文件的存在不会影响程序集构建流。
这来自Make’s built-in rules。 Make 知道如何从 C 文件构建可执行文件,所以当你要求它构建 mytest
(这是 make
所做的,因为你有一个需要 mytest
的 all
目标),它建立了它的依赖树并注意到:
- 它可以根据其内置规则从
mytest.c
构建 mytest
;
- 它可以根据您指定的规则从
mytest.o
构建 mytest
;
- 它可以根据其内置规则从
mytest.c
构建 mytest.o
;
- 它可以根据您指定的规则从
mytest.asm
构建 mytest.o
。
第一个规则获胜(我不确定优先级是多少),这就是它的作用。
您可以使用 -r
选项禁用此功能:
make -r mytest
将始终使用您的规则来构建程序。
单独重新定义它们:
% : %.c
在您的 Makefile
末尾将禁用该内置规则并导致您所追求的行为;
全局通过在你的 Makefile 中指定 MAKEFLAGS += -r
。
我正在做一个超级简单的NASMx86_64汇编程序mytest.asm
BITS 64
GLOBAL _start
SECTION .text
_start:
mov rax, 60 ; 'exit' system call
mov rdi, 42 ; exit with error code 42
syscall
这个程序所做的就是以状态 42 退出。我为它制作了一个非常简单的 Makefile,
AS=nasm
ASFLAGS=-f elf64
.PHONY: all
all: mytest
%.o : %.asm
$(AS) $(ASFLAGS) -o "$@" "$<"
% : %.o
$(LD) $(LDFLAGS) -o "$@" "$<"
执行时,效果很好,
nasm -f elf64 -o "mytest.o" "mytest.asm"
ld -m elf_x86_64 -o "mytest" "mytest.o"
rm mytest.o
除非有与.c
同名的文件,例如这里mytest.c
// exits with status 66
int main () {
__asm__ (
"mov , %%rax\n\t"
"mov , %%rdi\n\t"
"syscall\n\t"
::: "%rax", "%rdi"
);
}
如果我 运行 make
使用以下文件,C 代码实际上会编译为 mytest
。
尴尬的是,$(LDARGS)
被发送到 $(CC)
而不是 $(LD)
。这对我来说似乎不安全,任何具有这种非常典型的 Makefile
的人都可以通过插入具有相同名称的 .c
文件来从代号生成可执行文件?
GNU Make 是否记录了此行为?
GNU Make 4.1
Built for x86_64-pc-linux-gnu
理想情况下,.c
文件的存在不会影响程序集构建流。
这来自Make’s built-in rules。 Make 知道如何从 C 文件构建可执行文件,所以当你要求它构建 mytest
(这是 make
所做的,因为你有一个需要 mytest
的 all
目标),它建立了它的依赖树并注意到:
- 它可以根据其内置规则从
mytest.c
构建mytest
; - 它可以根据您指定的规则从
mytest.o
构建mytest
; - 它可以根据其内置规则从
mytest.c
构建mytest.o
; - 它可以根据您指定的规则从
mytest.asm
构建mytest.o
。
第一个规则获胜(我不确定优先级是多少),这就是它的作用。
您可以使用 -r
选项禁用此功能:
make -r mytest
将始终使用您的规则来构建程序。
单独重新定义它们:
% : %.c
在您的
Makefile
末尾将禁用该内置规则并导致您所追求的行为;全局通过在你的 Makefile 中指定
MAKEFLAGS += -r
。