簡體   English   中英

Makefile在Linux上運行但在Windows下無法運行,無法在子目錄中找到文件

[英]Makefile working in Linux but not under Windows, can't find files in subdirectory

我有一個在Linux下工作的makefile(gnu make),但是將其移植到Windows時不起作用。 makefile的目標是制作所有位於不同子目錄中的* .cpp文件,並將它們編譯為單個BUILD_DIR中的* .obj文件。

在linux和Windows之間,我僅調整了SOURCES變量,顯示了linux行,但已注釋。 當我檢查所有名稱和目錄時,它們顯示相同的內容(它們在透視符號中的相對路徑)和我期望的內容。

我在Windows上收到的“錯誤消息”是:make:***沒有規則來創建目標“ DEM.cpp”,這是“ DEM.obj”所需的。 停止。

在調試模式下,它說:文件'DEM.cpp'不存在。 (顯然是這樣)

在linux上,它通過VPATH查找文件,在調試模式下,它說:無需重新制作目標文件'DEM.cpp'; 使用VPATH名稱“ ./Code/DEM.cpp”。

linux和Windows中的子目錄結構相同,並且makefile從相同的位置運行。

問題:這里出了什么問題,我感覺這與在Windows上以不同方式處理VPATH有關,但我不確定。

我的makefile是:

# MAKEFILE    
# Some makefile settings 
SHELL = /bin/sh     #Make sure the shell is the standard shell
.SUFFIXES:      #Clear al implicit suffixes
.SUFFIXES: .cpp .obj    #Set used suffixes

# Variable Declaration
CXX := g++
BUILD_DIR = .\bin\Release
PROGRAM_NAME := DEM.exe

#SOURCES := $(shell find . -name '*.cpp')                   #All *.cpp files with directory (LINUX style)
SOURCES := $(shell FORFILES /S /M *.cpp /C "CMD /C ECHO @relpath")  #All *.cpp files with directory
NAMES := $(notdir $(basename $(SOURCES)))                   #Get all files names of the *.cpp files without extensions
OBJECTS := $(addsuffix .obj, $(NAMES))                      #Get the to be generate *.o files without directory
SRC_DIRS := $(dir $(SOURCES))                               #All the directory in which the sources are found
VPATH := $(SRC_DIRS) $(BUILD_DIR)

.PHONY: all
all: build                                  #Standard entry point, run release
    @echo "BUILD DONE"

.PHONY: build
    build: $(PROGRAM_NAME)
    @echo "BUILD DONE"

$(PROGRAM_NAME): $(OBJECTS)
    @echo "Link executable"
    $(CXX) -o $(BUILD_DIR)/$(PROGRAM_NAME) $(addprefix $(BUILD_DIR)/,$(OBJECTS))

$(OBJECTS): %.obj: %.cpp
    @echo "Compile into object code: $<"
    ${CXX} $(CXXFLAGS)  -c $< -o $(BUILD_DIR)/$@    #Compiles object code and places it in the $(BUILD_DIR)

更新1:基於一些程序員dude的評論,我用-p運行它,並得到以下有趣的結果:

# Not a target:
DEM.cpp:
#  Implicit rule search has been done.
#  File does not exist.
#  File has not been updated.

# Not a target:
World.cpp:
#  Implicit rule search has not been done.
#  Modification time never checked.
#  File has not been updated.

# Lot more targets below

似乎只是找不到DEM.cpp,而是找到其他所有內容。 DEM.cpp位於C:\\ Users \\ dklomp \\ Documents \\ Programming \\ C ++ Source \\ DEM \\ DEM \\ Code,但應解析為。\\ Code \\其他大多數文件位於Code的子目錄中。 但是stdafx.cpp也駐留在。\\ Code \\中,並且找到它沒有問題。

目錄名稱DEM是否類似於DEM.cpp可能是名稱沖突?

更新2:有關信息和結束。 我已經通過打印變量讀取變量來檢查VPATH,這似乎提供了正確的信息。 但是,如果我用@(info $ {VPATH))閱讀它,它似乎是空的:

