C Makefile包含多个文件

时间:2017-07-13 14:26:35

标签: makefile

我正在尝试编写一个编译多个文件的makefile。这是我的尝试:

CC = gcc
CFLAGS = -ansi -Wall -g -O0 -Wwrite-strings -Wshadow \
    -pedantic-errors -fstack-protector-all
PROGS = myprog.o test1 test2 test3 test4 \

all: $(PROGS)

clean:
        rm -f *.o $(PROGS) *.tmp

$(PROGS): myprog.o

myprog.o: prog-implementation.h myprog.c myprog.h
    gcc $(CFLAGS) -c myprog.c
memory_checker: memory_checker.o
    gcc -o memory_checker memory_checker.o
memory_checker.o: memory_checker.c memory_checker.h
    gcc $(CFLAGS) -c memory_checker.c
test1: test1.o
    gcc -o test1 test1.o myprog.o
test1.o: test1.c myprog.h myprog.c
    gcc $(CFLAGS) -c test1.c myprog.c
test2: test2.o
    gcc -o test2 test2.o myprog.o
test2.o: test2.c myprog.h
    gcc $(CFLAGS) -c test2.c
test3: test3.o
    gcc -o test3 test3.o myprog.o
test3.o: test3.c myprog.h
    gcc $(CFLAGS) -c test3.c
test4: test4.o
    gcc -o test4 test4.o myprog.o memory_checker.c
test4.o: test4.c myprog.h memory_checker.h
    gcc $(CFLAGS) -c test4.c

正如您可以从makefile中看到的那样,主要代码在myprog.c中,其中包括myprog.h和prog-implementation.h。我的代码也有4个测试,最后一个有一个memory_checker来确保我释放所有动态分配的内存。测试是main()方法和* .c文件的位置。

每当我尝试使用makefile时,它都会给我错误

make: Circular myprog.o <- myprog.o dependency dropped.
make: Nothing to be done for `all'.

我的所有观点都有标签而不是空格,所以这不是问题。我也很确定我的代码没有任何重大问题,所以makefile必须是我的问题。

2 个答案:

答案 0 :(得分:1)

此错误消息应该非常清楚:

make: Circular myprog.o <- myprog.o dependency dropped.

它说myprog.o取决于myprog.o。也就是说,要制作myprog.o,首先必须制作myprog.o,这是一个逻辑错误。其原因在于Makefile

PROGS = myprog.o test1 test2 test3 test4 \

....    

$(PROGS): myprog.o

第二行表示所有PROGS都取决于myprog.oPROGS中的一个是myprog.o,所以它现在取决于它自己。

要解决此问题,请从myprog.o列表中删除PROGS

答案 1 :(得分:0)

这有很多错误和不必要的复杂性,所以我会给你一个更好的解决方案和一些评论(假设你使用 GNU make ):

CC := gcc
CFLAGS := -ansi -Wall -g -O0 -Wwrite-strings -Wshadow \
    -pedantic-errors -fstack-protector-all

PROGS := test1 test2 test3 test4

# check these lists of object files needed for each binary, I extracted
# it from your rules in the question:
test1_OBJS := test1.o myprog.o
test2_OBJS := test2.o
test3_OBJS := test3.o myprog.o
test4_OBJS := test4.o myprog.o memory_checker.o
OBJS := $(sort $(test1_OBJS) $(test2_OBJS) $(test3_OBJS) $(test4_OBJS))

all: $(PROGS)

clean:
    rm -f *.o *.d $(PROGS) *.tmp

# the following rules link your final targets from the object files
# specified in the variables above:

test1: $(test1_OBJS)
    $(CC) -o$@ $^

test2: $(test2_OBJS)
    $(CC) -o$@ $^

test3: $(test3_OBJS)
    $(CC) -o$@ $^

test4: $(test4_OBJS)
    $(CC) -o$@ $^

# this automatically generates dependency files (with your headers)
%.d: %.c
    $(CC) -MM -MT"$@ $(@:.d=.o)" -MF$@ $(CFLAGS) $<

# and this includes them
ifneq ($(MAKECMDGOALS),clean)
-include $(OBJS:.o=.d)
endif

# finally, all you need is a pattern rule compiling your object files:

%.o: %.c
    $(CC) -c -o$@ $(CFLAGS) $<

.PHONY: all clean