Skip to content

Makefile: let ccache cache objects built with the precompiled header - #2464

Open
HaraldNordgren wants to merge 1 commit into
git:masterfrom
HaraldNordgren:makefile-ccache-pch
Open

HaraldNordgren wants to merge 1 commit into
git:masterfrom
HaraldNordgren:makefile-ccache-pch

Conversation

@HaraldNordgren

@HaraldNordgren HaraldNordgren commented Oct 22, 2026 •

Copy link
Copy Markdown
Contributor

With ccache, building after switching between two feature branches gets about 6 times faster. The first build of each branch gets about 25% slower while ccache fills its cache.

Changes in v2:

  • Move the CCACHE_SLOPPINESS export from the precompiled header targets into the ifndef NO_PRECOMPILED_HEADER block.

cc: Ben Knoble ben.knoble@gmail.com
cc: Patrick Steinhardt ps@pks.im

@HaraldNordgren

Copy link
Copy Markdown
Contributor Author

/submit

@gitgitgadget-git

Copy link
Copy Markdown

Submitted as pull.2464.git.git.1793104847288.gitgitgadget@gmail.com

To fetch this version into FETCH_HEAD:

git fetch https://github.com/gitgitgadget/git/ pr-git-2464/HaraldNordgren/makefile-ccache-pch-v1

To fetch this version to local tag pr-git-2464/HaraldNordgren/makefile-ccache-pch-v1:

git fetch --no-tags https://github.com/gitgitgadget/git/ tag pr-git-2464/HaraldNordgren/makefile-ccache-pch-v1

@gitgitgadget-git

Copy link
Copy Markdown

Ben Knoble wrote on the Git mailing list (how to reply to this email):

> Le 27 oct. 2026 à 08:49, Harald Nordgren via GitGitGadget <gitgitgadget@gmail.com> a écrit :
> 
> From: Harald Nordgren <haraldnordgren@gmail.com>
> 
> Since 8d3a673147 (Makefile: precompile "git-compat-util.h",
> 2026-09-15), rebuilding Git with ccache is almost as slow as building
> it without. ccache refuses to cache a compilation that uses a
> precompiled header unless its "pch_defines" and "time_macros"
> sloppiness is enabled, so it runs the compiler for nearly every object
> file, even after a "make clean" in a tree it has already built.
> 
> Both settings are safe for our build. The precompiled header is only
> pulled in with "-include" ahead of the source file, so no "#define" in
> a source file can come before it, and none of our sources use
> __DATE__, __TIME__ or __TIMESTAMP__.
> 
> Enable them for the precompiled header and the objects built with it.
> On my machine, "make clean && make -j8" with a warm cache goes from
> about 100 seconds to under 30.
> 
> With Clang, switching to a branch that changes one of the headers the
> precompiled header includes and back again still misses the cache,
> because Clang records the modification times of those headers in the
> precompiled header.
> 
> Signed-off-by: Harald Nordgren <haraldnordgren@gmail.com>
> ---
>    Makefile: let ccache cache objects built with the precompiled header
> 
>    With ccache, building after switching between two feature branches gets
>    about 6 times faster. The first build of each branch gets about 25%
>    slower while ccache fills its cache.
> 
> Published-As: https://github.com/gitgitgadget/git/releases/tag/pr-git-2464%2FHaraldNordgren%2Fmakefile-ccache-pch-v1
> Fetch-It-Via: git fetch https://github.com/gitgitgadget/git pr-git-2464/HaraldNordgren/makefile-ccache-pch-v1
> Pull-Request: https://github.com/git/git/pull/2464

I can’t comment on the above, not being a ccache user myself.

