How to enable march=native and -flto on gentoo-kernel

2026-04-11

Linux kernel’s compiler optimization techniques has been more or less the same, so my earlier blog[1] is still relevant.

However, since the debut of distribution kernel, the kernel can be now built and upgraded along with a normal portage sysupgrade.

The gentoo wiki has also been expanded, covering more possibilities for optimization like pgo, march, O3 and lto.

This blog records how I enable the march and clang lto optimizations for my gentoo-kernel package.

Preparations

Install and set up distribution kernel and make sure it works, according to gentoo’s wiki page.

Setup

As mentioned in gentoo wiki, it’s possible to enable march=native from make nconfig, however, it’s not enabled by gentoo packages as of right now, and my method will work with all kernel versions.

make.conf:

# Global settings
# These warnings indicate likely runtime problems with LTO, so promote them
# to errors. If a package fails to build with these, LTO should not be used there.
WARNING_FLAGS="-Werror=odr -Werror=lto-type-mismatch -Werror=strict-aliasing"

NOLTO_FLAGS="-O2 -pipe -march=raptorlake"
COMMON_FLAGS="${NOLTO_FLAGS} -flto ${WARNING_FLAGS}"

RUSTFLAGS="-C target-cpu=raptorlake"
GOAMD64=v3
CFLAGS="${COMMON_FLAGS}"
CXXFLAGS="${COMMON_FLAGS}"
FCFLAGS="${COMMON_FLAGS}"
FFLAGS="${COMMON_FLAGS}"
LDFLAGS="${COMMON_FLAGS} -fuse-ld=mold" # Use mold to speed up

This declares a NOLTO_FLAGS so that packages that can’t be built with lto can be disabled. This is taken from gentoo wiki. For all other packages including gentoo-kernel, lto will be used.

Note that -flto arg is used not -flto=full or -flto=16. This way it will be compatible with both gcc and clang.

Now we define a kernel-specific package.env to set the environmental variables of portage when building that package.

package.env/kernel:

sys-kernel/gentoo-kernel	kernel.conf

env/kernel.conf:

CC=clang
LD=ld.lld
AR=llvm-ar
NM=llvm-nm
STRIP=llvm-strip
OBJCOPY=llvm-objcopy
OBJDUMP=llvm-objdump
READELF=llvm-readelf
HOSTCC=clang
HOSTCXX=clang++
HOSTAR=llvm-ar
HOSTLD=ld.lld

This is taken from linux kernel’s official documentation, this is what it means to set LLVM=1.

  1. Optimize Linux even more by using clang + full LTO to compile the kernel


< Neovim Treesitter without the nvim-treesitter pluginA Reminder on How to Enable Bluetooth before Cryptsetup >