Stack Overflow 社区您好,
我在 C 项目中的 Makefile 中遇到问题,其中源文件中的更改(除了 SRC 变量中列出的第一个文件)不会触发重新编译。我有一个包含源文件、目标文件和依赖文件的典型设置,并且我在 Makefile 中为我的规则使用标准模式。
问题:
当我修改除 main.c 之外的任何源文件并运行 make 时,不会检测到这些更改,并且不会发生重新编译。尽管在我的 objs 文件夹中正确生成了所有对象文件和依赖项文件,但仍然如此。例如,如果我修改 main.c,make 会正确检测到更改并重新编译它。但是,修改任何其他文件(如 utils.c 或 Geometry.c)不会触发重新编译。
这是我的 Makefile 的片段供参考:
SRC = $(SRCDIR)main.c \
$(SRCDIR)utils.c \
$(SRCDIR)geomtery.c \
... (other source files) ...
OBJ = $(SRC:$(SRCDIR)%.c=$(OBJDIR)%.o)
DEP = $(OBJ:.o=.d)
-include $(DEP)
CC = gcc
CFLAGS = -Wall -Wextra -Werror -O3 # -g -g3 -fsanitize=address
LFLAGS = -lm -lft -lmlx -framework OpenGL -framework AppKit
DEP_FLAGS = -MMD -MP
all: start_compilation $(NAME) end_compilation
start_compilation:
@printf "\n$(YELLOW)Compiling...$(WHITE)\n"
end_compilation:
@printf "$(GREEN)Compilation succesfull!$(WHITE)\n"
$(OBJDIR)%.o: $(SRCDIR)%.c
@mkdir -p $(OBJDIR)
$(CC) $(CFLAGS) $(DEP_FLAGS) -I $(INCLUDES) -c $< -o $@
$(NAME): $(OBJ) $(LIBFT) $(MLX)
@printf "\n$(CYAN)Generating project executable...$(WHITE)\n"
$(CC) $(CFLAGS) $(LFLAGS) $(OBJ) -L $(LFT_PATH) -L $(MLX_PATH) -o $(NAME)
我尝试过的:
验证是否为每个 .c 文件生成了 .d 文件,并且它们包含正确的依赖项。 检查 .o 和 .d 文件的时间戳以确保它们在修改时得到更新。 尝试了 SRC 中源文件的不同顺序,但无论顺序如何,问题仍然存在。 我想知道我的 Makefile 配置中是否缺少某些内容导致此行为。有没有人遇到过类似的问题或者可以发现我的设置中的潜在错误?任何帮助或见解将不胜感激。
默认情况下,Make 将始终构建在 makefile 中找到的第一个显式目标。
您将
include
放在文件的开头:
-include $(DEP)
...
all:
这意味着除非您指定特定目标(例如通过运行
make all
),否则它将构建在任何包含的文件中找到的第一个目标。这可能不是您想要的。
我还应该说,这个:
all: start_compilation $(NAME) end_compilation
如果您使用并行构建运行,不太可能正常工作。一般来说,您不能“命令”使用先决条件来构建目标。它只是碰巧起作用,因为 make 会按照特定的顺序构建东西,并且如果您使用
-j1
(串行)构建模式,您可以确保在下一个开始之前完成前一个先决条件。