首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >搜索所有.c和.cpp文件并在一个makefile中编译它们

搜索所有.c和.cpp文件并在一个makefile中编译它们
EN

Stack Overflow用户
提问于 2020-02-20 22:48:37
回答 2查看 772关注 0票数 0

我正在尝试创建一个makefile,它将找到所有现有的.c和.cpp文件,然后编译它们。

我使用How to place object files in separate subdirectory作为模板,并将其与How to make a makefile for C and C++, with sources in subdirectories相结合。假设我已经定义了所有变量(因为它们是不必要的,所以我只是忽略了它们)。

我一直收到的错误是make: *** No rule to make target 'obj/<randoCfile>.c', needed by '<target>'. Stop.

代码语言:javascript
复制
SOURCES := $(call rwildcard,$(SRCDIR),*.c)
SOURCES += $(call rwildcard,$(SRCDIR),*.cpp)
OBJECTS     := $(patsubst $(SRCDIR)/%,$(BUILDDIR)/%,$(SOURCES:%.c=%.c.o))
OBJECTS     += $(patsubst $(SRCDIR)/%,$(BUILDDIR)/%,$(SOURCES:%.cpp=%.cpp.o))

#Default Make
all: $(TARGET)

#Remake
remake: cleaner all

#Make the Directories
directories:
    @mkdir -p $(TARGETDIR)
    @mkdir -p $(BUILDDIR)

#Clean only Objecst
clean:
    @$(RM) -rf $(BUILDDIR)

#Full Clean, Objects and Binaries
cleaner: clean
    @$(RM) -rf $(TARGETDIR)

#Link
$(TARGET): $(OBJECTS)
    $(CC) -o $(TARGETDIR)/$(TARGET) $^ $(LIB)

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

$(BUILDDIR)/%.cpp.o:
    $(CXX) $(INC) $(CXXFLAGS) -c -o $@ $<

#Non-File Targets
.PHONY: all remake clean cleaner resources

关于如何解决我的问题,有什么建议吗?我在Windows上运行(这就是为什么我使用通配符,而不是我找到的一个例子中的shell(find...) )。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2020-02-21 00:11:58

你有几个问题。最重要的是:

代码语言:javascript
复制
SOURCES := $(call rwildcard,$(SRCDIR),*.c)
SOURCES += $(call rwildcard,$(SRCDIR),*.cpp)

让我们假设这将导致SOURCES的以下值

代码语言:javascript
复制
SOURCES := src/foo.c src/bar/bar.c src/biz/biz.cpp src/boz.cpp

接下来,OBJECTS将是什么呢?

代码语言:javascript
复制
OBJECTS := $(patsubst $(SRCDIR)/%,$(BUILDDIR)/%,$(SOURCES:%.c=%.c.o))
OBJECTS += $(patsubst $(SRCDIR)/%,$(BUILDDIR)/%,$(SOURCES:%.cpp=%.cpp.o))

它将是(假设BUILDDIRobj):

代码语言:javascript
复制
OBJECTS := obj/foo.c.o obj/bar/bar.c.o obj/biz/biz.cpp obj/boz.cpp \
           obj/foo.c obj/bar/bar.c obj/biz/biz.cpp.o obj/boz.cpp.o

为什么?因为像$(SOURCES:%.c=%.c.o)这样的翻译并不只返回与模式匹配的单词.它返回所有的单词,并且只翻译与模式匹配的单词。

由于您只是将.o添加到后缀,而不是替换后缀,所以可以将其简化为:

代码语言:javascript
复制
SOURCES := $(call rwildcard,$(SRCDIR),*.c)
SOURCES += $(call rwildcard,$(SRCDIR),*.cpp)

OBJECTS := $(SOURCES:$(SRCDIR)/%=$(BUILDDIR)/%.o))

此外,这一规则也不正确:

代码语言:javascript
复制
$(BUILDDIR)/%.c.o:
        $(CC) $(INC) $(CFLAGS) -c -o $@ $<

在这里,您还没有声明任何先决条件。也许你会在其他地方做你没有给我们看的事情,但最好是这样做:

代码语言:javascript
复制
$(BUILDDIR)/%.c.o: $(SRCDIR)/%.c
        $(CC) $(INC) $(CFLAGS) -c -o $@ $<

当然,.cpp文件也是如此。

票数 2
EN

Stack Overflow用户

发布于 2020-02-21 20:11:58

Make (任意风味)是一个从目标(可执行文件)到源的程序,所以通常从可执行文件开始(需要构建一个对象文件列表),而这些对象取决于它们所依赖的源文件。你在想相反的方向..。搜索源文件,然后朝相反的方向走。虽然它更动态,但它并不是make工作的方式,所以解决方案很可能需要使用另一个程序来编译所有的源代码,并最终以一些您可能无法指定的东西结束,而make只会在那里执行搜索和编译程序。

因此,make的不同口味(例如gnu make或berkely make)开发了每一种不兼容的方法来实现可能的返回方式,使用gnu make中的函数,并在berkeley Make中具有强大的宏功能。我只想说,所有这些都不是标准的,都需要一些培训才能有效地处理。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/60329676

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档