• Josh Poimboeuf's avatar
    s390: compile relocatable kernel without -fPIE · 778666df
    Josh Poimboeuf authored
    On s390, currently kernel uses the '-fPIE' compiler flag for compiling
    vmlinux.  This has a few problems:
    
      - It uses dynamic symbols (.dynsym), for which the linker refuses to
        allow more than 64k sections.  This can break features which use
        '-ffunction-sections' and '-fdata-sections', including kpatch-build
        [1] and Function Granular KASLR.
    
      - It unnecessarily uses GOT relocations, adding an extra layer of
        indirection for many memory accesses.
    
    Instead of using '-fPIE', resolve all the relocations at link time and
    then manually adjust any absolute relocations (R_390_64) during boot.
    
    This is done by first telling the linker to preserve all relocations
    during the vmlinux link.  (Note this is harmless: they are later
    stripped in the vmlinux.bin link.)
    
    Then use the 'relocs' tool to find all absolute relocations (R_390_64)
    which apply to allocatable sections.  The offsets of those relocations
    are saved in a special section which is then used to adjust the
    relocations during boot.
    
    (Note: For some reason, Clang occasionally creates a GOT reference, even
    without '-fPIE'.  So Clang-compiled kernels have a GOT, which needs to
    be adjusted.)
    
    On my mostly-defconfig kernel, this reduces kernel text size by ~1.3%.
    
    [1] https://github.com/dynup/kpatch/issues/1284
    [2] https://gcc.gnu.org/pipermail/gcc-patches/2023-June/622872.html
    [3] https://gcc.gnu.org/pipermail/gcc-patches/2023-August/625986.html
    
    Compiler consideration:
    
    Gcc recently implemented an optimization [2] for loading symbols without
    explicit alignment, aligning with the IBM Z ELF ABI. This ABI mandates
    symbols to reside on a 2-byte boundary, enabling the use of the larl
    instruction. However, kernel linker scripts may still generate unaligned
    symbols. To address this, a new -munaligned-symbols option has been
    introduced [3] in recent gcc versions. This option has to be used with
    future gcc versions.
    
    Older Clang lacks support for handling unaligned symbols generated
    by kernel linker scripts when the kernel is built without -fPIE. However,
    future versions of Clang will include support for the -munaligned-symbols
    option. When the support is unavailable, compile the kernel with -fPIE
    to maintain the existing behavior.
    
    In addition to it:
    move vmlinux.relocs to safe relocation
    
    When the kernel is built with CONFIG_KERNEL_UNCOMPRESSED, the entire
    uncompressed vmlinux.bin is positioned in the bzImage decompressor
    image at the default kernel LMA of 0x100000, enabling it to be executed
    in-place. However, the size of .vmlinux.relocs could be large enough to
    cause an overlap with the uncompressed kernel at the address 0x100000.
    To address this issue, .vmlinux.relocs is positioned after the
    .rodata.compressed in the bzImage. Nevertheless, in this configuration,
    vmlinux.relocs will overlap with the .bss section of vmlinux.bin. To
    overcome that, move vmlinux.relocs to a safe location before clearing
    .bss and handling relocs.
    
    Compile warning fix from Sumanth Korikkar:
    
    When kernel is built with CONFIG_LD_ORPHAN_WARN and -fno-PIE, there are
    several warnings:
    
    ld: warning: orphan section `.rela.iplt' from
    `arch/s390/kernel/head64.o' being placed in section `.rela.dyn'
    ld: warning: orphan section `.rela.head.text' from
    `arch/s390/kernel/head64.o' being placed in section `.rela.dyn'
    ld: warning: orphan section `.rela.init.text' from
    `arch/s390/kernel/head64.o' being placed in section `.rela.dyn'
    ld: warning: orphan section `.rela.rodata.cst8' from
    `arch/s390/kernel/head64.o' being placed in section `.rela.dyn'
    
    Orphan sections are sections that exist in an object file but don't have
    a corresponding output section in the final executable. ld raises a
    warning when it identifies such sections.
    
    Eliminate the warning by placing all .rela orphan sections in .rela.dyn
    and raise an error when size of .rela.dyn is greater than zero. i.e.
    Dont just neglect orphan sections.
    
    This is similar to adjustment performed in x86, where kernel is built
    with -fno-PIE.
    commit 5354e845 ("x86/build: Add asserts for unwanted sections")
    
    [sumanthk@linux.ibm.com: rebased Josh Poimboeuf patches and move
     vmlinux.relocs to safe location]
    [hca@linux.ibm.com: merged compile warning fix from Sumanth]
    Tested-by: default avatarSumanth Korikkar <sumanthk@linux.ibm.com>
    Acked-by: default avatarVasily Gorbik <gor@linux.ibm.com>
    Signed-off-by: default avatarJosh Poimboeuf <jpoimboe@kernel.org>
    Signed-off-by: default avatarSumanth Korikkar <sumanthk@linux.ibm.com>
    Link: https://lore.kernel.org/r/20240219132734.22881-4-sumanthk@linux.ibm.com
    Link: https://lore.kernel.org/r/20240219132734.22881-5-sumanthk@linux.ibm.comSigned-off-by: default avatarHeiko Carstens <hca@linux.ibm.com>
    778666df
physmem_info.h 4.72 KB