2017-11-17 101 views
0

我有點奇怪的大小寫,我正在努力弄清楚。我有一個C++項目,我以一些.cpp文件開始,我需要從多個應用程序使用的多個遠程目錄中編譯一些源文件。這並不理想,但這是我的開發組使用的傳統目錄/編譯結構。Make:利用VPATH編譯和鏈接不同擴展名的文件

其他項目利用VPATH來實現這一點。但是,它們最終會對所鏈接的所需對象列表進行硬編碼,而且這種方法對我來說看起來不夠優雅或靈活。我想動態編譯和鏈接所有內容。另一個潛在的複雜情況是,這些遠程VPATH目錄中的某些目錄具有.c擴展名的文件(即使這些擴展名編譯爲C++)而不是.cpp。

我目前的解決方案:

# Directory for object files 
OBJ_DIR = build 

CPPSRC := $(wildcard *.cpp) 
CSRC := $(wildcard *.c) 
OBJ := $(CSRC:%.c=$(OBJ_DIR)/%.o) $(CPPSRC:%.cpp=$(OBJ_DIR)/%.o) 

# Directory for output binaries 
BIN_DIR = bin 

# Name of binary executable 
OUTPUT = foo 

# VPATH allows you to specify other directories to search for prereqs in 
VPATH = /one/remote/dir /another/remote/dir 

# 'make all' 
all: $(BIN_DIR)/$(OUTPUT) 

# 'make clean' 
clean: 
    @rm -rf $(BIN_DIR) 
    @rm -rf $(OBJ_DIR) 

$(OBJ_DIR)/%.o: %.cpp 
    @mkdir -p $(OBJ_DIR) 
    $(CXX) -c $< -o [email protected] 

$(OBJ_DIR)/%.o: %.c 
    @mkdir -p $(OBJ_DIR) 
    $(CXX) -c $< -o [email protected] 

$(BIN_DIR)/$(OUTPUT): $(OBJ) 
    @mkdir -p $(BIN_DIR) 
    $(CXX) -g -ansi -Wall -Werror -o [email protected] $(OBJ) 

其結果是,一切都被編譯和鏈接,除了在我的VPATH目錄中的文件。我懷疑這可能是因爲一旦我的$(OBJ)prereq被評估,結果對象本身都不在VPATH中,只是源文件。

我可以採取更好的方法嗎?我不能輕易更改這些遠程VPATH目錄的內容,因爲它們被不同所有者的許多不同應用程序使用。

+0

MadScientist的解決方案正是我所需要的,但他提到的警告將讓我在將來從這種事情中轉移出來...... –

回答

2

綜觀:

CPPSRC := $(wildcard *.cpp) 
CSRC := $(wildcard *.c) 
OBJ := $(CSRC:%.c=$(OBJ_DIR)/%.o) $(CPPSRC:%.cpp=$(OBJ_DIR)/%.o) 

$(BIN_DIR)/$(OUTPUT): $(OBJ) 

第一行說,讓所有在我的當前目錄中匹配的模式*.cpp的文件。第二行說,獲取當前目錄中與*.c模式匹配的所有文件。第三行說,將所有這些源文件轉換爲$(OBJ_DIR)目錄中的目標文件名。

最後一行說,當你想建立$(BIN_DIR)/$(OUTPUT)時,確保先建立所有這些目標文件。

你沒有告訴過它應該爲它可能在其他地方找到的源創建任何目標文件(例如,如/one/remote/dir/another/remote/dir)。那麼爲什麼它應該嘗試構建它們呢?

你必須找出這些文件並將它們添加到你的對象列表中。

你可以嘗試這樣的事:

VPATH = /one/remote/dir /another/remote/dir 
OBJ += $(patsubst %,$(OBJ_DIR)/%.o,$(notdir $(basename $(wildcard $(addsuffix /*.cpp,$(VPATH)) $(addsuffix /*.c,$(VPATH)))))) 

這增加了/*.cpp/*.c後綴在$(VPATH)每個目錄下,然後就一個通配符來獲取所有匹配的文件,然後採取基本名(去掉.cpp.c後綴),然後刪除目錄路徑,然後將每個基本文件名轉換爲$(OBJ_DIR),並將.o添加到最後。當然,如果你的系統中任何地方有兩個具有相同基本名稱的文件,那麼你運氣不好,你將不得不做更復雜的事情,例如保留目錄結構。