首页 > 解决方案 > 强制 make 在结束循环依赖之前查看文件

问题描述

我使用make有一个循环依赖:

CC              = gcc
IFLAGS          = -Iinclude
CFLAGS          = -Wall -g -c -fPIC -pedantic
AFLAGS          = -shared
LFLAGS          =
VERSION         = $(shell cat desc/major).$(shell cat desc/minor).$(shell cat desc/patch)
DFLAGS          = -D_XOPEN_SOURCE=700 -DLTKVER=\"$(VERSION)\"

OBJECTS         = $(patsubst src/%.c,tmp/%.o, $(shell ls -1 src/*.c))

#OUTPUT         = tmp/$(lastword $(subst /, ,$(shell pwd)))
OUT_BIN         = install/usr/lib/libLTK.so
OUT_MAN         = $(patsubst man/%,install/usr/share/man/%.gz, $(shell find man -type f))
PATH_INCLUDE    = install/usr/include/LTK-$(VERSION)
OUT_INCLUDE     = $(patsubst %,$(PATH_INCLUDE)/%, $(shell find include -type f -printf "%f\n"))
PC              = %

all: $(OUT_BIN) $(OUT_MAN) $(OUT_INCLUDE)
#   chmod 755 install/usr/lib/libLTK.so.$(VERSION)
    ln -sf install/usr/lib/libLTK.so.$(VERSION) install/usr/lib/libLTK.so
#   chmod 755 install/usr/include/LTK-$(VERSION)
#   chmod 644 install/usr/include/LTK-$(VERSION)/*
    ln -sf install/usr/include/LTK-$(VERSION) install/usr/include/LTK

$(OUT_BIN): $(OBJECTS)
    mkdir -p $(shell dirname $@)
    $(CC) $(AFLAGS) -o $@.$(VERSION) $^ $(LFLAGS)

tmp/%.o : src/%.c
    mkdir -p $(shell dirname $@)
    $(CC) $(CFLAGS) -o $@ $< $(DFLAGS) $(IFLAGS)

install/usr/share/%.gz : %
    mkdir -p $(shell dirname $@)
    gzip -c $< > $@

.SECONDEXPANSION:
%.h : $$(patsubst $(PATH_INCLUDE)/$$(PC),include/$$(PC),$$@)
    mkdir -p $(shell dirname $$@)
    cp $< $$@

clean:
    rm -rf tmp install

在第二次扩展头文件中,先决条件是从第二次扩展中生成的。但它是一个生成另一个标题的标题,这个新标题可以在磁盘上找到。但是 make 更喜欢考虑循环依赖并忽略它。在搜索目标以生成文件之前,如何强制 make 查看文件是否存在?

标签: makefile

解决方案


循环依赖完全独立于磁盘上存在或不存在的内容。当 make 运行时,它会解析 makefile 并构造一个表示目标之间依赖关系的图。该图必须是非循环的,因为 make 将遍历该图以查找目标是否已过期。如果图中有一个循环,那么 make 将永远递归尝试遍历该图。

例如:

a: b ; touch $@
b: a ; touch $@

这些文件是否存在并不重要:make仍然需要确保“a”比“b”更新以满足第一个依赖项,并且“b”比“a”更新以满足第二个依赖项.

显然,这不可能是真的。


推荐阅读