【问题标题】:Make does not compile good filesMake不编译好的文件
【发布时间】:2015-11-08 11:32:56
【问题描述】:

我的 Makefile 有问题,它只是多次编译同一个文件。

这是我的文件:

$ ls *
carnet.data  carnet.l  carnet.y  Makefile

struct:
carnet.c  carnet.h  ihm.c  ihm.h  struct.c  struct.h

这是我的 Makefile:

CC      = gcc
LEX     = lex
YACC    = yacc
FLAGS   = -Wall -Wextra -Werror -O3 -g
ELIB    = -lfl # Flex library
TARGET  = carnet

SRC     = $(shell find struct/ -name "*.c")
OBJ     = $(SRC:.c=.o)
SRCL    = $(shell find -name "*.l")
OBJL    = lex.yy.o
SRCY    = $(shell find -name "*.y")
OBJY    = y.tab.o

all : $(TARGET)

$(TARGET) : $(OBJ) $(OBJY) $(OBJL)
    @echo "Linking"
    @echo $(SRC)
    @echo $(OBJ)
    @$(CC) $^ -o $@ $(FLAGS) $(ELIB)


$(OBJY) : $(SRCY)
    @echo $<
    @$(YACC) -d $<
    @$(CC) -c y.tab.c -o $@

$(OBJL) : $(SRCL)
    @echo $<
    @$(LEX) $<
    @$(CC) -c lex.yy.c -o $@

$(OBJ) : $(SRC)
    @echo $<
    $(CC) -c $< -o $@ $(FLAGS)

clean :
    rm y.tab.c $(OBJY) y.tab.h lex.yy.c $(OBJL)
    rm $(OBJ)

destroy :
    rm $(TARGET)

rebuilt : destroy mrpropper

mrpropper : all clean

这是我做'make'时的输出:

struct/struct.c
gcc -c struct/struct.c -o struct/struct.o -Wall -Wextra -Werror -O3 -g
struct/struct.c
gcc -c struct/struct.c -o struct/carnet.o -Wall -Wextra -Werror -O3 -g
struct/struct.c
gcc -c struct/struct.c -o struct/ihm.o -Wall -Wextra -Werror -O3 -g
carnet.y
carnet.l
Linking
struct/struct.c struct/carnet.c struct/ihm.c
struct/struct.o struct/carnet.o struct/ihm.o

我们可以看到,当我执行“echo $(SRC)”时,他找到了所有三个文件,但他只编译了“struct.c”文件,我不明白为什么!

感谢您的帮助, 幻影

【问题讨论】:

  • 旁注并不真正属于我的答案:在您不需要后期扩展的任何地方使用:= 而不是= 以避免混淆。仅使用=,您将获得一个仅在其自身扩展时才扩展其内容的变量,并且大多数情况下,这不是您想要的(但有时是)

标签: c makefile yacc flex-lexer


【解决方案1】:
SRC     = $(shell find struct/ -name "*.c")

您在此处创建一个列表,$(SRC) 将是 struct/struct.c struct/carnet.c struct/ihm.c。或者任何其他订单find 可能会返回,但根据您的结果,这似乎是订单。

OBJ     = $(SRC:.c=.o)

这将创建修改后的列表struct/struct.o struct/carnet.o struct/ihm.o

$(OBJ) : $(SRC)
    @echo $<
    $(CC) -c $< -o $@ $(FLAGS)

我们开始,(部分,为了清楚起见)扩展导致

struct/struct.o struct/carnet.o struct/ihm.o : struct/struct.c struct/carnet.c struct/ihm.c
    @echo $<
    $(CC) -c $< -o $@ $(FLAGS)

所以你有一个规则适用于构建 3 个目标,很好。现在,$&lt; 扩展为 first 先决条件,此处为 struct/struct.c

如果您使用具有此功能的make,则可能是(也是常见的)解决方案,例如GNU make,就是用模式规则代替这个find-hack:

struct/%.o : struct/%.c
    @echo $<
    $(CC) -c $< -o $@ $(FLAGS)

请注意,通常情况下,您只需在 Makefile 中维护一份您的 taget 模块列表,通常是手动维护目标文件,如下所示:

OBJS:= struct/struct.o struct/carnet.o struct/ihm.o

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-10-14
    • 2011-02-05
    • 1970-01-01
    相关资源
    最近更新 更多