2016-09-27 2 views
0

マイプロジェクト構造は次のようになります。ソースファイルがさまざまなディレクトリにある場合のmakefileのコーディング方法は?

. 
├── build 
│   ├── makefile 
└── src 
    ├── subsys1 
    │   ├── includes 
    │   └── src_1.cpp 
    └── subsys2 
     ├── includes 
     └── src_2.cpp 

私は上記のソースファイルから実行ファイル「myappに」を構築するためのmakefileを書かれている:

print-% : ; @echo $* = $($*) 

# Application name 
APP := myapp 

# Set the directory to store the object files in 
OBJDIR_R = _gnuRelease 
OBJDIR_D = _gnuDebug 

# Names of compiler and linker, and their associated switches 
CXX:=g++ 
LINKER:=g++ 
CXXFLAGS+=-Wall -std=c++11 -pedantic -lpthread -m64 

ifeq ($(DEBUG),1) 
OBJDIR := $(OBJDIR_D) 
CXXFLAGS += -g 
else 
OBJDIR := $(OBJDIR_R) 
CXXFLAGS += -O2 
endif 

LDFLAGS = 

# Set the name of the output executable 
EXEFILE := LedaAP 

VPATH = ../src/subsys1 ../src/subsys2 

CPP_FILES = src_1.cpp src_2.cpp 

OBJ_FILES = $(patsubst %.cpp,%.o,$(CPP_FILES)) 

DEP_FILES = $(patsubst %.cpp,%.d,$(CPP_FILES)) 

INC_DIRS := ../src/subsys1/includes ../src/subsys2/includes 
INC_SWITCHES=$(foreach d, $(INC_DIRS), -I$d) 

# This default target builds the executable by linking the object files 
$(APP) : $(OBJ_FILES) 
    $(LINKER) $(CXXFLAGS) $^ -o [email protected] 

# A rule to build an .o file from a .cpp file 
%.o: %.cpp 
    $(CXX) $(CXXFLAGS) $(INC_SWITCHES) -c $< -o [email protected] 

# Running 'make clean' deletes the executables and all the libraries. 
.PHONY: clean 
clean: 
    @echo Deleting executables and libraries. Use make clean_exe to delete just the executables. 
    @rm -f $(OBJDIR_D)/$(EXEFILE) 
    @rm -f $(OBJDIR_R)/$(EXEFILE) 
    @rm -rf $(OBJDIR_D) 
    @rm -rf $(OBJDIR_R) 

結果は、ビルド中にオブジェクトファイルおよび実行可能ですディレクトリ:

build 
├── makefile 
├── myapp 
├── src_1.o 
└── src_2.o 

私が実際にしたい:

build 
├── _gnuRelease 
│   ├── myapp 
│   └── objects 
│    ├── src_1.o 
│    └── src_2.o 
└── makefile 

どうすれば達成できますか?

+0

こんにちはデビッド、私は以前も同様の質問がありました。この投稿をチェックしてください:http://stackoverflow.com/questions/39015453/building-c-program-out-of-source-tree-with-gnu-make –

+0

ありがとう、それは非常に便利な解決策です。 – DavidA

答えて

0

行の場合:ディレクトリ名を入力することをお勧めします(例:CPP_FILES = subsys1/src_1.cpp subsys2/src_2.cpp)。第1に、2つのサブシステムが同じ名前のファイルを持っていて、次にmakefileを簡単にして保守しやすくすると、問題を回避できます。

OBJ_FILES:OBJ_FILES=$(SOURCE_FILES:%.cpp=$(OBJ_DIR)/%.o)にディレクトリを追加し、それに応じてパターンルールを変更します。$(OBJ_DIR)/%.o : %.cpp .oファイルが適切なディレクトリに置かれます。

+0

あなたの答えをありがとう。ディレクトリ名で各srcファイルを指定する方が良いと私は同意します。しかし、私の難しさは、objファイルのパスを生成することです。私はそのディレクトリを取り除き、それを私の望むオブジェクトファイルパスに置き換える必要があります。だから、patsubstを使ってどうすれば '../subsys1/'か '../subsys2/'を取り除いてOBJDIRと置き換えることができますか?特に実際のプロジェクトのように、私は '../../some_dir/'にいくつかのファイルを持っています。正規表現を使用できますか? – user1768576

+0

@ user1768576: '$(addprefix $(OBJDIR)/、$(notdir $(SOURCE_FILES)))' – Beta

+0

ありがとうございました。だから今私は持っています: 'CPP_FILES = ../src/subsys1/src_1.cpp ../src/subsys1/src_2.cpp OBJ_FILES_TMP = $(patsubst%.cpp、%.o、$(CPP_FILES)) OBJ_FILES私の依存関係のルールはまだです: '%.o:%.cpp \t $(CXX)$(CXXFLAGS)$(INC_SWITCHES) - = $(addprefix $(OBJDIR)/、$(notdir $(OBJ_FILES_TMP) c $ <-o $ @ 'なので、makeを実行すると、myappで必要な_gnuRelease/src_1.oを作成するルールがありません。パスの変更に対処するためにこの依存関係ルールを変更するにはどうすればよいですか? – DavidA

関連する問題