]> git.ipfire.org Git - thirdparty/ccache.git/commitdiff
Allow treating "/dev/null" as an input file (#365)
authordianders <dianders@disordat.com>
Thu, 21 Mar 2019 19:46:34 +0000 (12:46 -0700)
committerJoel Rosdahl <joel@rosdahl.net>
Thu, 21 Mar 2019 19:46:34 +0000 (20:46 +0100)
One of the slow things for incremental Linux kernel builds is that
during the single-threaded parsing stage of the Makefile the kernel
calls into the C compiler to test which options the compiler supports.
A lot.  Specifically there are snippets like this all over the
Makefile:

$(call cc-option,-Oz,-Os)

...which translates into a call to the C compiler:

${CC} ... -Oz -c -x c /dev/null -o .178435.tmp

One of the contributing factors to the overall slowness is that the
input file for this test is "/dev/null".  This trips a check in ccache
because "/dev/null" "isn't a plain file".

As far as I understand it it should be totally fine to cache the
result of compiling "/dev/null".  It's basically just compiling an
empty file.

On my setup this improves the parsing stage of the kernel Makefile
from 3.25 seconds to 2.0 seconds (so saves 1.25 seconds for each of
build, install, and modules_install for 3.75 seconds total).

src/ccache.c

index ba98010ab86830049fbd69b867ee24635e1b46b9..48c655b5852d3cffeecb083d2350c9def843b8ab 100644 (file)
@@ -3044,8 +3044,12 @@ cc_process_args(struct args *args, struct args **preprocessor_args,
 
                // If an argument isn't a plain file then assume its an option, not an
                // input file. This allows us to cope better with unusual compiler options.
+               //
+               // NOTE that "/dev/null" is an exception that is sometimes used as an input
+               // file when code is testing compiler flags.
                struct stat st;
-               if (stat(argv[i], &st) != 0 || !S_ISREG(st.st_mode)) {
+               if (!str_eq(argv[i], "/dev/null") &&
++                  (stat(argv[i], &st) != 0 || !S_ISREG(st.st_mode))) {
                        cc_log("%s is not a regular file, not considering as input file",
                               argv[i]);
                        args_add(stripped_args, argv[i]);