当我在没有干净的情况下执行这个Makefile时,它运行正常,并且正确创建了共享库和主可执行文件。但是,当我添加干净的目标时,“make all”失败。可能是什么原因?
CC = gcc
CFLAGS = -fPIC -Wall -Werror
LDFLAGS = -shared
TARGET_LIB= libnsd.so
lib: nsd.o nd.o
$(CC) $(LDFLAGS) -o ${TARGET_LIB} nsd.o nd.o -lm
nd.o : nd.c nd.h
$(CC) -c $(CFLAGS) nd.c
nsd.o : nsd.c nsd.h
$(CC) -c $(CFLAGS) nsd.c
all: main.c
$(CC) -o -I. -L. main.c -lnsd
clean:
rm -f libnsd.so nd.o nsd.o
答案 0 :(得分:5)
您的all:
目标需要依赖于lib目标,因此首先构建库。
编译器的-o参数还需要一个应该创建的可执行文件的名称。
all: lib main.c
$(CC) -o main -I. -L. main.c -lnsd
通常,您希望目标名称是您创建的文件,否则在不需要时会重建内容。 (lib:target有相同的问题)但作为可执行文件的例子:
.PHONY: all
all: lib main
main: lib main.c
$(CC) -o main -I. -L. main.c -lnsd
答案 1 :(得分:2)
nos的回答是正确的。
之前只有出现,因为你碰巧以正确的顺序运行make。在clean
操作之后它将无法工作,因为正如nos指出的那样,您尚未声明所有先决条件。链接main.o
的规则必须依赖于共享库目标,因此make知道构建内容的正确顺序。
此外,您真的希望您的目标成为您正在构建的实际文件。如果它们是别的东西,那么即使你没有改变任何东西,make也总会认为它们已经过时了,并且总是重建它们。
这样的事情会更好:
CC = gcc
CFLAGS = -fPIC -Wall -Werror
CPPFLAGS = -I.
LDFLAGS = -shared
PROGRAM = main
TARGET_LIB= libnsd.so
all: $(PROGRAM)
$(PROGRAM): main.o $(TARGET_LIB)
$(CC) -o $@ -L. main.o -lnsd
$(TARGET_LIB): nsd.o nd.o
$(CC) $(LDFLAGS) -o $@ nsd.o nd.o -lm
nd.o : nd.c nd.h
nsd.o : nsd.c nsd.h
clean:
rm -f libnsd.so *.o