filter-out不是过滤文件? C 的 Makefile

问题描述 投票:0回答:1

所以我在这里得到了一个make文件,我的项目目前有一个master.c和slave.c,它们都有主要功能。因此我只想将slave.c 文件从构建过程中过滤掉。所以我在定义源文件时使用了过滤器。但是当运行 make 时,项目不断出现“main 的多个定义”错误。当过滤器应该隐藏slave.c 文件时为什么会出现这种情况?

########################################################################
####################### Makefile Template ##############################
########################################################################

#Compiler settings - Can be customized.
CC = gcc
CXXFLAGS = -std=c11 -Wall
LDFLAGS =

# Makefile settings - Can be customized.
APPNAME = master
SUBAPPNAME = slave
EXT = .c
SRCDIR = .
OBJDIR = .

############## Do not change anything from here downwards! #############
SRC := $(filter-out slave.c, $(wildcard $(SRCDIR)/*$(EXT)))
OBJ := $(SRC:$(SRCDIR)/%$(EXT)=$(OBJDIR)/%.o)
DEP := $(OBJ:$(OBJDIR)/%.o=%.d)
#UNIX-based OS variables & settings
RM = rm
DELOBJ = $(OBJ)
# Windows OS variables & settings
DEL = del
EXE = .exe
WDELOBJ = $(SRC:$(SRCDIR)/%$(EXT)=$(OBJDIR)\\%.o)

########################################################################
####################### Targets beginning here #########################
########################################################################

all: $(APPNAME)

# Builds the app
$(APPNAME): $(OBJ)
        $(CC) $(CXXFLAGS) -o $@ $^ $(LDFLAGS)

# Creates the dependecy rules
%.d: $(SRCDIR)/%$(EXT)
        @$(CPP) $(CFLAGS) $< -MM -MT $(@:%.d=$(OBJDIR)/%.o) >$@

# Includes all .h files
-include $(DEP)

# Building rule for .o files and its .c/.cpp in combination with all .h
$(OBJDIR)/%.o: $(SRCDIR)/%$(EXT)
        $(CC) $(CXXFLAGS) -o $@ -c $<

################### Cleaning rules for Unix-based OS ###################
# Cleans complete project
.PHONY: clean
clean:
        $(RM) $(DELOBJ) $(DEP) $(APPNAME)

# Cleans only all files with the extension .d
.PHONY: cleandep
cleandep:
        $(RM) $(DEP)

# Clean only all files with the extension .o
.PHONY: cleanobj
cleanobj:
        $(RM) $(DELOBJ)

# Cleans both files with .d and .o extensions
.PHONY: cleanod
cleanod:
        $(RM) $(DELOBJ) $(DEP)

c filter makefile
1个回答
1
投票

来电

SRC := $(filter-out slave.c, $(wildcard $(SRCDIR)/*$(EXT)))

只是一个字符串操作,也就是说,

make
不知道底层文件树,并尝试从列表
slave.c
中抛出字符串
yoursrcdir/slave.c yoursrcdir/master.c
,这显然失败了。尽管您一开始可能不同意,但这是一件好事,因为文件树上的过滤器操作的语义绝不是通用的或易于记录或传输。因此,
make
只查看所呈现的字符串,并决定逐个字符地比较哪些内容以及哪些内容要删除。 也就是说,重写为

SRC := $(filter-out $(SRCDIR)/slave.c, $(wildcard $(SRCDIR)/*$(EXT)))

将在你的情况下解决问题。 为了获得更广泛的功能,请查找两个函数

abspath
realpath
以获取规范格式的文件名,这会阻止
filter
等人。由于操作系统命名法的差异而被绊倒。

© www.soinside.com 2019 - 2024. All rights reserved.