如何在makefile中动态重命名对象文件

如何在makefile中动态重命名对象文件,makefile,gnu-make,multiple-makefiles,Makefile,Gnu Make,Multiple Makefiles,我对制作文件非常陌生。我以前做过的最复杂的任务是在已经设计好的makefile中包含新的.h和.cpp或.c 我必须将一个项目的编译过程从VisualStudio移植到gcc,一位同事已经为此编写了一个解决方案,但他使用了4个bash脚本和一个makefile来编译该解决方案 我没有这样做,而是在寻找解决方案,使其更易于维护。我承认我的问题可能很愚蠢,但我在任何地方都找不到,也无法完全理解 在以下目标中: $(OBJECTS): %.o: %.cpp $(CC) $(CPPFLAGS)

我对制作文件非常陌生。我以前做过的最复杂的任务是在已经设计好的makefile中包含新的.h和.cpp或.c

我必须将一个项目的编译过程从VisualStudio移植到gcc,一位同事已经为此编写了一个解决方案,但他使用了4个bash脚本和一个makefile来编译该解决方案

我没有这样做,而是在寻找解决方案,使其更易于维护。我承认我的问题可能很愚蠢,但我在任何地方都找不到,也无法完全理解

在以下目标中:

$(OBJECTS): %.o: %.cpp 
    $(CC) $(CPPFLAGS) -c $< -o $@
$(对象):%.o:%.cpp
$(CC)$(CPPFLAGS)-c$<-o$@
我想测试正在创建的.o是否已经存在,并将其重命名为其他名称。这是必要的,因为在项目中有多个源文件具有相同的名称,但它们的内容不同

例如,如果正在编译的当前.cpp名为file.cpp,将生成的对象为file.o,则规则应测试file.o是否已存在,并将当前文件.o重命名为其他文件

如果你知道任何解释这一点的好教程,请让我知道。我发现了很多例子,展示了如何根据该规则对当前编译的文件进行测试,但没有一个例子可以重命名object.o


提前感谢,并对此处所写的任何“愚蠢”表示歉意。:-)

首先,我们对您深表同情

Make并不是设计用来处理这种模糊性的,所以我们不得不使用一个模糊的方法。您尚未说明要将文件重命名为什么,因此现在让我们将
file.o
移动到
file\u save.o

# This tells Make that these are not real targets, so that it will
# proceed even if file.o already exists.
.PHONY: $(OBJECTS)

$(OBJECTS): %.o: %.cpp 
    # If file.o exists, move it to file_save.o
    @if [ -f $@ ]; then mv $@ $*_save.o; fi
    $(CC) $(CPPFLAGS) -c $< -o $@
#这告诉Make这些不是真正的目标,因此它将
#即使文件.o已经存在,也要继续。
.PHONY:$(对象)
$(对象):%.o:%.cpp
#如果文件.o存在,请将其移动到文件\u save.o
@如果[-f$@];然后mv$@$*\u save.o;fi
$(CC)$(CPPFLAGS)-c$<-o$@

首先,我们对您深表同情

Make并不是设计用来处理这种模糊性的,所以我们不得不使用一个模糊的方法。您尚未说明要将文件重命名为什么,因此现在让我们将
file.o
移动到
file\u save.o

# This tells Make that these are not real targets, so that it will
# proceed even if file.o already exists.
.PHONY: $(OBJECTS)

$(OBJECTS): %.o: %.cpp 
    # If file.o exists, move it to file_save.o
    @if [ -f $@ ]; then mv $@ $*_save.o; fi
    $(CC) $(CPPFLAGS) -c $< -o $@
#这告诉Make这些不是真正的目标,因此它将
#即使文件.o已经存在,也要继续。
.PHONY:$(对象)
$(对象):%.o:%.cpp
#如果文件.o存在,请将其移动到文件\u save.o
@如果[-f$@];然后mv$@$*\u save.o;fi
$(CC)$(CPPFLAGS)-c$<-o$@

扩展我对该问题的评论:

也许您应该考虑将对象文件放置在同一目录层次结构中作为源文件,以防止命名冲突。

因此,src/network/client.cpp被编译为build/obj/network/client.o

我对makefile非常生疏,但我相信我通过以下方式解决了这个问题:

$SRC= src/network/client.cpp src/main.cpp .....
$OBJ= makefile_replace_function($SRC, .o)

$(OBJ) : $(SRC)
   compile_instructions
您将不得不将
makefile\u replace\u函数
compile\u指令
替换为它们真正的等价物,因为我当时已经忘记了


我意识到这可能不是很有帮助,但至少是一个需要考虑的问题。

< P>我对问题的评论的扩展:

也许您应该考虑将对象文件放置在同一目录层次结构中作为源文件,以防止命名冲突。

因此,src/network/client.cpp被编译为build/obj/network/client.o

我对makefile非常生疏,但我相信我通过以下方式解决了这个问题:

$SRC= src/network/client.cpp src/main.cpp .....
$OBJ= makefile_replace_function($SRC, .o)

$(OBJ) : $(SRC)
   compile_instructions
您将不得不将
makefile\u replace\u函数
compile\u指令
替换为它们真正的等价物,因为我当时已经忘记了


我意识到这可能不是很有帮助,但至少是一个需要考虑的问题。这段代码似乎可以工作,但是没有生成*\u save.o文件。我想这是因为我的源cpp文件是在变量
source=file1.cpp file2.cpp file1.cpp
中定义的,然后我使用
OBJECTS=$(SOURCES:.cpp=.o)
来创建OBJECTS规则。真的吗?那不要紧。。。将
if
行替换为该行,然后查看发生的情况:
mv$@$*\u save.o
。当没有
file.o
可移动时,它会第一次抱怨,否则它会做同样的事情并告诉您它在做什么。谢谢您的帮助!当我尝试时,make会在第一个.o未找到后立即中止编译。@xlogdan:Ack!对不起,我应该说
-mv$@$*\u save.o
。首先只使用一个
文件.o
,而不是整个
对象列表。@Beta,非常感谢您的帮助!它仍然没有显示任何效果,make抱怨说我在同一个规则中包含了两个相等的目标,它不会执行上面的命令,因为没有.o。无论如何,我为这整件事道歉,但我在编译批处理文件中具有相同名称的源代码时成功了,我只是指定每个文件将具有不同的.o名称。接下来,我调用makefile,它将把所有内容捆绑在一个静态库中。我没有更多的时间在这方面,所以不幸的是,我将不得不让它,因为它是,至少我减少了它从5个bash脚本到1加上一个make文件。嘿,非常感谢。这段代码似乎可以工作,但是没有生成*\u save.o文件。我想这是因为我的源cpp文件是在变量
source=file1.cpp file2.cpp file1.cpp
中定义的,然后我使用
OBJECTS=$(SOURCES:.cpp=.o)
来创建OBJECTS规则。真的吗?那不要紧。。。将
if
行替换为该行,然后查看发生的情况:
mv$@$*\u save.o
。当没有
file.o
可移动时,它会第一次抱怨,否则它会做同样的事情并告诉您它在做什么。谢谢您的帮助!当我尝试时,make会在第一个.o未找到后立即中止编译。@xlogdan:Ack!对不起,我