6

I've tried using precompiled headers with GCC to speed up one of my builds. It is a project with around 80 files, most of which include a single header, which I precompiled. This header includes a large number of other headers. At least on paper this seems like a good usecase for using PCH.

When using clang, I get the expected speedup, which is around 2x faster. On gcc however, compilation takes significantly longer.

I store my PCHs in a separate directory, and have tried both adding the directory with -I, as well as specifying the PCH directly with -include (that didn't work: gcc ended up including both PCH and normal header). PCHs are compiled with the same options as source files.

Without PCH compilation takes around 13 seconds. With PCH it takes around 18 seconds. I validated with -H and -Winvalid-pch that gcc (only) includes the precompiled header. The complete output of -H for a single file looks like this:

! .bake_cache/x64-Linux-debug/include/corto.h.gch
 ./src/lang/boolean.c

The ! should indicate that gcc successfully loaded the pch:

-H Print the name of each header file used, in addition to other normal activities. Each name is indented to show how deep in the ‘#include’ stack it is. Precompiled header files are also printed, even if they are found to be invalid; an invalid precompiled header file is printed with ‘...x’ and a valid one with ‘...!’ .

From: https://gcc.gnu.org/onlinedocs/gcc/Preprocessor-Options.html

I'm at a loss. gcc seems to be able to locate and use the PCH, but still takes longer. Any idea what may be causing this?

Sander Mertens
  • 909
  • 8
  • 14
  • Are the output files substantially identical? Have you compared `-ftime-report` output? – Florian Weimer Feb 16 '19 at 21:15
  • I just tried `-ftime-report` and the output is bewildering. When it is enabled, compilation time for the entire project using PCHs is _faster_ vs not using PCH (19s vs 20s)! The reported times for individual files also seem uniformly faster for PCH vs. non-PCH. As soon as I remove `-ftime-report`, it goes back to the described behavior. – Sander Mertens Feb 16 '19 at 21:57
  • Still it would make sense to compare the overall time spent in the different phases between the PCH and non-PCH cases. The later phases should all show virtually identical timings. – Florian Weimer Feb 16 '19 at 22:05
  • You _may_ have to have the `.gch` in the _same_ directory as the `.h` for `gcc` to recognize it. You could run `gcc` under `strace` to see if `gcc` actually uses the `.gch` files. Also, do you use include guards (e.g. `#ifndef _myfile_h #define _myfile_h // stuff ... #endif`)? Also, `gcc` may use only _one_ `.gch`. See the `gcc` section of: https://en.wikipedia.org/wiki/Precompiled_header for some restrictions – Craig Estey Feb 16 '19 at 22:06
  • @CraigEstey thanks for your comment. I validated with the `-H` option that gcc is finding & using the precompiled header file (which has the extension `gch`). Storing the PCH in the same directory yields the same results. I only precompile one header file. – Sander Mertens Feb 16 '19 at 22:37

0 Answers0