2012-07-04 4 views
1

Я пытаюсь сделать Makefile, который делает следующее:Почему моя целевая переменная makefile не работает?

  • получает исходные файлы из Src каталога
  • помещает объектные файлы в каталоге OBJ
  • помещает бинарные файлы в bin
  • ставит цели выпуска в rel
  • ставит отладочных целей в Dbg директории

Первая проблема у меня в том, что, кажется, мои целевые конкретные переменные не будут работать здесь является Makefile:

# Build Directories 
src_dir=src 
obj_dir=obj 
bin_dir=bin 

cc=cl 
cc_flags= 

# create the directory for the current target. 
[email protected] -p $(@D) 

# source files 
src = MainTest.cpp 

# object files - replace .cpp on source files with .o and add the temp directory prefix 
obj = $(addprefix $(obj_dir)/$(cfg_dir)/, $(addsuffix .obj, $(basename $(src)))) 

release: cfg_dir = rel 
release: executable 

debug: cfg_dir = dbg 
debug: cc_flags += -Yd -ZI 
debug: executable 

executable: $(bin_dir)/$(cfg_dir)/MainTest.exe 

# build TwoDee.exe from all of the object files. 
$(bin_dir)/$(cfg_dir)/MainTest.exe : $(obj) 
    $(dir_guard) 
    $(cc) -out:[email protected] $(obj) -link 

# build all of the object files in the temp directory from their corresponding cpp files. 
$(obj_dir)/$(cfg_dir)/%.obj : $(source_dir)/%.cpp 
    $(dir_guard) 
    $(cc) $(cc_flags) -Fo$(obj_dir)/$(cfg_dir) -c $< 

Когда я бегу сделать отладки я получаю:

make: *** No rule to make target `obj//MainTest.obj', needed by `bin//MainTest.exe'. 

Существует также что-то еще не так, потому что если я удалю отладки и выпуска переменных и жёстко cfg_dir в отн тогда я получаю:

make: *** No rule to make target `obj/rel/MainTest.obj', needed by `bin/rel/MainTest.exe'. Stop. 

Так мое правило объект должен быть неправильным. Я новичок в создании файлов, поэтому, если кто-то видит другие вещи, которые ошибаются, комментарии приветствуются.

ответ

1

Целевые переменные доступны только в рецептах, а не в правилах. Это связано с тем, что правила анализируются при чтении Makefile, и из этого выводятся зависимости.

Чтобы получить ваши правила с учетом нескольких возможных значений cfg_dir, я предлагаю вам ознакомиться с примером в разделе eval руководства GNU Make. Это объясняет следующее:

release: $(bin_dir)/rel/MainTest.exe 

debug: cc_flags += -Yd -ZI 
debug: $(bin_dir)/dbg/MainTest.exe 

define template = 

# build TwoDee.exe from all of the object files. 
$(bin_dir)/$(cfg_dir)/MainTest.exe : $(obj) 
    $$(dir_guard) 
    $$(cc) -out:[email protected] $(obj) -link 

# build all of the object files in the temp directory from their corresponding cpp files. 
$(obj): $(obj_dir)/$(cfg_dir)/%.obj : $$(src_dir)/%.cpp 
    $$(dir_guard) 
    $$(cc) $$(cc_flags) -Fo$(obj_dir)/$(cfg_dir) -c $$< 

endef 
$(foreach cfg_dir,rel dbg,$(eval $(template))) 
+0

Это имеет смысл, я попытаюсь использовать eval. Вы знаете, почему мое правило obj не работает, даже когда я использую переменную, не предназначенную для конкретной цели? – Farnk

+0

Я попытался использовать eval, но он, похоже, не работает. Есть ли способ отладить это? – Farnk

+0

Вы должны перечислить все файлы, к которым применяются правила шаблона: prepend '$ (obj):' этому правилу, как я сделал выше. Также не следует смешивать 'src_dir' и' source_dir'. С этими изменениями и настройкой для gcc и его различных опций все работает для меня. – MvG

Смежные вопросы