[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: Performance loss when trying to use grouped targets
From: |
Stephen Touset |
Subject: |
Re: Performance loss when trying to use grouped targets |
Date: |
Tue, 5 Mar 2024 21:58:10 +0100 |
On Mar 5, 2024 at 10:06:44, Paul Smith <psmith@gnu.org> wrote:
> These two formulations are not really the same: grouped targets work
> differently and can't be replaced with an expanded version. A grouped
> target:
>
> a.x b.x &: a.q b.q ; <cmd>
>
> can only be emulated by something like this:
>
> a.x b.x : .sentinel ;
>
> .sentinel : a.q b.q ; <cmd> ; touch $@
This actually comes close to working for my use-case. It fixes the
O(n^2) performance issue of having every file depend on every other
file since the `.sentinel` intermediate step short-circuits things and
only needs to be evaluated once.
Unfortunately it forces a full rebuild in my case. The `Makefile` looks
something like:
```
.PHONY: output
output: output_a output_b
output_a: build/a/x build/a/y
[ build for a performed here ]
output_b: build/b/x build/b/y
[ build for b performed here ]
build/a/x build/a/y build/b/x build/b/y: build/.sentinel
build/.sentinel: src/a/x src/a/y src/b/x src/b/y
cp -a src build
touch $@
```
This is a minimal example, but in my case the number of outputs is large
and each of those outputs depends upon a few dozen sources. With this
style of recipe, if any of the sources is changed it causes
`make` to consider `build/.sentinel` stale. This in turn causes all the
outputs to be considered stale.
What I would like is if I `touch build/a/x` and re-`make`, the whole
source directory is copied into the build directory in one go *but* only
`output_a` is rebuilt (since the timestamps for everything under
`build/b` are unchanged).