具有多个文件的Makefile始终构建所有内容

时间:2017-03-13 01:49:55

标签: c makefile dependencies gnu-make

我正在编写一个Makefile,它编译了许多C文件,一些与Makefile在同一目录中,另一些在父目录中(由于历史原因必须在那里)。我想把所有* .o文件放在一个目录中(在我的例子中是objdir)。这似乎有效,但由于某种原因,这个Makefile总是构建所有东西,即使没有任何改变。我的规则/家属在哪里出错?

更新:我已经将我的Makefile和源代码提取到最低限度(请参阅下面的源文件内容。要清楚,这会编译和链接。问题是它每次运行时都进行编译和链接即使没有任何变化,这也不是典型的制造行为。

Makefile内容:

CC = gcc
CFLAGS = -g -Wall -Werror -I..
SRCS = main.c ../a.c
OBJS = $(patsubst %.c, objdir/%.o, $(SRCS))
LN_OBJS = $(patsubst %.c, objdir/%.o, $(notdir $(SRCS)))
MAIN = foo

.PHONY: clean

default: objdir $(MAIN)
    @echo  Done

$(MAIN): $(OBJS) 
    $(CC) $(CFLAGS) -o $(MAIN) $(LN_OBJS    )

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

objdir:
    @mkdir -p objdir

clean:
    @$(RM) -rf objdir $(FDP) $(DK)

main.c内容

#include "stdlib.h"
#include "stdio.h"

#include "a.h"

int main(int argc, char**argv)
{
    printf("Hello\n");
    a();
}

../ a.c内容

#include <stdio.h>

void a()
{
    printf("Hi from a\n");
}

../ a.h内容

#ifndef __a__
#define __a__

void a();

#endif

1 个答案:

答案 0 :(得分:2)

objdir/%.o:的规则已扩展为objdir/../a.o: ../a.c,但您继续创建objdir/$(notdir $@),违反了Rules of Makefiles的规则2.

解决此问题的一种方法是使用vpath(还要注意objdir应该是对象的(仅限订单)依赖关系):

SRCS = main.c a.c
vpath %.c ../
# [...]
objdir/%.o: %.c | objdir
    $(CC) $(CFLAGS) -c $< -o $@