@echo "VPATH print variable: "
@echo "$(VPATH)"
@echo "VPATH print info: "
$(info VPATH)

放棄:

"VPATH print variable: "
"./Code/InputOutput/ ./Code/InputOutput/ ./Code/InputOutput/ 
./Code/InputOutput/ ./Code/ ./Code/ ./Code/Models/ ./Code/Models/ 
./Code/Forces/ ./Code/Forces/ ./Code/Forces/ ./Code/Forces/ ./Code/Forces/ 
./Code/Forces/ ./Code/Forces/ ./Code/Forces/ ./Code/Forces/ ./Code/Tools/ 
./Code/Tools/ ./Code/Tools/ ./Code/Tools/ ./Code/Solvers/ ./Code/Solvers/ 
./Code/Solvers/ ./Code/World/ ./Code/World/ ./Code/World/ ./Code/World/ 
./Code/World/ ./Code/Interactions/ ./Code/Interactions/ ./Code/Interactions/ 
./Code/Interactions/ ./Code/Interactions/ ./Code/Interactions/                                                               
bin\Release"
"VPATH print info: "

確實有很多重復(將使用hardcoreHenry的排序建議),但是看起來不錯。 但是,由於某些原因,VPATH信息為空。

但是,通過code_fodder實現建議的解決方案並刪除所有內聯代碼注釋是可行的。 變量聲明中的內聯代碼注釋似乎無關緊要,rules部分中的注釋對於Windows而言確實有用,Linux似乎可以在任何地方很好地處理內聯代碼注釋。

像往常一樣感謝您的幫助和建議。

我在當前位置之前有空格的路徑中對此進行了測試(例如, d:\\path with spaces\\myfolder\\sub_folder1\\sub_folder2\\ )。

我認為FORFILES語法/輸出存在一些問題-至少我無法使其正常工作。 從這里第二個答案開始使用更通用的rwildcard時,它就開始很好地工作。 然后,我添加了創建/清理輸出文件夾的規則。

我也刪除了任何內聯注釋,因為我不是100%確信它們是有效的,因為它們到處都留有空格字符,並且makefile對此不太寬容... IE確保您不會在任何行上留下任何尾隨空白。

另外-這一切都假設其是gnu-make而並非nmake

# MAKEFILE    
# Some makefile settings 
SHELL = /bin/sh
.SUFFIXES:
.SUFFIXES: .cpp .obj

# Variable Declaration
CXX := g++
BUILD_DIR = .\bin\Release
PROGRAM_NAME := DEM.exe

# Define a recursive wild card function that is portable.
rwildcard=$(foreach d,$(wildcard $1*),$(call rwildcard,$d/,$2) $(filter $(subst *,%,$2),$d))

#SOURCES := $(shell FORFILES /S /M *.cpp /C "CMD /C ECHO @relpath")
SOURCES := $(call rwildcard, ./, *.cpp)
$(info SOURCES: $(SOURCES))
NAMES := $(notdir $(basename $(SOURCES)))
OBJECTS := $(addsuffix .obj, $(NAMES))
SRC_DIRS := $(dir $(SOURCES))
VPATH := $(SRC_DIRS) $(BUILD_DIR)

.PHONY: all
all: create_dirs build
    @echo "BUILD DONE"

# Has an order dependency on create_dirs to ensure that happens first, and so 
# it works with parallel build (e.g. `make -j4`)
.PHONY: build
build: $(PROGRAM_NAME) | create_dirs
    @echo "BUILD DONE"

$(PROGRAM_NAME): $(OBJECTS)
    @echo "Link executable"
    $(CXX) -o $(BUILD_DIR)/$(PROGRAM_NAME) $(addprefix $(BUILD_DIR)/,$(OBJECTS))

$(OBJECTS): %.obj: %.cpp
    @echo "Compile into object code: $<"
    ${CXX} $(CXXFLAGS)  -c $< -o $(BUILD_DIR)/$@

.PHONY: create_dirs
create_dirs:
    @echo "creating dirs"
    mkdir -p $(BUILD_DIR)

.PHONY: clean
clean:
    @echo "cleaning"
    rm -rf $(BUILD_DIR)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM