gccmakefilelinux-kernelkernel-modulekbuild

ccflag option in Makefile


I want to compile my c code (in kernel) which needs to include some header files from another directory.

Instead of specifying the complete path to header files in c file, I would like to specify the include path in Makefile.

My c file gets complied when the config option CONFIG_FEATURE_X is enabled. I have written the following in Makefile:

obj-$(CONFIG_FEATURE_X) += my_file.o

ccflags-$(CONFIG_FEATURE_X) += -I$(obj)/../../path
  1. When the CONFIG_FEATURE_X is enabled (Y) in .config using make menuconfig, it works fine.

  2. But when the CONFIG_FEATURE_X is enabled as module (m) in .config, this does not include the header files from the path specified and gives the file not found error.

How can I do this?


Solution

  • When the CONFIG_FEATURE_X is enabled (Y) in .config using make menuconfig, it works fine.

    That's because

    ccflags-$(CONFIG_FEATURE_X) += -I$(obj)/../../path  
    

    would evaluate to

    ccflags-y += -I$(obj)/../../path
    

    According to Documentation/kbuild/makefiles.txt:

    --- 3.7 Compilation flags
    
        ccflags-y, asflags-y and ldflags-y
            These three flags apply only to the kbuild makefile in which they
            are assigned. They are used for all the normal cc, as and ld
            invocations happening during a recursive build.
            Note: Flags with the same behaviour were previously named:
            EXTRA_CFLAGS, EXTRA_AFLAGS and EXTRA_LDFLAGS.
            They are still supported but their usage is deprecated.
    
            ccflags-y specifies options for compiling with $(CC).
    

    So you have defined a valid compilation flag for the built-in case.


    But when the CONFIG_FEATURE_X is enabled as module (m) in .config, this does not include the header files from the path specified and gives the file not found error.

    That's because

    ccflags-$(CONFIG_FEATURE_X) += -I$(obj)/../../path  
    

    would evaluate to

    ccflags-m += -I$(obj)/../../path
    

    According to the current version of Documentation/kbuild/makefiles.txt, there is no such compilation flag as "ccflags-m".
    So the path specification is never used for the loadable module.


    How can I do this?

    Instead of the ccflags-$() flag, you could try to use CFLAGS_$@, a per-file options for $(CC).

    CFLAGS_$@, AFLAGS_$@
    
        CFLAGS_$@ and AFLAGS_$@ only apply to commands in current
        kbuild makefile.
    
        $(CFLAGS_$@) specifies per-file options for $(CC).  The $@
        part has a literal value which specifies the file that it is for.
    
        Example:
            # drivers/scsi/Makefile
            CFLAGS_aha152x.o =   -DAHA152X_STAT -DAUTOCONF
            CFLAGS_gdth.o    = # -DDEBUG_GDTH=2 -D__SERIAL__ -D__COM2__ \
                     -DGDTH_STATISTICS
    
        These two lines specify compilation flags for aha152x.o and gdth.o.
    
        $(AFLAGS_$@) is a similar feature for source files in assembly
        languages.
    
        Example:
            # arch/arm/kernel/Makefile
            AFLAGS_head.o        := -DTEXT_OFFSET=$(TEXT_OFFSET)
            AFLAGS_crunch-bits.o := -Wa,-mcpu=ep9312
            AFLAGS_iwmmxt.o      := -Wa,-mcpu=iwmmxt
    

    So in your Makefile:

    CFLAGS_my_file.o =   -I$(obj)/../../path