> Makefile | 2 ++
> 1 file changed, 2 insertions(+)
> 
> diff --git a/Makefile b/Makefile
> index a96be506b5..43ea5e0c40 100644
> --- a/Makefile
> +++ b/Makefile
> @@ -2946,6 +2946,8 @@ $(PRECOMPILED_HEADER_GCH): %.gch: % GIT-CFLAGS $(missing_dep_dirs) $(missing_com
> $(PRECOMPILED_HEADER_USERS): %.o: %.c $(PRECOMPILED_HEADER_GCH) GIT-CFLAGS $(missing_dep_dirs) $(missing_compdb_dir)
>    $(QUIET_CC)$(CC) -o $*.o -c -include $(PRECOMPILED_HEADER) -Winvalid-pch $(dep_args) $(compdb_args) $(ALL_CFLAGS) $(EXTRA_CPPFLAGS) $<
> 
> +$(PRECOMPILED_HEADER_GCH) $(PRECOMPILED_HEADER_USERS): export CCACHE_SLOPPINESS += pch_defines,time_macros
> +

This is a little curious to me. I’m familiar with the GNU Make-ism 
to set variables for particular targets; how does the export work?
Is it the same but with a propagation to the recipe processes?

Would it be better (for some definition…) to put the export in the 2
pre-compiled header recipes directly?

And, what about Meson?

@gitgitgadget-git

Copy link
Copy Markdown

User Ben Knoble <ben.knoble@gmail.com> has been added to the cc: list.

Since 8d3a673 (Makefile: precompile "git-compat-util.h",
2026-09-15), rebuilding Git with ccache is almost as slow as building
it without. ccache refuses to cache a compilation that uses a
precompiled header unless its "pch_defines" and "time_macros"
sloppiness is enabled, so it runs the compiler for nearly every object
file, even after a "make clean" in a tree it has already built.

Both settings are safe for our build. The precompiled header is only
pulled in with "-include" ahead of the source file, so no "#define" in
a source file can come before it, and none of our sources use
__DATE__, __TIME__ or __TIMESTAMP__.

Enable them whenever we build with the precompiled header.
On my machine, "make clean && make -j8" with a warm cache goes from
about 100 seconds to under 30.

With Clang, switching to a branch that changes one of the headers the
precompiled header includes and back again still misses the cache,
because Clang records the modification times of those headers in the
precompiled header.

Signed-off-by: Harald Nordgren <haraldnordgren@gmail.com>
@gitgitgadget-git

Copy link
Copy Markdown

Harald Nordgren wrote on the Git mailing list (how to reply to this email):

> > @@ -2946,6 +2946,8 @@ $(PRECOMPILED_HEADER_GCH): %.gch: % GIT-CFLAGS $(missing_dep_dirs) $(missing_com
> > $(PRECOMPILED_HEADER_USERS): %.o: %.c $(PRECOMPILED_HEADER_GCH) GIT-CFLAGS $(missing_dep_dirs) $(missing_compdb_dir)
> >    $(QUIET_CC)$(CC) -o $*.o -c -include $(PRECOMPILED_HEADER) -Winvalid-pch $(dep_args) $(compdb_args) $(ALL_CFLAGS) $(EXTRA_CPPFLAGS) $<
> >
> > +$(PRECOMPILED_HEADER_GCH) $(PRECOMPILED_HEADER_USERS): export CCACHE_SLOPPINESS += pch_defines,time_macros
> > +
>
> This is a little curious to me. I’m familiar with the GNU Make-ism
> to set variables for particular targets; how does the export work?
> Is it the same but with a propagation to the recipe processes?
>
> Would it be better (for some definition…) to put the export in the 2
> pre-compiled header recipes directly?

Yeah, that could be a good idea.

> And, what about Meson?

I think it's not touched by this? My goal is just to speed up my local builds.


Harald

@gitgitgadget-git

Copy link
Copy Markdown

"D. Ben Knoble" wrote on the Git mailing list (how to reply to this email):

On Tue, Oct 27, 2026 at 4:00 PM Harald Nordgren
<haraldnordgren@gmail.com> wrote:
>
> > And, what about Meson?
>
> I think it's not touched by this? My goal is just to speed up my local builds.

Yeah, it'd generally be nice to keep the 2 on par though ;)

I don't know enough about our pch infra, though, so I'll bow out from
here. Just thought maybe we should make Meson do the same?

-- 
D. Ben Knoble

@gitgitgadget-git

Copy link
Copy Markdown

Patrick Steinhardt wrote on the Git mailing list (how to reply to this email):

On Tue, Oct 27, 2026 at 05:57:38PM -0400, D. Ben Knoble wrote:
> On Tue, Oct 27, 2026 at 4:00 PM Harald Nordgren
> <haraldnordgren@gmail.com> wrote:
> >
> > > And, what about Meson?
> >
> > I think it's not touched by this? My goal is just to speed up my local builds.
> 
> Yeah, it'd generally be nice to keep the 2 on par though ;)
> 
> I don't know enough about our pch infra, though, so I'll bow out from
> here. Just thought maybe we should make Meson do the same?

As Meson auto-detects ccache I'd think that stuff like this should
rather be handled in Meson itself. I e.g. found [1], which feels like
the right direction to me.

But if somebody wants to implement this in our instructions meanwhile I
won't complain.

Patrick

[1]: https://github.com/mesonbuild/meson/issues/14662

@gitgitgadget-git

Copy link
Copy Markdown

User Patrick Steinhardt <ps@pks.im> has been added to the cc: list.

@gitgitgadget-git

Copy link
Copy Markdown

Harald Nordgren wrote on the Git mailing list (how to reply to this email):

> > > > And, what about Meson?
> > >
> > > I think it's not touched by this? My goal is just to speed up my local builds.
> >
> > Yeah, it'd generally be nice to keep the 2 on par though ;)
> >
> > I don't know enough about our pch infra, though, so I'll bow out from
> > here. Just thought maybe we should make Meson do the same?
>
> As Meson auto-detects ccache I'd think that stuff like this should
> rather be handled in Meson itself. I e.g. found [1], which feels like
> the right direction to me.
>
> But if somebody wants to implement this in our instructions meanwhile I
> won't complain.
>
> Patrick
>
> [1]: https://github.com/mesonbuild/meson/issues/14662

Ok, so I'll leave Meson out of this. Maybe I'll look into opening a PR
there instead.


Harald

@HaraldNordgren

Copy link
Copy Markdown
Contributor Author

/submit

@gitgitgadget-git

Copy link
Copy Markdown

Submitted as pull.2464.v2.git.git.1793262816420.gitgitgadget@gmail.com

To fetch this version into FETCH_HEAD:

git fetch https://github.com/gitgitgadget/git/ pr-git-2464/HaraldNordgren/makefile-ccache-pch-v2

To fetch this version to local tag pr-git-2464/HaraldNordgren/makefile-ccache-pch-v2:

git fetch --no-tags https://github.com/gitgitgadget/git/ tag pr-git-2464/HaraldNordgren/makefile-ccache-pch-v2

@gitgitgadget-git

Copy link
Copy Markdown

Harald Nordgren wrote on the Git mailing list (how to reply to this email):

> > > > > And, what about Meson?
> > > >
> > > > I think it's not touched by this? My goal is just to speed up my local builds.
> > >
> > > Yeah, it'd generally be nice to keep the 2 on par though ;)
> > >
> > > I don't know enough about our pch infra, though, so I'll bow out from
> > > here. Just thought maybe we should make Meson do the same?
> >
> > As Meson auto-detects ccache I'd think that stuff like this should
> > rather be handled in Meson itself. I e.g. found [1], which feels like
> > the right direction to me.
> >
> > But if somebody wants to implement this in our instructions meanwhile I
> > won't complain.
> >
> > Patrick
> >
> > [1]: https://github.com/mesonbuild/meson/issues/14662
>
> Ok, so I'll leave Meson out of this. Maybe I'll look into opening a PR
> there instead.

This has now been merged into Meson:
https://github.com/mesonbuild/meson/pull/16317


Harald

@gitgitgadget-git

Copy link
Copy Markdown

This branch is now known as hn/ccache-sloppiness-for-pch.

@gitgitgadget-git

Copy link
Copy Markdown

This patch series was integrated into seen via b0ee26c.

@gitgitgadget-git gitgitgadget-git Bot added the seen label Nov 2, 2026
@gitgitgadget-git

Copy link
Copy Markdown

There was a status update in the "New Topics" section about the branch hn/ccache-sloppiness-for-pch on the Git mailing list:

The build procedure using GNU Make has been updated to export the
'CCACHE_SLOPPINESS' variable with 'pch_defines' and 'time_macros'
when the precompiled header is in use, which allows 'ccache' to
actually cache the objects built with it.

Needs review.
source: <pull.2464.v2.git.git.1793262816420.gitgitgadget@gmail.com>

@gitgitgadget-git

Copy link
Copy Markdown

There was a status update in the "Cooking" section about the branch hn/ccache-sloppiness-for-pch on the Git mailing list:

The build procedure using GNU Make has been updated to export the
'CCACHE_SLOPPINESS' variable with 'pch_defines' and 'time_macros'
when the precompiled header is in use, which allows 'ccache' to
actually cache the objects built with it.

Needs review.
source: <pull.2464.v2.git.git.1793262816420.gitgitgadget@gmail.com>

@gitgitgadget-git

Copy link
Copy Markdown

There was a status update in the "Cooking" section about the branch hn/ccache-sloppiness-for-pch on the Git mailing list:

The build procedure using GNU Make has been updated to export the
'CCACHE_SLOPPINESS' variable with 'pch_defines' and 'time_macros'
when the precompiled header is in use, which allows 'ccache' to
actually cache the objects built with it.

Needs review.
source: <pull.2464.v2.git.git.1793262816420.gitgitgadget@gmail.com>

@gitgitgadget-git

Copy link
Copy Markdown

There was a status update in the "Cooking" section about the branch hn/ccache-sloppiness-for-pch on the Git mailing list:

The build procedure using GNU Make has been updated to export the
'CCACHE_SLOPPINESS' variable with 'pch_defines' and 'time_macros'
when the precompiled header is in use, which allows 'ccache' to
actually cache the objects built with it.

Needs review.
source: <pull.2464.v2.git.git.1793262816420.gitgitgadget@gmail.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant