Loading arch/arm/Kconfig +12 −0 Original line number Diff line number Diff line Loading @@ -1375,6 +1375,18 @@ config UACCESS_WITH_MEMCPY However, if the CPU data cache is using a write-allocate mode, this option is unlikely to provide any performance gain. config CC_STACKPROTECTOR bool "Enable -fstack-protector buffer overflow detection (EXPERIMENTAL)" help This option turns on the -fstack-protector GCC feature. This feature puts, at the beginning of functions, a canary value on the stack just before the return address, and validates the value just before actually returning. Stack based buffer overflows (that need to overwrite this return address) now also overwrite the canary, which gets detected and the attack is then neutralized via a kernel panic. This feature requires gcc version 4.2 or above. endmenu menu "Boot options" Loading arch/arm/Makefile +4 −0 Original line number Diff line number Diff line Loading @@ -34,6 +34,10 @@ ifeq ($(CONFIG_FRAME_POINTER),y) KBUILD_CFLAGS +=-fno-omit-frame-pointer -mapcs -mno-sched-prolog endif ifeq ($(CONFIG_CC_STACKPROTECTOR),y) KBUILD_CFLAGS +=-fstack-protector endif ifeq ($(CONFIG_CPU_BIG_ENDIAN),y) KBUILD_CPPFLAGS += -mbig-endian AS += -EB Loading arch/arm/include/asm/elf.h +3 −0 Original line number Diff line number Diff line Loading @@ -121,4 +121,7 @@ int dump_task_regs(struct task_struct *t, elf_gregset_t *elfregs); extern void elf_set_personality(const struct elf32_hdr *); #define SET_PERSONALITY(ex) elf_set_personality(&(ex)) extern unsigned long arch_randomize_brk(struct mm_struct *mm); #define arch_randomize_brk arch_randomize_brk #endif arch/arm/include/asm/stackprotector.h 0 → 100644 +38 −0 Original line number Diff line number Diff line /* * GCC stack protector support. * * Stack protector works by putting predefined pattern at the start of * the stack frame and verifying that it hasn't been overwritten when * returning from the function. The pattern is called stack canary * and gcc expects it to be defined by a global variable called * "__stack_chk_guard" on ARM. This unfortunately means that on SMP * we cannot have a different canary value per task. */ #ifndef _ASM_STACKPROTECTOR_H #define _ASM_STACKPROTECTOR_H 1 #include <linux/random.h> #include <linux/version.h> extern unsigned long __stack_chk_guard; /* * Initialize the stackprotector canary value. * * NOTE: this must only be called from functions that never return, * and it must always be inlined. */ static __always_inline void boot_init_stack_canary(void) { unsigned long canary; /* Try to get a semi random initial value. */ get_random_bytes(&canary, sizeof(canary)); canary ^= LINUX_VERSION_CODE; current->stack_canary = canary; __stack_chk_guard = current->stack_canary; } #endif /* _ASM_STACKPROTECTOR_H */ arch/arm/kernel/asm-offsets.c +3 −0 Original line number Diff line number Diff line Loading @@ -40,6 +40,9 @@ int main(void) { DEFINE(TSK_ACTIVE_MM, offsetof(struct task_struct, active_mm)); #ifdef CONFIG_CC_STACKPROTECTOR DEFINE(TSK_STACK_CANARY, offsetof(struct task_struct, stack_canary)); #endif BLANK(); DEFINE(TI_FLAGS, offsetof(struct thread_info, flags)); DEFINE(TI_PREEMPT, offsetof(struct thread_info, preempt_count)); Loading Loading
arch/arm/Kconfig +12 −0 Original line number Diff line number Diff line Loading @@ -1375,6 +1375,18 @@ config UACCESS_WITH_MEMCPY However, if the CPU data cache is using a write-allocate mode, this option is unlikely to provide any performance gain. config CC_STACKPROTECTOR bool "Enable -fstack-protector buffer overflow detection (EXPERIMENTAL)" help This option turns on the -fstack-protector GCC feature. This feature puts, at the beginning of functions, a canary value on the stack just before the return address, and validates the value just before actually returning. Stack based buffer overflows (that need to overwrite this return address) now also overwrite the canary, which gets detected and the attack is then neutralized via a kernel panic. This feature requires gcc version 4.2 or above. endmenu menu "Boot options" Loading
arch/arm/Makefile +4 −0 Original line number Diff line number Diff line Loading @@ -34,6 +34,10 @@ ifeq ($(CONFIG_FRAME_POINTER),y) KBUILD_CFLAGS +=-fno-omit-frame-pointer -mapcs -mno-sched-prolog endif ifeq ($(CONFIG_CC_STACKPROTECTOR),y) KBUILD_CFLAGS +=-fstack-protector endif ifeq ($(CONFIG_CPU_BIG_ENDIAN),y) KBUILD_CPPFLAGS += -mbig-endian AS += -EB Loading
arch/arm/include/asm/elf.h +3 −0 Original line number Diff line number Diff line Loading @@ -121,4 +121,7 @@ int dump_task_regs(struct task_struct *t, elf_gregset_t *elfregs); extern void elf_set_personality(const struct elf32_hdr *); #define SET_PERSONALITY(ex) elf_set_personality(&(ex)) extern unsigned long arch_randomize_brk(struct mm_struct *mm); #define arch_randomize_brk arch_randomize_brk #endif
arch/arm/include/asm/stackprotector.h 0 → 100644 +38 −0 Original line number Diff line number Diff line /* * GCC stack protector support. * * Stack protector works by putting predefined pattern at the start of * the stack frame and verifying that it hasn't been overwritten when * returning from the function. The pattern is called stack canary * and gcc expects it to be defined by a global variable called * "__stack_chk_guard" on ARM. This unfortunately means that on SMP * we cannot have a different canary value per task. */ #ifndef _ASM_STACKPROTECTOR_H #define _ASM_STACKPROTECTOR_H 1 #include <linux/random.h> #include <linux/version.h> extern unsigned long __stack_chk_guard; /* * Initialize the stackprotector canary value. * * NOTE: this must only be called from functions that never return, * and it must always be inlined. */ static __always_inline void boot_init_stack_canary(void) { unsigned long canary; /* Try to get a semi random initial value. */ get_random_bytes(&canary, sizeof(canary)); canary ^= LINUX_VERSION_CODE; current->stack_canary = canary; __stack_chk_guard = current->stack_canary; } #endif /* _ASM_STACKPROTECTOR_H */
arch/arm/kernel/asm-offsets.c +3 −0 Original line number Diff line number Diff line Loading @@ -40,6 +40,9 @@ int main(void) { DEFINE(TSK_ACTIVE_MM, offsetof(struct task_struct, active_mm)); #ifdef CONFIG_CC_STACKPROTECTOR DEFINE(TSK_STACK_CANARY, offsetof(struct task_struct, stack_canary)); #endif BLANK(); DEFINE(TI_FLAGS, offsetof(struct thread_info, flags)); DEFINE(TI_PREEMPT, offsetof(struct thread_info, preempt_count)); Loading