[PATCH v3 1/3] arm64: unwind: add asynchronous unwind tables to kernel and modules
Ard Biesheuvel
ardb at kernel.org
Wed Jun 15 09:53:56 PDT 2022
On Wed, 15 Jun 2022 at 18:50, Sami Tolvanen <samitolvanen at google.com> wrote:
>
> On Mon, Jun 13, 2022 at 03:40:06PM +0200, Ard Biesheuvel wrote:
> > Enable asynchronous unwind table generation for both the core kernel as
> > well as modules, and emit the resulting .eh_frame sections as init code
> > so we can use the unwind directives for code patching at boot or module
> > load time.
> >
> > This will be used by dynamic shadow call stack support, which will rely
> > on code patching rather than compiler codegen to emit the shadow call
> > stack push and pop instructions.
> >
> > Signed-off-by: Ard Biesheuvel <ardb at kernel.org>
> > Reviewed-by: Nick Desaulniers <ndesaulniers at google.com>
> > ---
> > arch/arm64/Kconfig | 3 +++
> > arch/arm64/Makefile | 5 +++++
> > arch/arm64/include/asm/module.lds.h | 8 ++++++++
> > arch/arm64/kernel/vmlinux.lds.S | 13 +++++++++++++
> > arch/arm64/kvm/hyp/nvhe/Makefile | 1 +
> > drivers/firmware/efi/libstub/Makefile | 1 +
> > 6 files changed, 31 insertions(+)
> >
> > diff --git a/arch/arm64/Kconfig b/arch/arm64/Kconfig
> > index 1652a9800ebe..5f92344edff5 100644
> > --- a/arch/arm64/Kconfig
> > +++ b/arch/arm64/Kconfig
> > @@ -366,6 +366,9 @@ config KASAN_SHADOW_OFFSET
> > default 0xeffffff800000000 if ARM64_VA_BITS_36 && KASAN_SW_TAGS
> > default 0xffffffffffffffff
> >
> > +config UNWIND_TABLES
> > + bool
> > +
> > source "arch/arm64/Kconfig.platforms"
> >
> > menu "Kernel Features"
> > diff --git a/arch/arm64/Makefile b/arch/arm64/Makefile
> > index 6d9d4a58b898..4fbca56fa602 100644
> > --- a/arch/arm64/Makefile
> > +++ b/arch/arm64/Makefile
> > @@ -45,8 +45,13 @@ KBUILD_CFLAGS += $(call cc-option,-mabi=lp64)
> > KBUILD_AFLAGS += $(call cc-option,-mabi=lp64)
> >
> > # Avoid generating .eh_frame* sections.
> > +ifneq ($(CONFIG_UNWIND_TABLES),y)
> > KBUILD_CFLAGS += -fno-asynchronous-unwind-tables -fno-unwind-tables
> > KBUILD_AFLAGS += -fno-asynchronous-unwind-tables -fno-unwind-tables
> > +else
> > +KBUILD_CFLAGS += -fasynchronous-unwind-tables
> > +KBUILD_AFLAGS += -fasynchronous-unwind-tables
> > +endif
> >
> > ifeq ($(CONFIG_STACKPROTECTOR_PER_TASK),y)
> > prepare: stack_protector_prepare
> > diff --git a/arch/arm64/include/asm/module.lds.h b/arch/arm64/include/asm/module.lds.h
> > index 094701ec5500..dbba4b7559aa 100644
> > --- a/arch/arm64/include/asm/module.lds.h
> > +++ b/arch/arm64/include/asm/module.lds.h
> > @@ -17,4 +17,12 @@ SECTIONS {
> > */
> > .text.hot : { *(.text.hot) }
> > #endif
> > +
> > +#ifdef CONFIG_UNWIND_TABLES
> > + /*
> > + * Currently, we only use unwind info at module load time, so we can
> > + * put it into the .init allocation.
> > + */
> > + .init.eh_frame : { *(.eh_frame) }
> > +#endif
> > }
> > diff --git a/arch/arm64/kernel/vmlinux.lds.S b/arch/arm64/kernel/vmlinux.lds.S
> > index 2d4a8f995175..7bf4809f523d 100644
> > --- a/arch/arm64/kernel/vmlinux.lds.S
> > +++ b/arch/arm64/kernel/vmlinux.lds.S
> > @@ -120,6 +120,17 @@ jiffies = jiffies_64;
> > #define TRAMP_TEXT
> > #endif
> >
> > +#ifdef CONFIG_UNWIND_TABLES
> > +#define UNWIND_DATA_SECTIONS \
> > + .eh_frame : { \
> > + __eh_frame_start = .; \
> > + *(.eh_frame) \
> > + __eh_frame_end = .; \
> > + }
> > +#else
> > +#define UNWIND_DATA_SECTIONS
> > +#endif
>
> How does this work with SANITIZER_DISCARDS dropping .eh_frame in
> include/asm-generic/vmlinux.lds.h and scripts/module.lds.S? We would
> definitely want to enable this together with CONFIG_CFI_CLANG, so it
> seems like we'd have to drop the discard rules as well.
>
Good point, I had no idea that that existed.
Clang 13 should have the fix for the original issue, so we could make
this workaround specific to 12 and earlier.
More information about the linux-arm-kernel
mailing list