使用GNU Make输出平面对象文件目录结构 [英] Flat object file directory structure output with GNU Make

查看:86
本文介绍了使用GNU Make输出平面对象文件目录结构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个使用GNU Make的C ++小项目.我希望能够打开以下源文件:

I have a C++ small project using GNU Make. I'd like to be able to turn the following source files:

src/
  a.cpp
  b/
    b.cpp
  c/
    c.cpp

进入以下输出结构(目前我不关心重复项):

into the following output structure (I'm not concerned about duplicates at this point):

build/
  a.o
  b.o
  c.o

到目前为止,我有以下内容,不幸的是,它们将.o和.d放在每个.cpp旁边:

So far I have the following, which unfortunately puts the .o and .d right next to each .cpp:

OBJS            :=      $(foreach file,$(SRCS),$(file).o)
DEPS            :=      $(patsubst %.o,%.d,$(OBJS))
sinclude $(DEPS)

$(OBJS) : %.o : %.cpp
        @echo Compiling $<
        $(CC) $(CC_FLAGS) $(INCS) -MMD -o $@ $<  

我知道$(notdir ...)函数,但是在这一点上,我使用它来过滤对象的努力失败了.谁能对此有所启发?这似乎是相当合理的事情.

I'm aware of the $(notdir ...) function, but at this point my efforts to use it to filter the objects has failed. Can anyone shed some light on this? It seems like fairly reasonable thing to do.

推荐答案

至少有两种方法可以执行此操作.首先(也是我的建议),您可以将构建目录添加到目标名称(即使使用模式规则时).例如:

There are at least two ways you can do this. First (and what I'd recommend) is you can add the build directory to the target names (even when using a pattern rule). For example:

$(OBJS) : build/%.o : %.cpp

第二,您可以使用VPATH变量告诉make在其他目录中搜索先决条件.这可能是更常用(过度)的方法.它至少有一个严重的缺点,那就是如果您使用它,然后又遇到重复项"问题,则无法解决该问题.使用前一种方法,您始终可以在build目录下镜像源目录结构,以避免重复冲突.

Second, you can use the VPATH variable to tell make to search a different directory for prerequisites. This is probably the more commonly (over) used approach. It has at least one serious drawback, and that is if you go with it, and later run into problems with "duplicates", there's no way to solve the problem. With the former approach, you can always mirror the source directory structure underneath the build directory to avoid duplicates clashing.

编辑:我先前的回答在细节上有些欠缺,因此我将在其上进行扩展以表明它实际上与广告宣传的一样.这是一个完整的工作示例Makefile,它使用上述第一种技术来解决该问题.只需将其粘贴到Makefile中并运行make即可,其余的工作将完成,并表明它确实有效.

My previous answer was a little short on detail, so I will expand upon it to show that this actually works as advertised. Here is a complete working example Makefile that uses the first technique described above to solve the problem. Simply paste this into a Makefile and run make -- it will do the rest and show that this does in fact work.

编辑:我无法弄清楚如何使答案文本中包含制表符(用空格代替).复制并粘贴此示例后,您需要将命令脚本中的前导空格转换为选项卡.

I can't figure out how to get SO to allow tab characters in my answer text (it replaced them with spaces). After copying and pasting this example, you'll need to convert the leading spaces in the command scripts into tabs.

BUILD_DIR := build

SRCS := \
    a.c \
    b.c \
    c.c \
    a/a.c \
    b/b.c \
    c/c.c

OBJS := ${SRCS:%.c=${BUILD_DIR}/%.o}

foo: ${OBJS}
    @echo Linking $@ using $?
    @touch $@

${BUILD_DIR}/%.o: %.c
    @mkdir -p $(dir $@)
    @echo Compiling $< ...
    @touch $@

${SRCS}:
    @echo Creating $@
    @mkdir -p $(dir $@)
    @touch $@

.PHONY: clean
clean:
    rm -f foo
    rm -f ${OBJS}

尤其要注意,有些源文件具有重复的名称(a.c和a/a.c,b.c和b/b.c等),并且这不会引起任何问题.另外请注意,由于使用VPATH存在固有的局限性,因此建议不要使用VPATH.

In particular, note that there are source files with duplicate names (a.c and a/a.c, b.c and b/b.c, etc) and that this doesn't cause any problems. Also note there is no use of VPATH, which I recommend to avoid using due to its inherent limitations.

这篇关于使用GNU Make输出平面对象文件目录结构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