我正试图为我的项目制作一个库,但我对Makefiles非常非常陌生。我尝试了几种配置并添加了-I
,但都不起作用。
我有以下三个:
libft/
../includes/
....libft.h
../lst
....ft_lstnew.c
....ft_lstadd_front.c
....ft_lstadd_back.c
.... [...]
../src
....ft_isalpha.c
....ft_isalnum.c
.... [...]
和下面的makefile:
NAME=libft.a
LIBSO=libft.so
CC=gcc
CFLAGS=-Wall -Wextra -Werror
SRC_DIR=src/
BONUS_DIR=lst/
OBJ_DIR=obj/
SRC_FILES= ft_bzero.c
ft_isalmun.c
ft_isalpha.c
ft_isascii.c
ft_isdigit.c
ft_isprint.c
ft_memchr.c
ft_memcpy.c
ft_memmove.c
ft_memset.c
ft_strchr.c
ft_strlcat.c
ft_strlcpy.c
ft_strlen.c
ft_strncmp.c
ft_strrchr.c
ft_tolower.c
ft_toupper.c
BONUS_FILES=ft_lstadd_back.c
ft_lstadd_front.c
ft_lstdelone.c
ft_lstclear.c
ft_lstiter.c
ft_lstlast.c
ft_lstmap.c
ft_lstnew.c
ft_lstsize.c
SRC_PATH=$(addprefix $(SRC_DIR), $(SRC_FILES))
BONUS_PATH=$(addprefix $(BONUS_DIR), $(BONUS_FILES))
SRC_NAMES=$(SRC_FILES:.c=.o)
BONUS_NAMES=$(BONUS_FILES:.c=.o)
SRC_PATH_O=$(addprefix $(SRC_DIR), $(SRC_NAMES))
BONUS_PATH_O=$(addprefix $(BONUS_DIR), $(BONUS_NAMES))
HDR_NAME=libft.h
HDR_DIR=includes/
HDR= $(addprefix $(HDR_DIR),$(HDR_NAME))
all: $(NAME)
$(NAME): $(SRC_PATH_O)
ar rc $@ $<
ranlib $@
$(OBJ_DIR):
mkdir $@
$(OBJ_DIR)%.o: $(SRC_DIR)%.c $(HDR_NAME)
$(CC) $(CFLAGS) -c $< -o $@ -I $(HDR)
clean:
rm -rf $(OBJ_DIR)
fclean: clean
rm -f $(NAME)
re: fclean all
.PHONY: all clean fclean re
每次我在终端上输入make
我都得到这个
gcc -Wall -Wextra -Werror -c -o src/ft_bzero.o src/ft_bzero.c
src/ft_bzero.c:1:10: fatal error: libft.h: No such file or directory
1 | #include "libft.h"
| ^~~~~~~~~
compilation terminated.
make: *** [<builtin>: src/ft_bzero.o] Error 1
我错过了什么吗?这真的是我第一次。
是的,你错过了一些东西。
首先,看命令行make显示:
gcc -Wall -Wextra -Werror -c -o src/ft_bzero.o src/ft_bzero.c
注意,这里的输出不适合您创建的模式规则的配方:没有-I
选项,并且目标文件被写入src/
而不是obj/
。
从这里你应该意识到你的模式规则根本没有被使用,取而代之的是使用它的内置规则来构建目标文件。
为什么你的模式规则没有被使用?我们来看看:
$(OBJ_DIR)%.o: $(SRC_DIR)%.c $(HDR_NAME)
变量展开后是什么?
obj/%.o: src/%.c libft.h
此模式(像所有模式一样)只有在所有先决条件已经存在或可以构建时才能匹配。src/%.c
存在,在模式替换之后。libft.h
呢?不,这根本不存在。存在的是includes/libft.h
,但这不是一回事。
因此,该规则无法匹配,make返回使用其默认规则。
如果你想说每个目标文件都依赖于这个头文件,你必须在编写模式时使用头文件的正确路径。
接下来,这是错误的:
$(CC) $(CFLAGS) -c $< -o $@ -I $(HDR)
$(HDR)
是什么?这是文件的名称:include/libft.h
。你不包括头文件名与-I
;您包括目录查找头文件。所以这里需要的是$(HDR_DIR)
。