Search code examples
cgccprecompiled-headers

Precompiled headers aren't being used, GCC


I'm following exactly how it says in the official docs here, and I cannot find any results on Google whatsoever about precompiled headers not working. I'm compiling with gcc main.c -lSDL2 -lSDL2_image, and I've compiled the headers with gcc <headername>. I've used -H to check if the PCHs are being used and they aren't, I am also using about 45 headers, and there's a clear difference in compile times when not using headers.

Example:

// main.c
#include <stdio.h>

#include "header.h"

int main() {

    printf("%s\n", string);

    return 0;
}
// header.h
char* string = "Hello World!";

Compiled with gcc -H main.c it gives the same output after compiling the header with gcc header.h Output:

. /usr/include/stdio.h
.. /usr/include/bits/libc-header-start.h
... /usr/include/features.h
.... /usr/include/features-time64.h
..... /usr/include/bits/wordsize.h
..... /usr/include/bits/timesize.h
...... /usr/include/bits/wordsize.h
.... /usr/include/sys/cdefs.h
..... /usr/include/bits/wordsize.h
..... /usr/include/bits/long-double.h
.... /usr/include/gnu/stubs.h
..... /usr/include/gnu/stubs-64.h
.. /usr/lib/gcc/x86_64-pc-linux-gnu/13.2.1/include/stddef.h
.. /usr/lib/gcc/x86_64-pc-linux-gnu/13.2.1/include/stdarg.h
.. /usr/include/bits/types.h
... /usr/include/bits/wordsize.h
... /usr/include/bits/timesize.h
.... /usr/include/bits/wordsize.h
... /usr/include/bits/typesizes.h
... /usr/include/bits/time64.h
.. /usr/include/bits/types/__fpos_t.h
... /usr/include/bits/types/__mbstate_t.h
.. /usr/include/bits/types/__fpos64_t.h
.. /usr/include/bits/types/__FILE.h
.. /usr/include/bits/types/FILE.h
.. /usr/include/bits/types/struct_FILE.h
.. /usr/include/bits/types/cookie_io_functions_t.h
.. /usr/include/bits/stdio_lim.h
.. /usr/include/bits/floatn.h
... /usr/include/bits/floatn-common.h
.... /usr/include/bits/long-double.h
. header.h
Multiple include guards may be useful for:
/usr/include/bits/libc-header-start.h
/usr/include/bits/time64.h
/usr/include/bits/typesizes.h
/usr/include/features-time64.h
/usr/include/gnu/stubs-64.h
/usr/include/gnu/stubs.h
/usr/lib/gcc/x86_64-pc-linux-gnu/13.2.1/include/stddef.h
header.h

Solution

  • As the docs says

    A precompiled header cannot be used once the first C token is seen."

    However by including <stdio.h> before your "header.h", <stdio.h> contains lots of C tokens, and thus the precompiled header isn't used.

    Try include "header.h" before <stdio.h. Or even better, make "header.h" include <stdio.h> so you get the advantage of precompiling stdio.h.

    Note also your "header.h" contains definitions, not just declarations, which may lead you to issues in bigger projects.