我需要帮助编写一个makefile,它创建两个依赖于公共文件的独立可执行文件。所以,我有三个源文件:Master.c Common.c Worker.c和三个相应的头文件。现在,Master.c包括Master.h和Common.h。类似地,Worker.c包括Worker.h和Common.h。我想使用相同的makefile创建两个可执行文件,即Master和Worker。我有以下makefile,但是它运行不正常,因为对于在Common.h中声明的每个全局变量,当我输入 make 时,我得到错误“Multiple declarations”。请注意,我在所有头文件中都使用了#indef,#define和#endif。
CC = gcc
CFLAGS= -g -I -pthread -lpthread -std=c99
DEPS = Common.h
OBJ1 = Master.o Common.o
OBJ2 = Worker.o Common.o
%.o: %.c $(DEPS)
$(CC) -c -o $@ $< $(CFLAGS)
all: Master Worker
Master: $(OBJ1)
gcc -o $@ $^ $(CFLAGS)
Worker: $(OBJ2)
gcc -o $@ $^ $(CFLAGS)
clean:
rm -f *.o
你能帮忙吗
答案 0 :(得分:0)
不要将全局变量的定义放入标题中;相反,将它们放在一个源文件中,只有声明标题中的变量:
<强> COMMON.H:强>
extern int foo; /* declaration only */
<强> common.c中:强>
#include "Common.h"
int foo; /* definition */
否则,在多个翻译单元中包含标题会违反单一定义规则。
答案 1 :(得分:0)
上面的makefile完美无缺?
没有。我可以看到几个问题,如果你修复它们那么它将是“最先进的”:
(一个错误)所有目标至少应取决于$(MAKEFILE)
MAKEFILE := $(lastword $(MAKEFILE_LIST))
您还需要过滤食谱中的$^
:$(filter %.o, $^)
,这无论如何都是一种不错的做法
使用:=
代替=
,它更有效,并且使代码中的逻辑更容易理解,默认情况下应始终使用,除非=
是必要的
您将CC
定义为gcc
然后不使用它,而是使用gcc
代替
考虑自动生成依赖关系(grep手册),在这个小案例中可能不需要,但是对于更大的情况你需要它 - 现在gcc
有很好的支持
使用“罐装食谱”(grep手册)作为重复食谱
.PHONY: all clean
clean
不会删除所有内容