【问题标题】:makefile multiple source file compilation rule in one stepmakefile 多源文件编译规则一步到位
【发布时间】:2015-05-24 01:48:27
【问题描述】:

我的目录结构如下: 生成文件 源/ 文件 1.cpp 文件 2.cpp 公司/ 文件 1.h 文件 2.h 现在我想编写一个make规则来创建一个'objs'目录并将我所有的对象(.o文件)放在'objs'中,然后用它构建一个库。我想一次性完成,而不是为每个 .cpp 文件编写一个规则。 这是我尝试过的:

SRC_DIR:= src/
INC_DIR:=inc/

SRC_PATH:=$(foreach var, $(SRC_DIR), $(wildcard $(var)*.cpp))
OBJ_PATH:=$(patsubst %.cpp,%.o,$(SRC_PATH))
OBJ_PATH:=$(notdir $(OBJ_PATH))
OBJ_DIR:=./objs
OBJ_PATH:=$(addprefix $(OBJ_DIR)/,$(OBJ_PATH))

TARGET:=libcommon.a

all:$(TARGET)

$(TARGET): $(OBJ_PATH)
    ar -rcs $(TARGET) $(OBJ_PATH)
$(OBJ_PATH): $(SRC_PATH)    
    mkdir -p $(OBJ_DIR)
    $(CXX) -o $(OBJ_PATH) -c $(SRC_PATH) -I$(INC_DIR)

但我收到此错误:

[root@localhost common]# make
mkdir -p ./objs
g++   -o ./objs/file1.o ./objs/file2.o -c  src/file1.cpp src/file2.cpp -Iinc/
g++: ./objs/file1.o: No such file or directory
g++: cannot specify -o with -c or -S with multiple files

我在这个主题上做了很多搜索。没有得到任何帮助。请指出我正在做的错误。

【问题讨论】:

    标签: gcc makefile


    【解决方案1】:

    代码中的错误:您使用列表代替 $@

    我喜欢在子目录中自动搜索带有 src 和 header 的解决方案。

    OBJ_DIR:=./objs
    
    SOURCES:=$(wildcard */*.cpp *.cpp)
    OBJECTS:= $(notdir $(SOURCES:.cpp=.o))
    OBJECTS_LOCAL:=$(SOURCES:.cpp=.o)
    LOCAL_PATHS_HEADERS:=$(sort $(dir $(wildcard *.h */*.h)))
    
    OBJ_PATH:=$(addprefix $(OBJ_DIR)/, $(OBJECTS))
    
    TARGET:=libcommon.a
    
    all:$(TARGET)
    
    $(TARGET): $(OBJECTS_LOCAL)
            ar -rcs $@ $(OBJ_PATH)
    
    $(OBJECTS_LOCAL):
            mkdir -p $(OBJ_DIR)
            $(CC) -c $(@:.o=.cpp) -o $(OBJ_DIR)/$(notdir $@) $(addprefix -I,$(LOCAL_PATHS_HEADERS))
    

    --添加

    解决方案wo重新编译,但需要手动控制SRC_DIR

    OBJ_DIR:=obj
    SRC_DIR:=src
    
    SOURCES:=$(wildcard $(SRC_DIR)/*.cpp)
    OBJECTS_PATH:=$(addprefix $(OBJ_DIR)/, $(notdir $(SOURCES:.cpp=.o)))
    LOCAL_PATHS_HEADERS:=$(sort $(dir $(wildcard *.h */*.h)))
    
    TARGET:=libcommon.a
    
    all:$(TARGET)
    
    $(TARGET): $(OBJECTS_PATH)
            ar -rcs $@ $^
    
    $(OBJECTS_PATH): $(OBJ_DIR)/%.o : $(SRC_DIR)/%.cpp
            mkdir -p $(OBJ_DIR)
            $(CC) -o  $@ -c $< $(addprefix -I,$(LOCAL_PATHS_HEADERS))
    

    【讨论】:

    • 该解决方案运行良好。谢谢您的帮助。但是这里的一个问题是每次执行 make 时都会重新编译源代码。我们怎样才能纠正这个问题?我的意思是 .c 文件只有在时间戳发生变化时才应该编译。
    • @deadbeef 我有其他解决方案,但它对自动有一些限制
    • 这正是我想要的。这符合我的期望。但我不明白这一行:` $(OBJECTS_PATH): $(OBJ_DIR)/%.o : $(SRC_DIR)/%.cpp`。你能解释一下这个语句是做什么的吗?
    • @deadbeef Manual 解释它比我能做的更好。你需要阅读About targets : target-pattern: prereq-patternsAbout %
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多