Вопрос по c++ – makefile автоматическое обнаружение src-файлов и генерация зависимостей

2

У меня есть следующие настройки для моего проекта C ++:

в папке src есть * .cpp и соответствующие файлы * .h и в obj-папках я хочу иметь свои .o-файлы.

Пока что компиляция и компоновка не являются проблемой. Но теперь у меня слишком много файлов .cpp и .h, чтобы поместить их в Makefile вручную. Поэтому я решил написать эту маленькую инструкцию в make-файле:

<code>collect_sources:
@echo "collecting source files";
@echo "SRCS = \\" > sources;
@for file in ./src/*.cpp; \
do \
    echo "$$file \\" >> sources; \
done
</code>

Я тоже делаю

<code>-include sources
</code>

в начале make-файла

Полученный файлsources выглядит хорошо, хотя в последней строке есть обратный слеш, который мне не нравится. Но афаик это тоже должно быть вредно.

Теперь мне также нужно автоматически создавать зависимости. В моей последней версии, в которой я определил * .cpp-файлы какSRCS прямо в Makefile, следующий код был хорош:

<code>$(SRCDIR)/%.cpp:
  @$(CXX) $(DEPFLAGS) -MT \
  "$(subst $(SRCDIR),$(OBJDIR),$(subst $(EXT_SRC),$(EXT_OBJ),$$file))" \
  $(addprefix ,$$file) >> $(DEP);
clear_dependencies:
    echo "" > $(DEP);

depend: clear_dependencies $(SRCS)
</code>

Но с учетомsources-file, он никогда не достигает верхнего блока кода.

Вот константы, определенные в верхней части Makefile:

<code>CXX = g++
CXXFLAGS = -Wall \
       -Wextra \
       -Wuninitialized \
       -Wmissing-declarations \
       -pedantic \
       -O3 \
       -p -g -pg
LDFLAGS =  -p -g -pg
DEPFLAGS = -MM

SRCDIR  = ./src
OBJDIR  = ./obj

TARGET = ./bin/my_funky_function_which_is_not_the_real_name

-include sources

OBJSTMP =   $(SRCS:.cpp=.o)
OBJS        =   $(OBJSTMP:$(SRCDIR)=$(OBJDIR))
DEP = depend.main
EXT_SRC =   .cpp
EXT_OBJ =   .o
</code>

Что мне не хватает? Является ли мой подход действительным / выполнимым?

шаг за шагом к абсолютному оптимуму ;-) stefan
Есть одна простая ошибка и множество возможных улучшений. Как далеко вы хотите пойти? Beta
на заметку: пожалуйста, не предлагайте никаких инструментов, которые делают это уже. Я действительно хочу понять это и иметь полный контроль над тем, что происходит. stefan

Ваш Ответ

1   ответ
7

1: Вашcollect_sources:... include sources славный Рубе Голдберг взломать. Просто сделай это:

SRCS = $(wildcard ./src/*.cpp)

И если вы хотите подтвердить это на глаз, вы можете сделать это:

$(info $(SRCS))

2:

clear_dependencies:
    echo "" > $(DEP);

Просто ради эстетики, давайте исправим это.

clear_dependencies:
    $(RM) $(DEP);

3:

$(SRCDIR)/%.cpp:
    @$(CXX) $(DEPFLAGS) -MT \
  "$(subst $(SRCDIR),$(OBJDIR),$(subst $(EXT_SRC),$(EXT_OBJ),$$file))" \
  $(addprefix ,$$file) >> $(DEP);

Это займет некоторую работу. Сначала возникает непосредственная проблема: цель - это реальный файл, который существует, и у правила нет предварительных условий. Поэтому правило не будет выполняться (я понятия не имею, почему оно работало у вас в предыдущей версии, может быть, что-то еще было иначе). В качестве временного исправления я предлагаю перейти к статическому шаблонному правилу и целям PHONY:

.PHONY:$(SRCS)
$(SRCS) : $(SRCDIR)/%.cpp:
    @$(CXX) $(DEPFLAGS) -MT \
   ...

Посмотрим, если все это работает, то мы можем заняться большими делами.

Error: User Rate Limit Exceeded[email protected]Error: User Rate Limit Exceeded./src/foo.cppError: User Rate Limit Exceeded$$fileError: User Rate Limit Exceeded
Error: User Rate Limit Exceeded stefan
Error: User Rate Limit Exceeded stefan
Error: User Rate Limit Exceeded
Error: User Rate Limit Exceeded stefan

Похожие вопросы