Message ID | 20250503161938.646908-1-alvinga@andestech.com |
---|---|
State | New |
Headers | show |
Series | lib: utils: Initial compiler built-in stack protector support | expand |
Hi Alvin, I encountered an issue when building with DEBUG=1 and CONFIG_STACK_PROTECTOR_ALL=y. An exception occurs at the __check_csr_64 macro which calls sbi_hart_expected_trap_addr(). Not sure the root cause but here's a workaround that disables stack protection specifically for this function: + #pragma GCC push_options + #pragma GCC optimize ("no-stack-protector") static inline ulong sbi_hart_expected_trap_addr(void) { return (ulong)sbi_hart_expected_trap; } + #pragma GCC pop_options Regards, Peter Lin On 5/4/25 12:19 AM, Alvin Chang wrote: > Add stack_protector.c which defines the stack guard variable and the > function which will be referenced by compiler built-in stack protector. > > This patch just try to support stack-protector so the value of the stack > guard variable is simply fixed for now. It could be improved by > deriving from a random number generator, such as Zkr extension or any > platform-specific random number sources. > > Introduce three configurations for the stack protector: > 1. CONFIG_STACK_PROTECTOR to enable the stack protector feature by > providing "-fstack-protector" compiler flag > 2. CONFIG_STACK_PROTECTOR_STRONG to provide "-fstack-protector-strong" > 3. CONFIG_STACK_PROTECTOR_ALL to provide "-fstack-protector-all" > > Instead of fixing the compiler flag of stack-protector feature as > "-fstack-protector", we derive it from the introduced Kconfig > configurations. The compiler flag "stack-protector-cflags-y" is defined > as Makefile "immediately expanded variables" with ":=". Thus, the > stronger configuration of the stack protector can overwrite the > preceding one. > > Signed-off-by: Alvin Chang <alvinga@andestech.com> > --- > Makefile | 3 ++- > lib/utils/Kconfig | 2 ++ > lib/utils/stack_protector/Kconfig | 28 +++++++++++++++++++++ > lib/utils/stack_protector/objects.mk | 18 +++++++++++++ > lib/utils/stack_protector/stack_protector.c | 18 +++++++++++++ > 5 files changed, 68 insertions(+), 1 deletion(-) > create mode 100644 lib/utils/stack_protector/Kconfig > create mode 100644 lib/utils/stack_protector/objects.mk > create mode 100644 lib/utils/stack_protector/stack_protector.c > > diff --git a/Makefile b/Makefile > index e90836c..eae6d16 100644 > --- a/Makefile > +++ b/Makefile > @@ -360,7 +360,7 @@ GENFLAGS += $(libsbiutils-genflags-y) > GENFLAGS += $(platform-genflags-y) > GENFLAGS += $(firmware-genflags-y) > > -CFLAGS = -g -Wall -Werror -ffreestanding -nostdlib -fno-stack-protector -fno-strict-aliasing -ffunction-sections -fdata-sections > +CFLAGS = -g -Wall -Werror -ffreestanding -nostdlib -fno-strict-aliasing -ffunction-sections -fdata-sections > CFLAGS += -fno-omit-frame-pointer -fno-optimize-sibling-calls > # Optionally supported flags > ifeq ($(CC_SUPPORT_VECTOR),y) > @@ -379,6 +379,7 @@ CFLAGS += $(GENFLAGS) > CFLAGS += $(platform-cflags-y) > CFLAGS += -fPIE -pie > CFLAGS += $(firmware-cflags-y) > +CFLAGS += $(stack-protector-cflags-y) > > CPPFLAGS += $(GENFLAGS) > CPPFLAGS += $(platform-cppflags-y) > diff --git a/lib/utils/Kconfig b/lib/utils/Kconfig > index 901ba56..40e5633 100644 > --- a/lib/utils/Kconfig > +++ b/lib/utils/Kconfig > @@ -26,6 +26,8 @@ source "$(OPENSBI_SRC_DIR)/lib/utils/reset/Kconfig" > > source "$(OPENSBI_SRC_DIR)/lib/utils/serial/Kconfig" > > +source "$(OPENSBI_SRC_DIR)/lib/utils/stack_protector/Kconfig" > + > source "$(OPENSBI_SRC_DIR)/lib/utils/suspend/Kconfig" > > source "$(OPENSBI_SRC_DIR)/lib/utils/sys/Kconfig" > diff --git a/lib/utils/stack_protector/Kconfig b/lib/utils/stack_protector/Kconfig > new file mode 100644 > index 0000000..c1fee19 > --- /dev/null > +++ b/lib/utils/stack_protector/Kconfig > @@ -0,0 +1,28 @@ > +# SPDX-License-Identifier: BSD-2-Clause > + > +menu "Stack Protector Support" > + > +config STACK_PROTECTOR > + bool "Stack Protector buffer overflow detection" > + default n > + help > + This option turns on the "stack-protector" compiler feature. > + > +config STACK_PROTECTOR_STRONG > + bool "Strong Stack Protector" > + depends on STACK_PROTECTOR > + default n > + help > + Turn on the "stack-protector" with "-fstack-protector-strong" option. > + Like -fstack-protector but includes additional functions to be > + protected. > + > +config STACK_PROTECTOR_ALL > + bool "Almighty Stack Protector" > + depends on STACK_PROTECTOR > + default n > + help > + Turn on the "stack-protector" with "-fstack-protector-all" option. > + Like -fstack-protector except that all functions are protected. > + > +endmenu > diff --git a/lib/utils/stack_protector/objects.mk b/lib/utils/stack_protector/objects.mk > new file mode 100644 > index 0000000..d7563e3 > --- /dev/null > +++ b/lib/utils/stack_protector/objects.mk > @@ -0,0 +1,18 @@ > +# > +# SPDX-License-Identifier: BSD-2-Clause > +# > +# Copyright (c) 2025 Andes Technology Corporation > +# > +# Authors: > +# Alvin Chang <alvinga@andestech.com> > +# > + > +libsbiutils-objs-$(CONFIG_STACK_PROTECTOR) += stack_protector/stack_protector.o > + > +ifeq ($(CONFIG_STACK_PROTECTOR),y) > +stack-protector-cflags-$(CONFIG_STACK_PROTECTOR) := -fstack-protector > +stack-protector-cflags-$(CONFIG_STACK_PROTECTOR_STRONG) := -fstack-protector-strong > +stack-protector-cflags-$(CONFIG_STACK_PROTECTOR_ALL) := -fstack-protector-all > +else > +stack-protector-cflags-y := -fno-stack-protector > +endif > diff --git a/lib/utils/stack_protector/stack_protector.c b/lib/utils/stack_protector/stack_protector.c > new file mode 100644 > index 0000000..3088421 > --- /dev/null > +++ b/lib/utils/stack_protector/stack_protector.c > @@ -0,0 +1,18 @@ > +/* > + * SPDX-License-Identifier: BSD-2-Clause > + * > + * Copyright (c) 2025 Andes Technology Corporation > + * > + * Authors: > + * Alvin Chang <alvinga@andestech.com> > + */ > + > +#include <sbi/sbi_console.h> > +#include <sbi/sbi_types.h> > + > +void *__stack_chk_guard = (void *)0x95B5FF5AUL; > + > +void __noreturn __stack_chk_fail(void) > +{ > + sbi_panic("Stack corruption detected\n"); > +}
diff --git a/Makefile b/Makefile index e90836c..eae6d16 100644 --- a/Makefile +++ b/Makefile @@ -360,7 +360,7 @@ GENFLAGS += $(libsbiutils-genflags-y) GENFLAGS += $(platform-genflags-y) GENFLAGS += $(firmware-genflags-y) -CFLAGS = -g -Wall -Werror -ffreestanding -nostdlib -fno-stack-protector -fno-strict-aliasing -ffunction-sections -fdata-sections +CFLAGS = -g -Wall -Werror -ffreestanding -nostdlib -fno-strict-aliasing -ffunction-sections -fdata-sections CFLAGS += -fno-omit-frame-pointer -fno-optimize-sibling-calls # Optionally supported flags ifeq ($(CC_SUPPORT_VECTOR),y) @@ -379,6 +379,7 @@ CFLAGS += $(GENFLAGS) CFLAGS += $(platform-cflags-y) CFLAGS += -fPIE -pie CFLAGS += $(firmware-cflags-y) +CFLAGS += $(stack-protector-cflags-y) CPPFLAGS += $(GENFLAGS) CPPFLAGS += $(platform-cppflags-y) diff --git a/lib/utils/Kconfig b/lib/utils/Kconfig index 901ba56..40e5633 100644 --- a/lib/utils/Kconfig +++ b/lib/utils/Kconfig @@ -26,6 +26,8 @@ source "$(OPENSBI_SRC_DIR)/lib/utils/reset/Kconfig" source "$(OPENSBI_SRC_DIR)/lib/utils/serial/Kconfig" +source "$(OPENSBI_SRC_DIR)/lib/utils/stack_protector/Kconfig" + source "$(OPENSBI_SRC_DIR)/lib/utils/suspend/Kconfig" source "$(OPENSBI_SRC_DIR)/lib/utils/sys/Kconfig" diff --git a/lib/utils/stack_protector/Kconfig b/lib/utils/stack_protector/Kconfig new file mode 100644 index 0000000..c1fee19 --- /dev/null +++ b/lib/utils/stack_protector/Kconfig @@ -0,0 +1,28 @@ +# SPDX-License-Identifier: BSD-2-Clause + +menu "Stack Protector Support" + +config STACK_PROTECTOR + bool "Stack Protector buffer overflow detection" + default n + help + This option turns on the "stack-protector" compiler feature. + +config STACK_PROTECTOR_STRONG + bool "Strong Stack Protector" + depends on STACK_PROTECTOR + default n + help + Turn on the "stack-protector" with "-fstack-protector-strong" option. + Like -fstack-protector but includes additional functions to be + protected. + +config STACK_PROTECTOR_ALL + bool "Almighty Stack Protector" + depends on STACK_PROTECTOR + default n + help + Turn on the "stack-protector" with "-fstack-protector-all" option. + Like -fstack-protector except that all functions are protected. + +endmenu diff --git a/lib/utils/stack_protector/objects.mk b/lib/utils/stack_protector/objects.mk new file mode 100644 index 0000000..d7563e3 --- /dev/null +++ b/lib/utils/stack_protector/objects.mk @@ -0,0 +1,18 @@ +# +# SPDX-License-Identifier: BSD-2-Clause +# +# Copyright (c) 2025 Andes Technology Corporation +# +# Authors: +# Alvin Chang <alvinga@andestech.com> +# + +libsbiutils-objs-$(CONFIG_STACK_PROTECTOR) += stack_protector/stack_protector.o + +ifeq ($(CONFIG_STACK_PROTECTOR),y) +stack-protector-cflags-$(CONFIG_STACK_PROTECTOR) := -fstack-protector +stack-protector-cflags-$(CONFIG_STACK_PROTECTOR_STRONG) := -fstack-protector-strong +stack-protector-cflags-$(CONFIG_STACK_PROTECTOR_ALL) := -fstack-protector-all +else +stack-protector-cflags-y := -fno-stack-protector +endif diff --git a/lib/utils/stack_protector/stack_protector.c b/lib/utils/stack_protector/stack_protector.c new file mode 100644 index 0000000..3088421 --- /dev/null +++ b/lib/utils/stack_protector/stack_protector.c @@ -0,0 +1,18 @@ +/* + * SPDX-License-Identifier: BSD-2-Clause + * + * Copyright (c) 2025 Andes Technology Corporation + * + * Authors: + * Alvin Chang <alvinga@andestech.com> + */ + +#include <sbi/sbi_console.h> +#include <sbi/sbi_types.h> + +void *__stack_chk_guard = (void *)0x95B5FF5AUL; + +void __noreturn __stack_chk_fail(void) +{ + sbi_panic("Stack corruption detected\n"); +}
Add stack_protector.c which defines the stack guard variable and the function which will be referenced by compiler built-in stack protector. This patch just try to support stack-protector so the value of the stack guard variable is simply fixed for now. It could be improved by deriving from a random number generator, such as Zkr extension or any platform-specific random number sources. Introduce three configurations for the stack protector: 1. CONFIG_STACK_PROTECTOR to enable the stack protector feature by providing "-fstack-protector" compiler flag 2. CONFIG_STACK_PROTECTOR_STRONG to provide "-fstack-protector-strong" 3. CONFIG_STACK_PROTECTOR_ALL to provide "-fstack-protector-all" Instead of fixing the compiler flag of stack-protector feature as "-fstack-protector", we derive it from the introduced Kconfig configurations. The compiler flag "stack-protector-cflags-y" is defined as Makefile "immediately expanded variables" with ":=". Thus, the stronger configuration of the stack protector can overwrite the preceding one. Signed-off-by: Alvin Chang <alvinga@andestech.com> --- Makefile | 3 ++- lib/utils/Kconfig | 2 ++ lib/utils/stack_protector/Kconfig | 28 +++++++++++++++++++++ lib/utils/stack_protector/objects.mk | 18 +++++++++++++ lib/utils/stack_protector/stack_protector.c | 18 +++++++++++++ 5 files changed, 68 insertions(+), 1 deletion(-) create mode 100644 lib/utils/stack_protector/Kconfig create mode 100644 lib/utils/stack_protector/objects.mk create mode 100644 lib/utils/stack_protector/stack_protector.c