Forum | Documentation | Website | Blog

Skip to content
Snippets Groups Projects
  1. Jun 21, 2024
  2. May 14, 2024
  3. Mar 31, 2024
    • Borislav Petkov (AMD)'s avatar
      kbuild: Disable KCSAN for autogenerated *.mod.c intermediaries · 54babdc0
      Borislav Petkov (AMD) authored
      
      When KCSAN and CONSTRUCTORS are enabled, one can trigger the
      
        "Unpatched return thunk in use. This should not happen!"
      
      catch-all warning.
      
      Usually, when objtool runs on the .o objects, it does generate a section
      .return_sites which contains all offsets in the objects to the return
      thunks of the functions present there. Those return thunks then get
      patched at runtime by the alternatives.
      
      KCSAN and CONSTRUCTORS add this to the object file's .text.startup
      section:
      
        -------------------
        Disassembly of section .text.startup:
      
        ...
      
        0000000000000010 <_sub_I_00099_0>:
          10:   f3 0f 1e fa             endbr64
          14:   e8 00 00 00 00          call   19 <_sub_I_00099_0+0x9>
                                15: R_X86_64_PLT32      __tsan_init-0x4
          19:   e9 00 00 00 00          jmp    1e <__UNIQUE_ID___addressable_cryptd_alloc_aead349+0x6>
                                1a: R_X86_64_PLT32      __x86_return_thunk-0x4
        -------------------
      
      which, if it is built as a module goes through the intermediary stage of
      creating a <module>.mod.c file which, when translated, receives a second
      constructor:
      
        -------------------
        Disassembly of section .text.startup:
      
        0000000000000010 <_sub_I_00099_0>:
          10:   f3 0f 1e fa             endbr64
          14:   e8 00 00 00 00          call   19 <_sub_I_00099_0+0x9>
                                15: R_X86_64_PLT32      __tsan_init-0x4
          19:   e9 00 00 00 00          jmp    1e <_sub_I_00099_0+0xe>
                                1a: R_X86_64_PLT32      __x86_return_thunk-0x4
      
        ...
      
        0000000000000030 <_sub_I_00099_0>:
          30:   f3 0f 1e fa             endbr64
          34:   e8 00 00 00 00          call   39 <_sub_I_00099_0+0x9>
                                35: R_X86_64_PLT32      __tsan_init-0x4
          39:   e9 00 00 00 00          jmp    3e <__ksymtab_cryptd_alloc_ahash+0x2>
                                3a: R_X86_64_PLT32      __x86_return_thunk-0x4
        -------------------
      
      in the .ko file.
      
      Objtool has run already so that second constructor's return thunk cannot
      be added to the .return_sites section and thus the return thunk remains
      unpatched and the warning rightfully fires.
      
      Drop KCSAN flags from the mod.c generation stage as those constructors
      do not contain data races one would be interested about.
      
      Debugged together with David Kaplan <David.Kaplan@amd.com> and Nikolay
      Borisov <nik.borisov@suse.com>.
      
      Reported-by: default avatarPaul Menzel <pmenzel@molgen.mpg.de>
      Closes: https://lore.kernel.org/r/0851a207-7143-417e-be31-8bf2b3afb57d@molgen.mpg.de
      
      
      Signed-off-by: default avatarBorislav Petkov (AMD) <bp@alien8.de>
      Tested-by: Paul Menzel <pmenzel@molgen.mpg.de> # Dell XPS 13
      Reviewed-by: default avatarNikolay Borisov <nik.borisov@suse.com>
      Reviewed-by: default avatarMarco Elver <elver@google.com>
      Signed-off-by: default avatarMasahiro Yamada <masahiroy@kernel.org>
      54babdc0
  4. Oct 28, 2023
  5. Aug 10, 2023
  6. Jun 25, 2023
  7. Jan 22, 2023
    • Masahiro Yamada's avatar
      kbuild: rename cmd_$@ to savedcmd_$@ in *.cmd files · 92215e7a
      Masahiro Yamada authored
      
      The cmd-check macro compares $(cmd_$@) and $(cmd_$1), but a pitfall is
      that you cannot use cmd_<target> as the variable name for the command.
      
      For example, the following code will not work in the top Makefile
      or ./Kbuild.
      
          quiet_cmd_foo = GEN     $@
                cmd_foo = touch $@
      
          targets += foo
          foo: FORCE
                  $(call if_changed,foo)
      
      In this case, both $@ and $1 are expanded to 'foo', so $(cmd_check)
      is always empty.
      
      We do not need to use the same prefix for cmd_$@ and cmd_$1.
      Rename the former to savedcmd_$@.
      
      Signed-off-by: default avatarMasahiro Yamada <masahiroy@kernel.org>
      Reviewed-by: default avatarNicolas Schier <nicolas@fjasle.eu>
      92215e7a
  8. Dec 14, 2022
  9. Dec 13, 2022
  10. Sep 28, 2022
  11. May 29, 2022
    • Masahiro Yamada's avatar
      kbuild: do not create *.prelink.o for Clang LTO or IBT · c25e1c55
      Masahiro Yamada authored
      
      When CONFIG_LTO_CLANG=y, additional intermediate *.prelink.o is created
      for each module. Also, objtool is postponed until LLVM IR is converted
      to ELF.
      
      CONFIG_X86_KERNEL_IBT works in a similar way to postpone objtool until
      objects are merged together.
      
      This commit stops generating *.prelink.o, so the build flow will look
      similar with/without LTO.
      
      The following figures show how the LTO build currently works, and
      how this commit is changing it.
      
      Current build flow
      ==================
      
       [1] single-object module
      
                                            $(LD)
                 $(CC)                     +objtool              $(LD)
          foo.c --------------------> foo.o -----> foo.prelink.o -----> foo.ko
                                    (LLVM IR)          (ELF)       |    (ELF)
                                                                   |
                                                       foo.mod.o --/
                                                       (LLVM IR)
      
       [2] multi-object module
                                            $(LD)
                 $(CC)         $(AR)       +objtool               $(LD)
          foo1.c -----> foo1.o -----> foo.o -----> foo.prelink.o -----> foo.ko
                                 |  (archive)          (ELF)       |    (ELF)
          foo2.c -----> foo2.o --/                                 |
                       (LLVM IR)                       foo.mod.o --/
                                                       (LLVM IR)
      
        One confusion is that foo.o in multi-object module is an archive
        despite of its suffix.
      
      New build flow
      ==============
      
       [1] single-object module
      
        Since there is only one object, there is no need to keep the LLVM IR.
        Use $(CC)+$(LD) to generate an ELF object in one build rule. When LTO
        is disabled, $(LD) is unneeded because $(CC) produces an ELF object.
      
                     $(CC)+$(LD)+objtool              $(LD)
          foo.c ----------------------------> foo.o ---------> foo.ko
                                              (ELF)     |      (ELF)
                                                        |
                                            foo.mod.o --/
                                            (LLVM IR)
      
       [2] multi-object module
      
        Previously, $(AR) was used to combine LLVM IR files into an archive,
        but there was no technical reason to do so. Use $(LD) to merge them
        into a single ELF object.
      
                                     $(LD)
                   $(CC)            +objtool          $(LD)
          foo1.c ---------> foo1.o ---------> foo.o ---------> foo.ko
                                       |      (ELF)     |      (ELF)
          foo2.c ---------> foo2.o ----/                |
                           (LLVM IR)        foo.mod.o --/
                                            (LLVM IR)
      
      Signed-off-by: default avatarMasahiro Yamada <masahiroy@kernel.org>
      Reviewed-by: default avatarNicolas Schier <nicolas@fjasle.eu>
      Tested-by: default avatarNathan Chancellor <nathan@kernel.org>
      Reviewed-by: default avatarSami Tolvanen <samitolvanen@google.com>
      Tested-by: Sedat Dilek <sedat.dilek@gmail.com> # LLVM-14 (x86-64)
      Acked-by: default avatarJosh Poimboeuf <jpoimboe@kernel.org>
      c25e1c55
  12. Nov 01, 2021
  13. Oct 05, 2021
  14. Sep 02, 2021
  15. May 27, 2021
    • Javier Martinez Canillas's avatar
      kbuild: Quote OBJCOPY var to avoid a pahole call break the build · ff2e6efd
      Javier Martinez Canillas authored
      The ccache tool can be used to speed up cross-compilation, by calling the
      compiler and binutils through ccache. For example, following should work:
      
          $ export ARCH=arm64 CROSS_COMPILE="ccache aarch64-linux-gnu-"
      
          $ make M=drivers/gpu/drm/rockchip/
      
      but pahole fails to extract the BTF info from DWARF, breaking the build:
      
            CC [M]  drivers/gpu/drm/rockchip//rockchipdrm.mod.o
            LD [M]  drivers/gpu/drm/rockchip//rockchipdrm.ko
            BTF [M] drivers/gpu/drm/rockchip//rockchipdrm.ko
          aarch64-linux-gnu-objcopy: invalid option -- 'J'
          Usage: aarch64-linux-gnu-objcopy [option(s)] in-file [out-file]
           Copies a binary file, possibly transforming it in the process
          ...
          make[1]: *** [scripts/Makefile.modpost:156: __modpost] Error 2
          make: *** [Makefile:1866: modules] Error 2
      
      this fails because OBJCOPY is set to "ccache aarch64-linux-gnu-copy" and
      later pahole is executed with the following command line:
      
          LLVM_OBJCOPY=$(OBJCOPY) $(PAHOLE) -J --btf_base vmlinux $@
      
      which gets expanded to:
      
          LLVM_OBJCOPY=ccache aarch64-linux-gnu-objcopy pahole -J ...
      
      instead of:
      
          LLVM_OBJCOPY="ccache aarch64-linux-gnu-objcopy" pahole -J ...
      
      Fixes: 5f9ae91f
      
       ("kbuild: Build kernel module BTFs if BTF is enabled and pahole supports it")
      Signed-off-by: default avatarJavier Martinez Canillas <javierm@redhat.com>
      Signed-off-by: default avatarAndrii Nakryiko <andrii@kernel.org>
      Acked-by: default avatarAndrii Nakryiko <andrii@kernel.org>
      Acked-by: default avatarArnaldo Carvalho de Melo <acme@redhat.com>
      Link: https://lore.kernel.org/bpf/20210526215228.3729875-1-javierm@redhat.com
      ff2e6efd
  16. May 23, 2021
    • Masahiro Yamada's avatar
      kbuild: remove libelf checks from top Makefile · 0d989ac2
      Masahiro Yamada authored
      I do not see a good reason why only the libelf development package must
      be so carefully checked.
      
      Kbuild generally does not check host tools or libraries.
      
      For example, x86_64 defconfig fails to build with no libssl development
      package installed.
      
      scripts/extract-cert.c:21:10: fatal error: openssl/bio.h: No such file or directory
         21 | #include <openssl/bio.h>
            |          ^~~~~~~~~~~~~~~
      
      To solve the build error, you need to install libssl-dev or openssl-devel
      package, depending on your distribution.
      
      'apt-file search', 'dnf provides', etc. is your frined to find a proper
      package to install.
      
      This commit removes all the libelf checks from the top Makefile.
      
      If libelf is missing, objtool will fail to build in a similar pattern:
      
      .../linux/tools/objtool/include/objtool/elf.h:10:10: fatal error: gelf.h: No such file or directory
         10 | #include <gelf.h>
      
      You need to install libelf-dev, libelf-devel, or elfutils-libelf-devel
      to proceed.
      
      Another remarkable change is, CONFIG_STACK_VALIDATION (without
      CONFIG_UNWINDER_ORC) previously continued to build with a warning,
      but now it will treat missing libelf as an error.
      
      This is just a one-time installation, so it should not hurt to break
      a build and make a user install the package.
      
      BTW, the traditional way to handle such checks is autotool, but according
      to [1], I do not expect the kernel build would have similar scripting
      like './configure' does.
      
      [1]: https://lore.kernel.org/lkml/CA+55aFzr2HTZVOuzpHYDwmtRJLsVzE-yqg2DHpHi_9ePsYp5ug@mail.gmail.com/
      
      
      
      Signed-off-by: default avatarMasahiro Yamada <masahiroy@kernel.org>
      Acked-by: default avatarAndrii Nakryiko <andrii@kernel.org>
      0d989ac2
  17. Apr 08, 2021
    • Sami Tolvanen's avatar
      add support for Clang CFI · cf68fffb
      Sami Tolvanen authored
      This change adds support for Clang’s forward-edge Control Flow
      Integrity (CFI) checking. With CONFIG_CFI_CLANG, the compiler
      injects a runtime check before each indirect function call to ensure
      the target is a valid function with the correct static type. This
      restricts possible call targets and makes it more difficult for
      an attacker to exploit bugs that allow the modification of stored
      function pointers. For more details, see:
      
        https://clang.llvm.org/docs/ControlFlowIntegrity.html
      
      
      
      Clang requires CONFIG_LTO_CLANG to be enabled with CFI to gain
      visibility to possible call targets. Kernel modules are supported
      with Clang’s cross-DSO CFI mode, which allows checking between
      independently compiled components.
      
      With CFI enabled, the compiler injects a __cfi_check() function into
      the kernel and each module for validating local call targets. For
      cross-module calls that cannot be validated locally, the compiler
      calls the global __cfi_slowpath_diag() function, which determines
      the target module and calls the correct __cfi_check() function. This
      patch includes a slowpath implementation that uses __module_address()
      to resolve call targets, and with CONFIG_CFI_CLANG_SHADOW enabled, a
      shadow map that speeds up module look-ups by ~3x.
      
      Clang implements indirect call checking using jump tables and
      offers two methods of generating them. With canonical jump tables,
      the compiler renames each address-taken function to <function>.cfi
      and points the original symbol to a jump table entry, which passes
      __cfi_check() validation. This isn’t compatible with stand-alone
      assembly code, which the compiler doesn’t instrument, and would
      result in indirect calls to assembly code to fail. Therefore, we
      default to using non-canonical jump tables instead, where the compiler
      generates a local jump table entry <function>.cfi_jt for each
      address-taken function, and replaces all references to the function
      with the address of the jump table entry.
      
      Note that because non-canonical jump table addresses are local
      to each component, they break cross-module function address
      equality. Specifically, the address of a global function will be
      different in each module, as it's replaced with the address of a local
      jump table entry. If this address is passed to a different module,
      it won’t match the address of the same function taken there. This
      may break code that relies on comparing addresses passed from other
      components.
      
      CFI checking can be disabled in a function with the __nocfi attribute.
      Additionally, CFI can be disabled for an entire compilation unit by
      filtering out CC_FLAGS_CFI.
      
      By default, CFI failures result in a kernel panic to stop a potential
      exploit. CONFIG_CFI_PERMISSIVE enables a permissive mode, where the
      kernel prints out a rate-limited warning instead, and allows execution
      to continue. This option is helpful for locating type mismatches, but
      should only be enabled during development.
      
      Signed-off-by: default avatarSami Tolvanen <samitolvanen@google.com>
      Reviewed-by: default avatarKees Cook <keescook@chromium.org>
      Tested-by: default avatarNathan Chancellor <nathan@kernel.org>
      Signed-off-by: default avatarKees Cook <keescook@chromium.org>
      Link: https://lore.kernel.org/r/20210408182843.1754385-2-samitolvanen@google.com
      cf68fffb
  18. Feb 23, 2021
    • Sami Tolvanen's avatar
      kbuild: lto: postpone objtool · b1a1a1a0
      Sami Tolvanen authored
      
      With LTO, LLVM bitcode won't be compiled into native code until
      modpost_link, or modfinal for modules. This change postpones calls
      to objtool until after these steps, and moves objtool_args to
      Makefile.lib, so the arguments can be reused in Makefile.modfinal.
      
      As we didn't have objects to process earlier, we use --duplicate
      when processing vmlinux.o. This change also disables unreachable
      instruction warnings with LTO to avoid warnings about the int3
      padding between functions.
      
      Signed-off-by: default avatarSami Tolvanen <samitolvanen@google.com>
      Reviewed-by: default avatarKees Cook <keescook@chromium.org>
      b1a1a1a0
  19. Jan 14, 2021
    • Sami Tolvanen's avatar
      kbuild: add support for Clang LTO · dc5723b0
      Sami Tolvanen authored
      This change adds build system support for Clang's Link Time
      Optimization (LTO). With -flto, instead of ELF object files, Clang
      produces LLVM bitcode, which is compiled into native code at link
      time, allowing the final binary to be optimized globally. For more
      details, see:
      
        https://llvm.org/docs/LinkTimeOptimization.html
      
      The Kconfig option CONFIG_LTO_CLANG is implemented as a choice,
      which defaults to LTO being disabled. To use LTO, the architecture
      must select ARCH_SUPPORTS_LTO_CLANG and support:
      
        - compiling with Clang,
        - compiling all assembly code with Clang's integrated assembler,
        - and linking with LLD.
      
      While using CONFIG_LTO_CLANG_FULL results in the best runtime
      performance, the compilation is not scalable in time or
      memory. CONFIG_LTO_CLANG_THIN enables ThinLTO, which allows
      parallel optimization and faster incremental builds. ThinLTO is
      used by default if the architecture also selects
      ARCH_SUPPORTS_LTO_CLANG_THIN:
      
        https://clang.llvm.org/docs/ThinLTO...
      dc5723b0
  20. Nov 24, 2020
    • Andrii Nakryiko's avatar
      kbuild: Skip module BTF generation for out-of-tree external modules · e732b538
      Andrii Nakryiko authored
      In some modes of operation, Kbuild allows to build modules without having
      vmlinux image around. In such case, generation of module BTF is impossible.
      This patch changes the behavior to emit a warning about impossibility of
      generating kernel module BTF, instead of breaking the build. This is especially
      important for out-of-tree external module builds.
      
      In vmlinux-less mode:
      
      $ make clean
      $ make modules_prepare
      $ touch drivers/acpi/button.c
      $ make M=drivers/acpi
      ...
        CC [M]  drivers/acpi/button.o
        MODPOST drivers/acpi/Module.symvers
        LD [M]  drivers/acpi/button.ko
        BTF [M] drivers/acpi/button.ko
      Skipping BTF generation for drivers/acpi/button.ko due to unavailability of vmlinux
      ...
      $ readelf -S ~/linux-build/default/drivers/acpi/button.ko | grep BTF -A1
      ... empty ...
      
      Now with normal build:
      
      $ make all
      ...
      LD [M]  drivers/acpi/button.ko
      BTF [M] drivers/acpi/button.ko
      ...
      $ readelf -S ~/linux-build/default/drivers/acpi/button.ko | grep BTF -A1
        [60] .BTF              PROGBITS         0000000000000000  00029310
             000000000000ab3f  0000000000000000           0     0     1
      
      Fixes: 5f9ae91f
      
       ("kbuild: Build kernel module BTFs if BTF is enabled and pahole supports it")
      Reported-by: default avatarBruce Allan <bruce.w.allan@intel.com>
      Signed-off-by: default avatarAndrii Nakryiko <andrii@kernel.org>
      Signed-off-by: default avatarDaniel Borkmann <daniel@iogearbox.net>
      Cc: Jessica Yu <jeyu@kernel.org>
      Cc: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
      Cc: Masahiro Yamada <yamada.masahiro@socionext.com>
      Link: https://lore.kernel.org/bpf/20201121070829.2612884-1-andrii@kernel.org
      e732b538
  21. Nov 10, 2020
    • Andrii Nakryiko's avatar
      kbuild: Build kernel module BTFs if BTF is enabled and pahole supports it · 5f9ae91f
      Andrii Nakryiko authored
      
      Detect if pahole supports split BTF generation, and generate BTF for each
      selected kernel module, if it does. This is exposed to Makefiles and C code as
      CONFIG_DEBUG_INFO_BTF_MODULES flag.
      
      Kernel module BTF has to be re-generated if either vmlinux's BTF changes or
      module's .ko changes. To achieve that, I needed a helper similar to
      if_changed, but that would allow to filter out vmlinux from the list of
      updated dependencies for .ko building. I've put it next to the only place that
      uses and needs it, but it might be a better idea to just add it along the
      other if_changed variants into scripts/Kbuild.include.
      
      Each kernel module's BTF deduplication is pretty fast, as it does only
      incremental BTF deduplication on top of already deduplicated vmlinux BTF. To
      show the added build time, I've first ran make only just built kernel (to
      establish the baseline) and then forced only BTF re-generation, without
      regenerating .ko files. The build was performed with -j60 parallelization on
      56-core machine. The final time also includes bzImage building, so it's not
      a pure BTF overhead.
      
      $ time make -j60
      ...
      make -j60  27.65s user 10.96s system 782% cpu 4.933 total
      $ touch ~/linux-build/default/vmlinux && time make -j60
      ...
      make -j60  123.69s user 27.85s system 1566% cpu 9.675 total
      
      So 4.6 seconds real time, with noticeable part spent in compressed vmlinux and
      bzImage building.
      
      To show size savings, I've built my kernel configuration with about 700 kernel
      modules with full BTF per each kernel module (without deduplicating against
      vmlinux) and with split BTF against deduplicated vmlinux (approach in this
      patch). Below are top 10 modules with biggest BTF sizes. And total size of BTF
      data across all kernel modules.
      
      It shows that split BTF "compresses" 115MB down to 5MB total. And the biggest
      kernel modules get a downsize from 500-570KB down to 200-300KB.
      
      FULL BTF
      ========
      
      $ for f in $(find . -name '*.ko'); do size -A -d $f | grep BTF | awk '{print $2}'; done | awk '{ s += $1 } END { print s }'
      115710691
      
      $ for f in $(find . -name '*.ko'); do printf "%s %d\n" $f $(size -A -d $f | grep BTF | awk '{print $2}'); done | sort -nr -k2 | head -n10
      ./drivers/gpu/drm/i915/i915.ko 570570
      ./drivers/net/ethernet/mellanox/mlx5/core/mlx5_core.ko 520240
      ./drivers/gpu/drm/radeon/radeon.ko 503849
      ./drivers/infiniband/hw/mlx5/mlx5_ib.ko 491777
      ./fs/xfs/xfs.ko 411544
      ./drivers/net/ethernet/intel/i40e/i40e.ko 403904
      ./drivers/net/ethernet/broadcom/bnx2x/bnx2x.ko 398754
      ./drivers/infiniband/core/ib_core.ko 397224
      ./fs/cifs/cifs.ko 386249
      ./fs/nfsd/nfsd.ko 379738
      
      SPLIT BTF
      =========
      
      $ for f in $(find . -name '*.ko'); do size -A -d $f | grep BTF | awk '{print $2}'; done | awk '{ s += $1 } END { print s }'
      5194047
      
      $ for f in $(find . -name '*.ko'); do printf "%s %d\n" $f $(size -A -d $f | grep BTF | awk '{print $2}'); done | sort -nr -k2 | head -n10
      ./drivers/gpu/drm/i915/i915.ko 293206
      ./drivers/gpu/drm/radeon/radeon.ko 282103
      ./fs/xfs/xfs.ko 222150
      ./drivers/net/ethernet/mellanox/mlx5/core/mlx5_core.ko 198503
      ./drivers/infiniband/hw/mlx5/mlx5_ib.ko 198356
      ./drivers/net/ethernet/broadcom/bnx2x/bnx2x.ko 113444
      ./fs/cifs/cifs.ko 109379
      ./arch/x86/kvm/kvm.ko 100225
      ./drivers/gpu/drm/drm.ko 94827
      ./drivers/infiniband/core/ib_core.ko 91188
      
      Signed-off-by: default avatarAndrii Nakryiko <andrii@kernel.org>
      Signed-off-by: default avatarAlexei Starovoitov <ast@kernel.org>
      Link: https://lore.kernel.org/bpf/20201110011932.3201430-4-andrii@kernel.org
      5f9ae91f
  22. Sep 24, 2020
  23. Aug 21, 2019