Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'hardening-v6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux

Pull hardening updates from Kees Cook:

- Introduce and start using TRAILING_OVERLAP() helper for fixing
embedded flex array instances (Gustavo A. R. Silva)

- mux: Convert mux_control_ops to a flex array member in mux_chip
(Thorsten Blum)

- string: Group str_has_prefix() and strstarts() (Andy Shevchenko)

- Remove KCOV instrumentation from __init and __head (Ritesh Harjani,
Kees Cook)

- Refactor and rename stackleak feature to support Clang

- Add KUnit test for seq_buf API

- Fix KUnit fortify test under LTO

* tag 'hardening-v6.17-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux: (22 commits)
sched/task_stack: Add missing const qualifier to end_of_stack()
kstack_erase: Support Clang stack depth tracking
kstack_erase: Add -mgeneral-regs-only to silence Clang warnings
init.h: Disable sanitizer coverage for __init and __head
kstack_erase: Disable kstack_erase for all of arm compressed boot code
x86: Handle KCOV __init vs inline mismatches
arm64: Handle KCOV __init vs inline mismatches
s390: Handle KCOV __init vs inline mismatches
arm: Handle KCOV __init vs inline mismatches
mips: Handle KCOV __init vs inline mismatch
powerpc/mm/book3s64: Move kfence and debug_pagealloc related calls to __init section
configs/hardening: Enable CONFIG_INIT_ON_FREE_DEFAULT_ON
configs/hardening: Enable CONFIG_KSTACK_ERASE
stackleak: Split KSTACK_ERASE_CFLAGS from GCC_PLUGINS_CFLAGS
stackleak: Rename stackleak_track_stack to __sanitizer_cov_stack_depth
stackleak: Rename STACKLEAK to KSTACK_ERASE
seq_buf: Introduce KUnit tests
string: Group str_has_prefix() and strstarts()
kunit/fortify: Add back "volatile" for sizeof() constants
acpi: nfit: intel: avoid multiple -Wflex-array-member-not-at-end warnings
...

+514 -259
+2 -2
Documentation/admin-guide/sysctl/kernel.rst
··· 1465 1465 ============= 1466 1466 1467 1467 This parameter can be used to control kernel stack erasing at the end 1468 - of syscalls for kernels built with ``CONFIG_GCC_PLUGIN_STACKLEAK``. 1468 + of syscalls for kernels built with ``CONFIG_KSTACK_ERASE``. 1469 1469 1470 1470 That erasing reduces the information which kernel stack leak bugs 1471 1471 can reveal and blocks some uninitialized stack variable attacks. ··· 1473 1473 compilation sees a 1% slowdown, other systems and workloads may vary. 1474 1474 1475 1475 = ==================================================================== 1476 - 0 Kernel stack erasing is disabled, STACKLEAK_METRICS are not updated. 1476 + 0 Kernel stack erasing is disabled, KSTACK_ERASE_METRICS are not updated. 1477 1477 1 Kernel stack erasing is enabled (default), it is performed before 1478 1478 returning to the userspace at the end of syscalls. 1479 1479 = ====================================================================
+1 -1
Documentation/arch/x86/x86_64/mm.rst
··· 176 176 range must not overlap with anything except the KASAN shadow area, which is 177 177 correct as KASAN disables KASLR. 178 178 179 - For both 4- and 5-level layouts, the STACKLEAK_POISON value in the last 2MB 179 + For both 4- and 5-level layouts, the KSTACK_ERASE_POISON value in the last 2MB 180 180 hole: ffffffffffff4111
+1 -1
Documentation/security/self-protection.rst
··· 303 303 304 304 When releasing memory, it is best to poison the contents, to avoid reuse 305 305 attacks that rely on the old contents of memory. E.g., clear stack on a 306 - syscall return (``CONFIG_GCC_PLUGIN_STACKLEAK``), wipe heap memory on a 306 + syscall return (``CONFIG_KSTACK_ERASE``), wipe heap memory on a 307 307 free. This frustrates many uninitialized variable attacks, stack content 308 308 exposures, heap content exposures, and use-after-free attacks. 309 309
+1 -1
Documentation/translations/zh_CN/security/self-protection.rst
··· 259 259 -------- 260 260 261 261 在释放内存时,最好对内存内容进行清除处理,以防止攻击者重用内存中以前 262 - 的内容。例如,在系统调用返回时清除堆栈(CONFIG_GCC_PLUGIN_STACKLEAK), 262 + 的内容。例如,在系统调用返回时清除堆栈(CONFIG_KSTACK_ERASE), 263 263 在释放堆内容是清除其内容。这有助于防止许多未初始化变量攻击、堆栈内容 264 264 泄露、堆内容泄露以及使用后释放攻击(user-after-free)。 265 265
+4 -2
MAINTAINERS
··· 9997 9997 S: Maintained 9998 9998 T: git git://git.kernel.org/pub/scm/linux/kernel/git/kees/linux.git for-next/hardening 9999 9999 F: Documentation/kbuild/gcc-plugins.rst 10000 - F: include/linux/stackleak.h 10001 - F: kernel/stackleak.c 10002 10000 F: scripts/Makefile.gcc-plugins 10003 10001 F: scripts/gcc-plugins/ 10004 10002 ··· 13092 13094 F: Documentation/ABI/testing/sysfs-kernel-oops_count 13093 13095 F: Documentation/ABI/testing/sysfs-kernel-warn_count 13094 13096 F: arch/*/configs/hardening.config 13097 + F: include/linux/kstack_erase.h 13095 13098 F: include/linux/overflow.h 13096 13099 F: include/linux/randomize_kstack.h 13097 13100 F: include/linux/ucopysize.h 13098 13101 F: kernel/configs/hardening.config 13102 + F: kernel/kstack_erase.c 13099 13103 F: lib/tests/randstruct_kunit.c 13100 13104 F: lib/tests/usercopy_kunit.c 13101 13105 F: mm/usercopy.c 13106 + F: scripts/Makefile.kstack_erase 13107 + F: scripts/Makefile.randstruct 13102 13108 F: security/Kconfig.hardening 13103 13109 K: \b(add|choose)_random_kstack_offset\b 13104 13110 K: \b__check_(object_size|heap_object)\b
+1
Makefile
··· 1086 1086 include-$(CONFIG_UBSAN) += scripts/Makefile.ubsan 1087 1087 include-$(CONFIG_KCOV) += scripts/Makefile.kcov 1088 1088 include-$(CONFIG_RANDSTRUCT) += scripts/Makefile.randstruct 1089 + include-$(CONFIG_KSTACK_ERASE) += scripts/Makefile.kstack_erase 1089 1090 include-$(CONFIG_AUTOFDO_CLANG) += scripts/Makefile.autofdo 1090 1091 include-$(CONFIG_PROPELLER_CLANG) += scripts/Makefile.propeller 1091 1092 include-$(CONFIG_GCC_PLUGINS) += scripts/Makefile.gcc-plugins
+2 -2
arch/Kconfig
··· 630 630 631 631 If unsure, say N. 632 632 633 - config HAVE_ARCH_STACKLEAK 633 + config HAVE_ARCH_KSTACK_ERASE 634 634 bool 635 635 help 636 636 An architecture should select this if it has the code which 637 - fills the used part of the kernel stack with the STACKLEAK_POISON 637 + fills the used part of the kernel stack with the KSTACK_ERASE_POISON 638 638 value before returning from system calls. 639 639 640 640 config HAVE_STACKPROTECTOR
+1 -1
arch/arm/Kconfig
··· 87 87 select HAVE_ARCH_KGDB if !CPU_ENDIAN_BE32 && MMU 88 88 select HAVE_ARCH_KASAN if MMU && !XIP_KERNEL 89 89 select HAVE_ARCH_KASAN_VMALLOC if HAVE_ARCH_KASAN 90 + select HAVE_ARCH_KSTACK_ERASE 90 91 select HAVE_ARCH_MMAP_RND_BITS if MMU 91 92 select HAVE_ARCH_PFN_VALID 92 93 select HAVE_ARCH_SECCOMP 93 94 select HAVE_ARCH_SECCOMP_FILTER if AEABI && !OABI_COMPAT 94 - select HAVE_ARCH_STACKLEAK 95 95 select HAVE_ARCH_THREAD_STRUCT_WHITELIST 96 96 select HAVE_ARCH_TRACEHOOK 97 97 select HAVE_ARCH_TRANSPARENT_HUGEPAGE if ARM_LPAE
+1 -1
arch/arm/boot/compressed/Makefile
··· 9 9 10 10 HEAD = head.o 11 11 OBJS += misc.o decompress.o 12 - CFLAGS_decompress.o += $(DISABLE_STACKLEAK_PLUGIN) 13 12 ifeq ($(CONFIG_DEBUG_UNCOMPRESS),y) 14 13 OBJS += debug.o 15 14 AFLAGS_head.o += -DDEBUG ··· 95 96 96 97 ccflags-y := -fpic $(call cc-option,-mno-single-pic-base,) -fno-builtin \ 97 98 -I$(srctree)/scripts/dtc/libfdt -fno-stack-protector \ 99 + $(DISABLE_KSTACK_ERASE) \ 98 100 -I$(obj) 99 101 ccflags-remove-$(CONFIG_FUNCTION_TRACER) += -pg 100 102 asflags-y := -DZIMAGE
+1 -1
arch/arm/kernel/entry-common.S
··· 119 119 120 120 ct_user_enter save = 0 121 121 122 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 122 + #ifdef CONFIG_KSTACK_ERASE 123 123 bl stackleak_erase_on_task_stack 124 124 #endif 125 125 restore_user_regs fast = 0, offset = 0
+1 -1
arch/arm/mm/cache-feroceon-l2.c
··· 295 295 return u; 296 296 } 297 297 298 - static inline void write_extra_features(u32 u) 298 + static inline void __init write_extra_features(u32 u) 299 299 { 300 300 __asm__("mcr p15, 1, %0, c15, c1, 0" : : "r" (u)); 301 301 }
+1 -1
arch/arm/mm/cache-tauros2.c
··· 177 177 __asm__("mcr p15, 0, %0, c1, c0, 1\n" : : "r" (actlr)); 178 178 } 179 179 180 - static void enable_extra_feature(unsigned int features) 180 + static void __init enable_extra_feature(unsigned int features) 181 181 { 182 182 u32 u; 183 183
+1 -1
arch/arm/vdso/Makefile
··· 26 26 CFLAGS_REMOVE_vdso.o = -pg 27 27 28 28 # Force -O2 to avoid libgcc dependencies 29 - CFLAGS_REMOVE_vgettimeofday.o = -pg -Os $(RANDSTRUCT_CFLAGS) $(GCC_PLUGINS_CFLAGS) 29 + CFLAGS_REMOVE_vgettimeofday.o = -pg -Os $(RANDSTRUCT_CFLAGS) $(KSTACK_ERASE_CFLAGS) $(GCC_PLUGINS_CFLAGS) 30 30 ifeq ($(c-gettimeofday-y),) 31 31 CFLAGS_vgettimeofday.o = -O2 32 32 else
+1 -1
arch/arm64/Kconfig
··· 187 187 select HAVE_ARCH_KCSAN if EXPERT 188 188 select HAVE_ARCH_KFENCE 189 189 select HAVE_ARCH_KGDB 190 + select HAVE_ARCH_KSTACK_ERASE 190 191 select HAVE_ARCH_MMAP_RND_BITS 191 192 select HAVE_ARCH_MMAP_RND_COMPAT_BITS if COMPAT 192 193 select HAVE_ARCH_PREL32_RELOCATIONS 193 194 select HAVE_ARCH_RANDOMIZE_KSTACK_OFFSET 194 195 select HAVE_ARCH_SECCOMP_FILTER 195 - select HAVE_ARCH_STACKLEAK 196 196 select HAVE_ARCH_THREAD_STRUCT_WHITELIST 197 197 select HAVE_ARCH_TRACEHOOK 198 198 select HAVE_ARCH_TRANSPARENT_HUGEPAGE
+1 -1
arch/arm64/include/asm/acpi.h
··· 150 150 {} 151 151 #endif 152 152 153 - static inline const char *acpi_get_enable_method(int cpu) 153 + static __always_inline const char *acpi_get_enable_method(int cpu) 154 154 { 155 155 if (acpi_psci_present()) 156 156 return "psci";
+1 -1
arch/arm64/kernel/entry.S
··· 614 614 SYM_CODE_START_LOCAL(ret_to_user) 615 615 ldr x19, [tsk, #TSK_TI_FLAGS] // re-check for single-step 616 616 enable_step_tsk x19, x2 617 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 617 + #ifdef CONFIG_KSTACK_ERASE 618 618 bl stackleak_erase_on_task_stack 619 619 #endif 620 620 kernel_exit 0
+1 -1
arch/arm64/kernel/pi/Makefile
··· 2 2 # Copyright 2022 Google LLC 3 3 4 4 KBUILD_CFLAGS := $(subst $(CC_FLAGS_FTRACE),,$(KBUILD_CFLAGS)) -fpie \ 5 - -Os -DDISABLE_BRANCH_PROFILING $(DISABLE_STACKLEAK_PLUGIN) \ 5 + -Os -DDISABLE_BRANCH_PROFILING $(DISABLE_KSTACK_ERASE) \ 6 6 $(DISABLE_LATENT_ENTROPY_PLUGIN) \ 7 7 $(call cc-option,-mbranch-protection=none) \ 8 8 -I$(srctree)/scripts/dtc/libfdt -fno-stack-protector \
+2 -1
arch/arm64/kernel/vdso/Makefile
··· 36 36 # -Wmissing-prototypes and -Wmissing-declarations are removed from 37 37 # the CFLAGS to make possible to build the kernel with CONFIG_WERROR enabled. 38 38 CC_FLAGS_REMOVE_VDSO := $(CC_FLAGS_FTRACE) -Os $(CC_FLAGS_SCS) \ 39 - $(RANDSTRUCT_CFLAGS) $(GCC_PLUGINS_CFLAGS) \ 39 + $(RANDSTRUCT_CFLAGS) $(KSTACK_ERASE_CFLAGS) \ 40 + $(GCC_PLUGINS_CFLAGS) \ 40 41 $(CC_FLAGS_LTO) $(CC_FLAGS_CFI) \ 41 42 -Wmissing-prototypes -Wmissing-declarations 42 43
+1 -1
arch/arm64/kvm/hyp/nvhe/Makefile
··· 12 12 ccflags-y := -D__KVM_NVHE_HYPERVISOR__ -D__DISABLE_EXPORTS -D__DISABLE_TRACE_MMIO__ 13 13 ccflags-y += -fno-stack-protector \ 14 14 -DDISABLE_BRANCH_PROFILING \ 15 - $(DISABLE_STACKLEAK_PLUGIN) 15 + $(DISABLE_KSTACK_ERASE) 16 16 17 17 hostprogs := gen-hyprel 18 18 HOST_EXTRACFLAGS += -I$(objtree)/include
+1 -1
arch/loongarch/Kconfig
··· 120 120 select HAVE_ARCH_KASAN 121 121 select HAVE_ARCH_KFENCE 122 122 select HAVE_ARCH_KGDB if PERF_EVENTS 123 + select HAVE_ARCH_KSTACK_ERASE 123 124 select HAVE_ARCH_MMAP_RND_BITS if MMU 124 125 select HAVE_ARCH_RANDOMIZE_KSTACK_OFFSET 125 126 select HAVE_ARCH_SECCOMP 126 127 select HAVE_ARCH_SECCOMP_FILTER 127 - select HAVE_ARCH_STACKLEAK 128 128 select HAVE_ARCH_TRACEHOOK 129 129 select HAVE_ARCH_TRANSPARENT_HUGEPAGE 130 130 select HAVE_ARCH_USERFAULTFD_MINOR if USERFAULTFD
+1 -1
arch/mips/include/asm/time.h
··· 55 55 */ 56 56 extern int init_r4k_clocksource(void); 57 57 58 - static inline int init_mips_clocksource(void) 58 + static inline __init int init_mips_clocksource(void) 59 59 { 60 60 #ifdef CONFIG_CSRC_R4K 61 61 return init_r4k_clocksource();
+3 -3
arch/powerpc/mm/book3s64/hash_utils.c
··· 343 343 static u8 *linear_map_hash_slots; 344 344 static unsigned long linear_map_hash_count; 345 345 static DEFINE_RAW_SPINLOCK(linear_map_hash_lock); 346 - static void hash_debug_pagealloc_alloc_slots(void) 346 + static __init void hash_debug_pagealloc_alloc_slots(void) 347 347 { 348 348 if (!hash_supports_debug_pagealloc()) 349 349 return; ··· 409 409 410 410 static phys_addr_t kfence_pool; 411 411 412 - static inline void hash_kfence_alloc_pool(void) 412 + static __init void hash_kfence_alloc_pool(void) 413 413 { 414 414 if (!kfence_early_init_enabled()) 415 415 goto err; ··· 445 445 disable_kfence(); 446 446 } 447 447 448 - static inline void hash_kfence_map_pool(void) 448 + static __init void hash_kfence_map_pool(void) 449 449 { 450 450 unsigned long kfence_pool_start, kfence_pool_end; 451 451 unsigned long prot = pgprot_val(PAGE_KERNEL);
+2 -2
arch/powerpc/mm/book3s64/radix_pgtable.c
··· 363 363 } 364 364 365 365 #ifdef CONFIG_KFENCE 366 - static inline phys_addr_t alloc_kfence_pool(void) 366 + static __init phys_addr_t alloc_kfence_pool(void) 367 367 { 368 368 phys_addr_t kfence_pool; 369 369 ··· 393 393 return 0; 394 394 } 395 395 396 - static inline void map_kfence_pool(phys_addr_t kfence_pool) 396 + static __init void map_kfence_pool(phys_addr_t kfence_pool) 397 397 { 398 398 if (!kfence_pool) 399 399 return;
+1 -1
arch/riscv/Kconfig
··· 137 137 select HAVE_ARCH_KASAN if MMU && 64BIT 138 138 select HAVE_ARCH_KASAN_VMALLOC if MMU && 64BIT 139 139 select HAVE_ARCH_KFENCE if MMU && 64BIT 140 + select HAVE_ARCH_KSTACK_ERASE 140 141 select HAVE_ARCH_KGDB if !XIP_KERNEL 141 142 select HAVE_ARCH_KGDB_QXFER_PKT 142 143 select HAVE_ARCH_MMAP_RND_BITS if MMU 143 144 select HAVE_ARCH_MMAP_RND_COMPAT_BITS if COMPAT 144 145 select HAVE_ARCH_RANDOMIZE_KSTACK_OFFSET 145 146 select HAVE_ARCH_SECCOMP_FILTER 146 - select HAVE_ARCH_STACKLEAK 147 147 select HAVE_ARCH_THREAD_STRUCT_WHITELIST 148 148 select HAVE_ARCH_TRACEHOOK 149 149 select HAVE_ARCH_TRANSPARENT_HUGEPAGE if 64BIT && MMU
+1 -1
arch/riscv/kernel/entry.S
··· 220 220 #endif 221 221 bnez s0, 1f 222 222 223 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 223 + #ifdef CONFIG_KSTACK_ERASE 224 224 call stackleak_erase_on_task_stack 225 225 #endif 226 226
+1 -1
arch/riscv/kernel/pi/Makefile
··· 2 2 # This file was copied from arm64/kernel/pi/Makefile. 3 3 4 4 KBUILD_CFLAGS := $(subst $(CC_FLAGS_FTRACE),,$(KBUILD_CFLAGS)) -fpie \ 5 - -Os -DDISABLE_BRANCH_PROFILING $(DISABLE_STACKLEAK_PLUGIN) \ 5 + -Os -DDISABLE_BRANCH_PROFILING $(DISABLE_KSTACK_ERASE) \ 6 6 $(call cc-option,-mbranch-protection=none) \ 7 7 -I$(srctree)/scripts/dtc/libfdt -fno-stack-protector \ 8 8 -include $(srctree)/include/linux/hidden.h \
+1 -1
arch/riscv/purgatory/Makefile
··· 53 53 54 54 PURGATORY_CFLAGS_REMOVE := -mcmodel=kernel 55 55 PURGATORY_CFLAGS := -mcmodel=medany -ffreestanding -fno-zero-initialized-in-bss 56 - PURGATORY_CFLAGS += $(DISABLE_STACKLEAK_PLUGIN) -DDISABLE_BRANCH_PROFILING 56 + PURGATORY_CFLAGS += $(DISABLE_KSTACK_ERASE) -DDISABLE_BRANCH_PROFILING 57 57 PURGATORY_CFLAGS += -fno-stack-protector -g0 58 58 59 59 # Default KBUILD_CFLAGS can have -pg option set when FTRACE is enabled. That
+1 -1
arch/s390/Kconfig
··· 176 176 select HAVE_ARCH_KCSAN 177 177 select HAVE_ARCH_KMSAN 178 178 select HAVE_ARCH_KFENCE 179 + select HAVE_ARCH_KSTACK_ERASE 179 180 select HAVE_ARCH_RANDOMIZE_KSTACK_OFFSET 180 181 select HAVE_ARCH_SECCOMP_FILTER 181 182 select HAVE_ARCH_SOFT_DIRTY 182 - select HAVE_ARCH_STACKLEAK 183 183 select HAVE_ARCH_TRACEHOOK 184 184 select HAVE_ARCH_TRANSPARENT_HUGEPAGE 185 185 select HAVE_ARCH_VMAP_STACK
+1 -1
arch/s390/hypfs/hypfs.h
··· 48 48 49 49 int __hypfs_fs_init(void); 50 50 51 - static inline int hypfs_fs_init(void) 51 + static __always_inline int hypfs_fs_init(void) 52 52 { 53 53 if (IS_ENABLED(CONFIG_S390_HYPFS_FS)) 54 54 return __hypfs_fs_init();
+1 -1
arch/s390/hypfs/hypfs_diag.h
··· 19 19 int __hypfs_diag_fs_init(void); 20 20 void __hypfs_diag_fs_exit(void); 21 21 22 - static inline int hypfs_diag_fs_init(void) 22 + static __always_inline int hypfs_diag_fs_init(void) 23 23 { 24 24 if (IS_ENABLED(CONFIG_S390_HYPFS_FS)) 25 25 return __hypfs_diag_fs_init();
+1 -1
arch/s390/kernel/entry.S
··· 124 124 #endif 125 125 126 126 .macro STACKLEAK_ERASE 127 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 127 + #ifdef CONFIG_KSTACK_ERASE 128 128 brasl %r14,stackleak_erase_on_task_stack 129 129 #endif 130 130 .endm
+1 -1
arch/s390/mm/init.c
··· 142 142 } 143 143 144 144 /* protected virtualization */ 145 - static void pv_init(void) 145 + static void __init pv_init(void) 146 146 { 147 147 if (!is_prot_virt_guest()) 148 148 return;
+2 -1
arch/sparc/vdso/Makefile
··· 48 48 49 49 SPARC_REG_CFLAGS = -ffixed-g4 -ffixed-g5 $(call cc-option,-fcall-used-g5) $(call cc-option,-fcall-used-g7) 50 50 51 - $(vobjs): KBUILD_CFLAGS := $(filter-out $(RANDSTRUCT_CFLAGS) $(GCC_PLUGINS_CFLAGS) $(SPARC_REG_CFLAGS),$(KBUILD_CFLAGS)) $(CFL) 51 + $(vobjs): KBUILD_CFLAGS := $(filter-out $(RANDSTRUCT_CFLAGS) $(KSTACK_ERASE_CFLAGS) $(GCC_PLUGINS_CFLAGS) $(SPARC_REG_CFLAGS),$(KBUILD_CFLAGS)) $(CFL) 52 52 53 53 # 54 54 # vDSO code runs in userspace and -pg doesn't help with profiling anyway. ··· 79 79 KBUILD_CFLAGS_32 := $(filter-out -mcmodel=medlow,$(KBUILD_CFLAGS_32)) 80 80 KBUILD_CFLAGS_32 := $(filter-out -fno-pic,$(KBUILD_CFLAGS_32)) 81 81 KBUILD_CFLAGS_32 := $(filter-out $(RANDSTRUCT_CFLAGS),$(KBUILD_CFLAGS_32)) 82 + KBUILD_CFLAGS_32 := $(filter-out $(KSTACK_ERASE_CFLAGS),$(KBUILD_CFLAGS_32)) 82 83 KBUILD_CFLAGS_32 := $(filter-out $(GCC_PLUGINS_CFLAGS),$(KBUILD_CFLAGS_32)) 83 84 KBUILD_CFLAGS_32 := $(filter-out $(SPARC_REG_CFLAGS),$(KBUILD_CFLAGS_32)) 84 85 KBUILD_CFLAGS_32 += -m32 -msoft-float -fpic
+1 -1
arch/x86/Kconfig
··· 204 204 select HAVE_ARCH_KFENCE 205 205 select HAVE_ARCH_KMSAN if X86_64 206 206 select HAVE_ARCH_KGDB 207 + select HAVE_ARCH_KSTACK_ERASE 207 208 select HAVE_ARCH_MMAP_RND_BITS if MMU 208 209 select HAVE_ARCH_MMAP_RND_COMPAT_BITS if MMU && COMPAT 209 210 select HAVE_ARCH_COMPAT_MMAP_BASES if MMU && COMPAT 210 211 select HAVE_ARCH_PREL32_RELOCATIONS 211 212 select HAVE_ARCH_SECCOMP_FILTER 212 213 select HAVE_ARCH_THREAD_STRUCT_WHITELIST 213 - select HAVE_ARCH_STACKLEAK 214 214 select HAVE_ARCH_TRACEHOOK 215 215 select HAVE_ARCH_TRANSPARENT_HUGEPAGE 216 216 select HAVE_ARCH_TRANSPARENT_HUGEPAGE_PUD if X86_64
+2 -2
arch/x86/entry/calling.h
··· 369 369 .endm 370 370 371 371 .macro STACKLEAK_ERASE_NOCLOBBER 372 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 372 + #ifdef CONFIG_KSTACK_ERASE 373 373 PUSH_AND_CLEAR_REGS 374 374 call stackleak_erase 375 375 POP_REGS ··· 388 388 #endif /* !CONFIG_X86_64 */ 389 389 390 390 .macro STACKLEAK_ERASE 391 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 391 + #ifdef CONFIG_KSTACK_ERASE 392 392 call stackleak_erase 393 393 #endif 394 394 .endm
+2 -1
arch/x86/entry/vdso/Makefile
··· 62 62 endif 63 63 endif 64 64 65 - $(vobjs): KBUILD_CFLAGS := $(filter-out $(PADDING_CFLAGS) $(CC_FLAGS_LTO) $(CC_FLAGS_CFI) $(RANDSTRUCT_CFLAGS) $(GCC_PLUGINS_CFLAGS) $(RETPOLINE_CFLAGS),$(KBUILD_CFLAGS)) $(CFL) 65 + $(vobjs): KBUILD_CFLAGS := $(filter-out $(PADDING_CFLAGS) $(CC_FLAGS_LTO) $(CC_FLAGS_CFI) $(RANDSTRUCT_CFLAGS) $(KSTACK_ERASE_CFLAGS) $(GCC_PLUGINS_CFLAGS) $(RETPOLINE_CFLAGS),$(KBUILD_CFLAGS)) $(CFL) 66 66 $(vobjs): KBUILD_AFLAGS += -DBUILD_VDSO 67 67 68 68 # ··· 123 123 KBUILD_CFLAGS_32 := $(filter-out -fno-pic,$(KBUILD_CFLAGS_32)) 124 124 KBUILD_CFLAGS_32 := $(filter-out -mfentry,$(KBUILD_CFLAGS_32)) 125 125 KBUILD_CFLAGS_32 := $(filter-out $(RANDSTRUCT_CFLAGS),$(KBUILD_CFLAGS_32)) 126 + KBUILD_CFLAGS_32 := $(filter-out $(KSTACK_ERASE_CFLAGS),$(KBUILD_CFLAGS_32)) 126 127 KBUILD_CFLAGS_32 := $(filter-out $(GCC_PLUGINS_CFLAGS),$(KBUILD_CFLAGS_32)) 127 128 KBUILD_CFLAGS_32 := $(filter-out $(RETPOLINE_CFLAGS),$(KBUILD_CFLAGS_32)) 128 129 KBUILD_CFLAGS_32 := $(filter-out $(CC_FLAGS_LTO),$(KBUILD_CFLAGS_32))
+2 -2
arch/x86/include/asm/acpi.h
··· 158 158 } 159 159 160 160 #define ACPI_HAVE_ARCH_SET_ROOT_POINTER 161 - static inline void acpi_arch_set_root_pointer(u64 addr) 161 + static __always_inline void acpi_arch_set_root_pointer(u64 addr) 162 162 { 163 163 x86_init.acpi.set_root_pointer(addr); 164 164 } 165 165 166 166 #define ACPI_HAVE_ARCH_GET_ROOT_POINTER 167 - static inline u64 acpi_arch_get_root_pointer(void) 167 + static __always_inline u64 acpi_arch_get_root_pointer(void) 168 168 { 169 169 return x86_init.acpi.get_root_pointer(); 170 170 }
+1 -1
arch/x86/include/asm/init.h
··· 5 5 #if defined(CONFIG_CC_IS_CLANG) && CONFIG_CLANG_VERSION < 170000 6 6 #define __head __section(".head.text") __no_sanitize_undefined __no_stack_protector 7 7 #else 8 - #define __head __section(".head.text") __no_sanitize_undefined 8 + #define __head __section(".head.text") __no_sanitize_undefined __no_sanitize_coverage 9 9 #endif 10 10 11 11 struct x86_mapping_info {
+1 -1
arch/x86/include/asm/realmode.h
··· 78 78 extern unsigned char secondary_startup_64_no_verify[]; 79 79 #endif 80 80 81 - static inline size_t real_mode_size_needed(void) 81 + static __always_inline size_t real_mode_size_needed(void) 82 82 { 83 83 if (real_mode_header) 84 84 return 0; /* already allocated. */
+1 -1
arch/x86/kernel/kvm.c
··· 420 420 return steal; 421 421 } 422 422 423 - static inline void __set_percpu_decrypted(void *ptr, unsigned long size) 423 + static inline __init void __set_percpu_decrypted(void *ptr, unsigned long size) 424 424 { 425 425 early_set_memory_decrypted((unsigned long) ptr, size); 426 426 }
+1 -1
arch/x86/mm/init_64.c
··· 805 805 } 806 806 807 807 #ifndef CONFIG_NUMA 808 - static inline void x86_numa_init(void) 808 + static __always_inline void x86_numa_init(void) 809 809 { 810 810 memblock_set_node(0, PHYS_ADDR_MAX, &memblock.memory, 0); 811 811 }
+1 -1
arch/x86/purgatory/Makefile
··· 35 35 PURGATORY_CFLAGS_REMOVE := -mcmodel=kernel 36 36 PURGATORY_CFLAGS := -mcmodel=small -ffreestanding -fno-zero-initialized-in-bss -g0 37 37 PURGATORY_CFLAGS += -fpic -fvisibility=hidden 38 - PURGATORY_CFLAGS += $(DISABLE_STACKLEAK_PLUGIN) -DDISABLE_BRANCH_PROFILING 38 + PURGATORY_CFLAGS += $(DISABLE_KSTACK_ERASE) -DDISABLE_BRANCH_PROFILING 39 39 PURGATORY_CFLAGS += -fno-stack-protector 40 40 41 41 # Default KBUILD_CFLAGS can have -pg option set when FTRACE is enabled. That
+52 -67
drivers/acpi/nfit/intel.c
··· 55 55 { 56 56 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 57 57 unsigned long security_flags = 0; 58 - struct { 59 - struct nd_cmd_pkg pkg; 58 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 60 59 struct nd_intel_get_security_state cmd; 61 - } nd_cmd = { 60 + ) nd_cmd = { 62 61 .pkg = { 63 62 .nd_command = NVDIMM_INTEL_GET_SECURITY_STATE, 64 63 .nd_family = NVDIMM_FAMILY_INTEL, ··· 119 120 static int intel_security_freeze(struct nvdimm *nvdimm) 120 121 { 121 122 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 122 - struct { 123 - struct nd_cmd_pkg pkg; 123 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 124 124 struct nd_intel_freeze_lock cmd; 125 - } nd_cmd = { 125 + ) nd_cmd = { 126 126 .pkg = { 127 127 .nd_command = NVDIMM_INTEL_FREEZE_LOCK, 128 128 .nd_family = NVDIMM_FAMILY_INTEL, ··· 151 153 unsigned int cmd = ptype == NVDIMM_MASTER ? 152 154 NVDIMM_INTEL_SET_MASTER_PASSPHRASE : 153 155 NVDIMM_INTEL_SET_PASSPHRASE; 154 - struct { 155 - struct nd_cmd_pkg pkg; 156 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 156 157 struct nd_intel_set_passphrase cmd; 157 - } nd_cmd = { 158 + ) nd_cmd = { 158 159 .pkg = { 159 160 .nd_family = NVDIMM_FAMILY_INTEL, 160 161 .nd_size_in = ND_INTEL_PASSPHRASE_SIZE * 2, ··· 192 195 const struct nvdimm_key_data *key_data) 193 196 { 194 197 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 195 - struct { 196 - struct nd_cmd_pkg pkg; 198 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 197 199 struct nd_intel_unlock_unit cmd; 198 - } nd_cmd = { 200 + ) nd_cmd = { 199 201 .pkg = { 200 202 .nd_command = NVDIMM_INTEL_UNLOCK_UNIT, 201 203 .nd_family = NVDIMM_FAMILY_INTEL, ··· 230 234 { 231 235 int rc; 232 236 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 233 - struct { 234 - struct nd_cmd_pkg pkg; 237 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 235 238 struct nd_intel_disable_passphrase cmd; 236 - } nd_cmd = { 239 + ) nd_cmd = { 237 240 .pkg = { 238 241 .nd_command = NVDIMM_INTEL_DISABLE_PASSPHRASE, 239 242 .nd_family = NVDIMM_FAMILY_INTEL, ··· 272 277 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 273 278 unsigned int cmd = ptype == NVDIMM_MASTER ? 274 279 NVDIMM_INTEL_MASTER_SECURE_ERASE : NVDIMM_INTEL_SECURE_ERASE; 275 - struct { 276 - struct nd_cmd_pkg pkg; 280 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 277 281 struct nd_intel_secure_erase cmd; 278 - } nd_cmd = { 282 + ) nd_cmd = { 279 283 .pkg = { 280 284 .nd_family = NVDIMM_FAMILY_INTEL, 281 285 .nd_size_in = ND_INTEL_PASSPHRASE_SIZE, ··· 312 318 { 313 319 int rc; 314 320 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 315 - struct { 316 - struct nd_cmd_pkg pkg; 321 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 317 322 struct nd_intel_query_overwrite cmd; 318 - } nd_cmd = { 323 + ) nd_cmd = { 319 324 .pkg = { 320 325 .nd_command = NVDIMM_INTEL_QUERY_OVERWRITE, 321 326 .nd_family = NVDIMM_FAMILY_INTEL, ··· 347 354 { 348 355 int rc; 349 356 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 350 - struct { 351 - struct nd_cmd_pkg pkg; 357 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 352 358 struct nd_intel_overwrite cmd; 353 - } nd_cmd = { 359 + ) nd_cmd = { 354 360 .pkg = { 355 361 .nd_command = NVDIMM_INTEL_OVERWRITE, 356 362 .nd_family = NVDIMM_FAMILY_INTEL, ··· 399 407 static int intel_bus_fwa_businfo(struct nvdimm_bus_descriptor *nd_desc, 400 408 struct nd_intel_bus_fw_activate_businfo *info) 401 409 { 402 - struct { 403 - struct nd_cmd_pkg pkg; 410 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 404 411 struct nd_intel_bus_fw_activate_businfo cmd; 405 - } nd_cmd = { 412 + ) nd_cmd = { 406 413 .pkg = { 407 414 .nd_command = NVDIMM_BUS_INTEL_FW_ACTIVATE_BUSINFO, 408 415 .nd_family = NVDIMM_BUS_FAMILY_INTEL, ··· 509 518 static int intel_bus_fwa_activate(struct nvdimm_bus_descriptor *nd_desc) 510 519 { 511 520 struct acpi_nfit_desc *acpi_desc = to_acpi_desc(nd_desc); 512 - struct { 513 - struct nd_cmd_pkg pkg; 521 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 514 522 struct nd_intel_bus_fw_activate cmd; 515 - } nd_cmd = { 516 - .pkg = { 517 - .nd_command = NVDIMM_BUS_INTEL_FW_ACTIVATE, 518 - .nd_family = NVDIMM_BUS_FAMILY_INTEL, 519 - .nd_size_in = sizeof(nd_cmd.cmd.iodev_state), 520 - .nd_size_out = 521 - sizeof(struct nd_intel_bus_fw_activate), 522 - .nd_fw_size = 523 - sizeof(struct nd_intel_bus_fw_activate), 524 - }, 523 + ) nd_cmd; 524 + int rc; 525 + 526 + nd_cmd.pkg = (struct nd_cmd_pkg) { 527 + .nd_command = NVDIMM_BUS_INTEL_FW_ACTIVATE, 528 + .nd_family = NVDIMM_BUS_FAMILY_INTEL, 529 + .nd_size_in = sizeof(nd_cmd.cmd.iodev_state), 530 + .nd_size_out = 531 + sizeof(struct nd_intel_bus_fw_activate), 532 + .nd_fw_size = 533 + sizeof(struct nd_intel_bus_fw_activate), 534 + }; 535 + nd_cmd.cmd = (struct nd_intel_bus_fw_activate) { 525 536 /* 526 537 * Even though activate is run from a suspended context, 527 538 * for safety, still ask platform firmware to force 528 539 * quiesce devices by default. Let a module 529 540 * parameter override that policy. 530 541 */ 531 - .cmd = { 532 - .iodev_state = acpi_desc->fwa_noidle 533 - ? ND_INTEL_BUS_FWA_IODEV_OS_IDLE 534 - : ND_INTEL_BUS_FWA_IODEV_FORCE_IDLE, 535 - }, 542 + .iodev_state = acpi_desc->fwa_noidle 543 + ? ND_INTEL_BUS_FWA_IODEV_OS_IDLE 544 + : ND_INTEL_BUS_FWA_IODEV_FORCE_IDLE, 536 545 }; 537 - int rc; 538 - 539 546 switch (intel_bus_fwa_state(nd_desc)) { 540 547 case NVDIMM_FWA_ARMED: 541 548 case NVDIMM_FWA_ARM_OVERFLOW: ··· 571 582 static int intel_fwa_dimminfo(struct nvdimm *nvdimm, 572 583 struct nd_intel_fw_activate_dimminfo *info) 573 584 { 574 - struct { 575 - struct nd_cmd_pkg pkg; 585 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 576 586 struct nd_intel_fw_activate_dimminfo cmd; 577 - } nd_cmd = { 587 + ) nd_cmd = { 578 588 .pkg = { 579 589 .nd_command = NVDIMM_INTEL_FW_ACTIVATE_DIMMINFO, 580 590 .nd_family = NVDIMM_FAMILY_INTEL, ··· 676 688 { 677 689 struct nfit_mem *nfit_mem = nvdimm_provider_data(nvdimm); 678 690 struct acpi_nfit_desc *acpi_desc = nfit_mem->acpi_desc; 679 - struct { 680 - struct nd_cmd_pkg pkg; 691 + TRAILING_OVERLAP(struct nd_cmd_pkg, pkg, nd_payload, 681 692 struct nd_intel_fw_activate_arm cmd; 682 - } nd_cmd = { 683 - .pkg = { 684 - .nd_command = NVDIMM_INTEL_FW_ACTIVATE_ARM, 685 - .nd_family = NVDIMM_FAMILY_INTEL, 686 - .nd_size_in = sizeof(nd_cmd.cmd.activate_arm), 687 - .nd_size_out = 688 - sizeof(struct nd_intel_fw_activate_arm), 689 - .nd_fw_size = 690 - sizeof(struct nd_intel_fw_activate_arm), 691 - }, 692 - .cmd = { 693 - .activate_arm = arm == NVDIMM_FWA_ARM 694 - ? ND_INTEL_DIMM_FWA_ARM 695 - : ND_INTEL_DIMM_FWA_DISARM, 696 - }, 697 - }; 693 + ) nd_cmd; 698 694 int rc; 695 + 696 + nd_cmd.pkg = (struct nd_cmd_pkg) { 697 + .nd_command = NVDIMM_INTEL_FW_ACTIVATE_ARM, 698 + .nd_family = NVDIMM_FAMILY_INTEL, 699 + .nd_size_in = sizeof(nd_cmd.cmd.activate_arm), 700 + .nd_size_out = sizeof(struct nd_intel_fw_activate_arm), 701 + .nd_fw_size = sizeof(struct nd_intel_fw_activate_arm), 702 + }; 703 + nd_cmd.cmd = (struct nd_intel_fw_activate_arm) { 704 + .activate_arm = arm == NVDIMM_FWA_ARM ? 705 + ND_INTEL_DIMM_FWA_ARM : 706 + ND_INTEL_DIMM_FWA_DISARM, 707 + }; 699 708 700 709 switch (intel_fwa_state(nvdimm)) { 701 710 case NVDIMM_FWA_INVALID:
+1 -1
drivers/clocksource/timer-orion.c
··· 43 43 .read_current_timer = orion_read_timer, 44 44 }; 45 45 46 - static void orion_delay_timer_init(unsigned long rate) 46 + static void __init orion_delay_timer_init(unsigned long rate) 47 47 { 48 48 orion_delay_timer.freq = rate; 49 49 register_current_timer_delay(&orion_delay_timer);
+4 -4
drivers/firmware/efi/libstub/Makefile
··· 22 22 23 23 # arm64 uses the full KBUILD_CFLAGS so it's necessary to explicitly 24 24 # disable the stackleak plugin 25 - cflags-$(CONFIG_ARM64) += -fpie $(DISABLE_STACKLEAK_PLUGIN) \ 25 + cflags-$(CONFIG_ARM64) += -fpie $(DISABLE_KSTACK_ERASE) \ 26 26 -fno-unwind-tables -fno-asynchronous-unwind-tables 27 27 cflags-$(CONFIG_ARM) += -DEFI_HAVE_STRLEN -DEFI_HAVE_STRNLEN \ 28 28 -DEFI_HAVE_MEMCHR -DEFI_HAVE_STRRCHR \ 29 29 -DEFI_HAVE_STRCMP -fno-builtin -fpic \ 30 30 $(call cc-option,-mno-single-pic-base) \ 31 - $(DISABLE_STACKLEAK_PLUGIN) 31 + $(DISABLE_KSTACK_ERASE) 32 32 cflags-$(CONFIG_RISCV) += -fpic -DNO_ALTERNATIVE -mno-relax \ 33 - $(DISABLE_STACKLEAK_PLUGIN) 34 - cflags-$(CONFIG_LOONGARCH) += -fpie $(DISABLE_STACKLEAK_PLUGIN) 33 + $(DISABLE_KSTACK_ERASE) 34 + cflags-$(CONFIG_LOONGARCH) += -fpie $(DISABLE_KSTACK_ERASE) 35 35 36 36 cflags-$(CONFIG_EFI_PARAMS_FROM_FDT) += -I$(srctree)/scripts/dtc/libfdt 37 37
+1 -1
drivers/misc/lkdtm/Makefile
··· 8 8 lkdtm-$(CONFIG_LKDTM) += refcount.o 9 9 lkdtm-$(CONFIG_LKDTM) += rodata_objcopy.o 10 10 lkdtm-$(CONFIG_LKDTM) += usercopy.o 11 - lkdtm-$(CONFIG_LKDTM) += stackleak.o 11 + lkdtm-$(CONFIG_LKDTM) += kstack_erase.o 12 12 lkdtm-$(CONFIG_LKDTM) += cfi.o 13 13 lkdtm-$(CONFIG_LKDTM) += fortify.o 14 14 lkdtm-$(CONFIG_PPC_64S_HASH_MMU) += powerpc.o
+13 -13
drivers/misc/lkdtm/stackleak.c drivers/misc/lkdtm/kstack_erase.c
··· 1 1 // SPDX-License-Identifier: GPL-2.0 2 2 /* 3 3 * This code tests that the current task stack is properly erased (filled 4 - * with STACKLEAK_POISON). 4 + * with KSTACK_ERASE_POISON). 5 5 * 6 6 * Authors: 7 7 * Alexander Popov <alex.popov@linux.com> ··· 9 9 */ 10 10 11 11 #include "lkdtm.h" 12 - #include <linux/stackleak.h> 12 + #include <linux/kstack_erase.h> 13 13 14 - #if defined(CONFIG_GCC_PLUGIN_STACKLEAK) 14 + #if defined(CONFIG_KSTACK_ERASE) 15 15 /* 16 16 * Check that stackleak tracks the lowest stack pointer and erases the stack 17 17 * below this as expected. ··· 85 85 while (poison_low > task_stack_low) { 86 86 poison_low -= sizeof(unsigned long); 87 87 88 - if (*(unsigned long *)poison_low == STACKLEAK_POISON) 88 + if (*(unsigned long *)poison_low == KSTACK_ERASE_POISON) 89 89 continue; 90 90 91 91 instrumentation_begin(); ··· 96 96 } 97 97 98 98 instrumentation_begin(); 99 - pr_info("stackleak stack usage:\n" 99 + pr_info("kstack erase stack usage:\n" 100 100 " high offset: %lu bytes\n" 101 101 " current: %lu bytes\n" 102 102 " lowest: %lu bytes\n" ··· 121 121 instrumentation_end(); 122 122 } 123 123 124 - static void lkdtm_STACKLEAK_ERASING(void) 124 + static void lkdtm_KSTACK_ERASE(void) 125 125 { 126 126 unsigned long flags; 127 127 ··· 129 129 check_stackleak_irqoff(); 130 130 local_irq_restore(flags); 131 131 } 132 - #else /* defined(CONFIG_GCC_PLUGIN_STACKLEAK) */ 133 - static void lkdtm_STACKLEAK_ERASING(void) 132 + #else /* defined(CONFIG_KSTACK_ERASE) */ 133 + static void lkdtm_KSTACK_ERASE(void) 134 134 { 135 - if (IS_ENABLED(CONFIG_HAVE_ARCH_STACKLEAK)) { 136 - pr_err("XFAIL: stackleak is not enabled (CONFIG_GCC_PLUGIN_STACKLEAK=n)\n"); 135 + if (IS_ENABLED(CONFIG_HAVE_ARCH_KSTACK_ERASE)) { 136 + pr_err("XFAIL: stackleak is not enabled (CONFIG_KSTACK_ERASE=n)\n"); 137 137 } else { 138 - pr_err("XFAIL: stackleak is not supported on this arch (HAVE_ARCH_STACKLEAK=n)\n"); 138 + pr_err("XFAIL: stackleak is not supported on this arch (HAVE_ARCH_KSTACK_ERASE=n)\n"); 139 139 } 140 140 } 141 - #endif /* defined(CONFIG_GCC_PLUGIN_STACKLEAK) */ 141 + #endif /* defined(CONFIG_KSTACK_ERASE) */ 142 142 143 143 static struct crashtype crashtypes[] = { 144 - CRASHTYPE(STACKLEAK_ERASING), 144 + CRASHTYPE(KSTACK_ERASE), 145 145 }; 146 146 147 147 struct crashtype_category stackleak_crashtypes = {
+3 -4
drivers/mux/core.c
··· 98 98 if (WARN_ON(!dev || !controllers)) 99 99 return ERR_PTR(-EINVAL); 100 100 101 - mux_chip = kzalloc(sizeof(*mux_chip) + 102 - controllers * sizeof(*mux_chip->mux) + 103 - sizeof_priv, GFP_KERNEL); 101 + mux_chip = kzalloc(size_add(struct_size(mux_chip, mux, controllers), 102 + sizeof_priv), 103 + GFP_KERNEL); 104 104 if (!mux_chip) 105 105 return ERR_PTR(-ENOMEM); 106 106 107 - mux_chip->mux = (struct mux_control *)(mux_chip + 1); 108 107 mux_chip->dev.class = &mux_class; 109 108 mux_chip->dev.type = &mux_type; 110 109 mux_chip->dev.parent = dev;
+1 -1
drivers/soc/ti/pm33xx.c
··· 145 145 return pm_ops->cpu_suspend(am33xx_do_wfi_sram, wfi_flags); 146 146 } 147 147 148 - static int __init am43xx_map_gic(void) 148 + static int am43xx_map_gic(void) 149 149 { 150 150 gic_dist_base = ioremap(AM43XX_GIC_DIST_BASE, SZ_4K); 151 151
+3 -3
fs/proc/base.c
··· 3290 3290 } 3291 3291 #endif /* CONFIG_KSM */ 3292 3292 3293 - #ifdef CONFIG_STACKLEAK_METRICS 3293 + #ifdef CONFIG_KSTACK_ERASE_METRICS 3294 3294 static int proc_stack_depth(struct seq_file *m, struct pid_namespace *ns, 3295 3295 struct pid *pid, struct task_struct *task) 3296 3296 { ··· 3303 3303 prev_depth, depth); 3304 3304 return 0; 3305 3305 } 3306 - #endif /* CONFIG_STACKLEAK_METRICS */ 3306 + #endif /* CONFIG_KSTACK_ERASE_METRICS */ 3307 3307 3308 3308 /* 3309 3309 * Thread groups ··· 3410 3410 #ifdef CONFIG_LIVEPATCH 3411 3411 ONE("patch_state", S_IRUSR, proc_pid_patch_state), 3412 3412 #endif 3413 - #ifdef CONFIG_STACKLEAK_METRICS 3413 + #ifdef CONFIG_KSTACK_ERASE_METRICS 3414 3414 ONE("stack_depth", S_IRUGO, proc_stack_depth), 3415 3415 #endif 3416 3416 #ifdef CONFIG_PROC_PID_ARCH_STATUS
+2 -2
include/linux/acpi.h
··· 759 759 #endif 760 760 761 761 #ifndef ACPI_HAVE_ARCH_SET_ROOT_POINTER 762 - static inline void acpi_arch_set_root_pointer(u64 addr) 762 + static __always_inline void acpi_arch_set_root_pointer(u64 addr) 763 763 { 764 764 } 765 765 #endif 766 766 767 767 #ifndef ACPI_HAVE_ARCH_GET_ROOT_POINTER 768 - static inline u64 acpi_arch_get_root_pointer(void) 768 + static __always_inline u64 acpi_arch_get_root_pointer(void) 769 769 { 770 770 return 0; 771 771 }
+1 -1
include/linux/bootconfig.h
··· 290 290 /* XBC cleanup data structures */ 291 291 void __init _xbc_exit(bool early); 292 292 293 - static inline void xbc_exit(void) 293 + static __always_inline void xbc_exit(void) 294 294 { 295 295 _xbc_exit(false); 296 296 }
+1 -1
include/linux/efi.h
··· 1334 1334 1335 1335 bool xen_efi_config_table_is_usable(const efi_guid_t *guid, unsigned long table); 1336 1336 1337 - static inline 1337 + static __always_inline 1338 1338 bool efi_config_table_is_usable(const efi_guid_t *guid, unsigned long table) 1339 1339 { 1340 1340 if (!IS_ENABLED(CONFIG_XEN_EFI))
+3 -1
include/linux/init.h
··· 49 49 50 50 /* These are for everybody (although not all archs will actually 51 51 discard it in modules) */ 52 - #define __init __section(".init.text") __cold __latent_entropy __noinitretpoline 52 + #define __init __section(".init.text") __cold __latent_entropy \ 53 + __noinitretpoline \ 54 + __no_sanitize_coverage 53 55 #define __initdata __section(".init.data") 54 56 #define __initconst __section(".init.rodata") 55 57 #define __exitdata __section(".exit.data")
+1 -1
include/linux/memblock.h
··· 463 463 NUMA_NO_NODE); 464 464 } 465 465 466 - static inline void *memblock_alloc_from(phys_addr_t size, 466 + static __always_inline void *memblock_alloc_from(phys_addr_t size, 467 467 phys_addr_t align, 468 468 phys_addr_t min_addr) 469 469 {
+1 -1
include/linux/mfd/dbx500-prcmu.h
··· 213 213 214 214 #if defined(CONFIG_UX500_SOC_DB8500) 215 215 216 - static inline void prcmu_early_init(void) 216 + static inline void __init prcmu_early_init(void) 217 217 { 218 218 db8500_prcmu_early_init(); 219 219 }
+2 -2
include/linux/mux/driver.h
··· 56 56 /** 57 57 * struct mux_chip - Represents a chip holding mux controllers. 58 58 * @controllers: Number of mux controllers handled by the chip. 59 - * @mux: Array of mux controllers that are handled. 60 59 * @dev: Device structure. 61 60 * @id: Used to identify the device internally. 62 61 * @ops: Mux controller operations. 62 + * @mux: Array of mux controllers that are handled. 63 63 */ 64 64 struct mux_chip { 65 65 unsigned int controllers; 66 - struct mux_control *mux; 67 66 struct device dev; 68 67 int id; 69 68 70 69 const struct mux_control_ops *ops; 70 + struct mux_control mux[] __counted_by(controllers); 71 71 }; 72 72 73 73 #define to_mux_chip(x) container_of((x), struct mux_chip, dev)
+3 -1
include/linux/sched.h
··· 1603 1603 /* Used by BPF for per-TASK xdp storage */ 1604 1604 struct bpf_net_context *bpf_net_context; 1605 1605 1606 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 1606 + #ifdef CONFIG_KSTACK_ERASE 1607 1607 unsigned long lowest_stack; 1608 + #endif 1609 + #ifdef CONFIG_KSTACK_ERASE_METRICS 1608 1610 unsigned long prev_lowest_stack; 1609 1611 #endif 1610 1612
+1 -1
include/linux/sched/task_stack.h
··· 53 53 * When the stack grows up, this is the highest address. 54 54 * Beyond that position, we corrupt data on the next page. 55 55 */ 56 - static inline unsigned long *end_of_stack(struct task_struct *p) 56 + static inline unsigned long *end_of_stack(const struct task_struct *p) 57 57 { 58 58 #ifdef CONFIG_STACK_GROWSUP 59 59 return (unsigned long *)((unsigned long)task_thread_info(p) + THREAD_SIZE) - 1;
+1 -1
include/linux/smp.h
··· 221 221 222 222 #ifdef CONFIG_UP_LATE_INIT 223 223 extern void __init up_late_init(void); 224 - static inline void smp_init(void) { up_late_init(); } 224 + static __always_inline void smp_init(void) { up_late_init(); } 225 225 #else 226 226 static inline void smp_init(void) { } 227 227 #endif
+10 -10
include/linux/stackleak.h include/linux/kstack_erase.h
··· 1 1 /* SPDX-License-Identifier: GPL-2.0 */ 2 - #ifndef _LINUX_STACKLEAK_H 3 - #define _LINUX_STACKLEAK_H 2 + #ifndef _LINUX_KSTACK_ERASE_H 3 + #define _LINUX_KSTACK_ERASE_H 4 4 5 5 #include <linux/sched.h> 6 6 #include <linux/sched/task_stack.h> ··· 9 9 * Check that the poison value points to the unused hole in the 10 10 * virtual memory map for your platform. 11 11 */ 12 - #define STACKLEAK_POISON -0xBEEF 13 - #define STACKLEAK_SEARCH_DEPTH 128 12 + #define KSTACK_ERASE_POISON -0xBEEF 13 + #define KSTACK_ERASE_SEARCH_DEPTH 128 14 14 15 - #ifdef CONFIG_GCC_PLUGIN_STACKLEAK 15 + #ifdef CONFIG_KSTACK_ERASE 16 16 #include <asm/stacktrace.h> 17 17 #include <linux/linkage.h> 18 18 ··· 50 50 static __always_inline unsigned long 51 51 stackleak_find_top_of_poison(const unsigned long low, const unsigned long high) 52 52 { 53 - const unsigned int depth = STACKLEAK_SEARCH_DEPTH / sizeof(unsigned long); 53 + const unsigned int depth = KSTACK_ERASE_SEARCH_DEPTH / sizeof(unsigned long); 54 54 unsigned int poison_count = 0; 55 55 unsigned long poison_high = high; 56 56 unsigned long sp = high; ··· 58 58 while (sp > low && poison_count < depth) { 59 59 sp -= sizeof(unsigned long); 60 60 61 - if (*(unsigned long *)sp == STACKLEAK_POISON) { 61 + if (*(unsigned long *)sp == KSTACK_ERASE_POISON) { 62 62 poison_count++; 63 63 } else { 64 64 poison_count = 0; ··· 72 72 static inline void stackleak_task_init(struct task_struct *t) 73 73 { 74 74 t->lowest_stack = stackleak_task_low_bound(t); 75 - # ifdef CONFIG_STACKLEAK_METRICS 75 + # ifdef CONFIG_KSTACK_ERASE_METRICS 76 76 t->prev_lowest_stack = t->lowest_stack; 77 77 # endif 78 78 } ··· 80 80 asmlinkage void noinstr stackleak_erase(void); 81 81 asmlinkage void noinstr stackleak_erase_on_task_stack(void); 82 82 asmlinkage void noinstr stackleak_erase_off_task_stack(void); 83 - void __no_caller_saved_registers noinstr stackleak_track_stack(void); 83 + void __no_caller_saved_registers noinstr __sanitizer_cov_stack_depth(void); 84 84 85 - #else /* !CONFIG_GCC_PLUGIN_STACKLEAK */ 85 + #else /* !CONFIG_KSTACK_ERASE */ 86 86 static inline void stackleak_task_init(struct task_struct *t) { } 87 87 #endif 88 88
+20
include/linux/stddef.h
··· 93 93 #define DECLARE_FLEX_ARRAY(TYPE, NAME) \ 94 94 __DECLARE_FLEX_ARRAY(TYPE, NAME) 95 95 96 + /** 97 + * TRAILING_OVERLAP() - Overlap a flexible-array member with trailing members. 98 + * 99 + * Creates a union between a flexible-array member (FAM) in a struct and a set 100 + * of additional members that would otherwise follow it. 101 + * 102 + * @TYPE: Flexible structure type name, including "struct" keyword. 103 + * @NAME: Name for a variable to define. 104 + * @FAM: The flexible-array member within @TYPE 105 + * @MEMBERS: Trailing overlapping members. 106 + */ 107 + #define TRAILING_OVERLAP(TYPE, NAME, FAM, MEMBERS) \ 108 + union { \ 109 + TYPE NAME; \ 110 + struct { \ 111 + unsigned char __offset_to_##FAM[offsetof(TYPE, FAM)]; \ 112 + MEMBERS \ 113 + }; \ 114 + } 115 + 96 116 #endif
+10 -10
include/linux/string.h
··· 345 345 346 346 int ptr_to_hashval(const void *ptr, unsigned long *hashval_out); 347 347 348 - /** 349 - * strstarts - does @str start with @prefix? 350 - * @str: string to examine 351 - * @prefix: prefix to look for. 352 - */ 353 - static inline bool strstarts(const char *str, const char *prefix) 354 - { 355 - return strncmp(str, prefix, strlen(prefix)) == 0; 356 - } 357 - 358 348 size_t memweight(const void *ptr, size_t bytes); 359 349 360 350 /** ··· 550 560 { 551 561 size_t len = strlen(prefix); 552 562 return strncmp(str, prefix, len) == 0 ? len : 0; 563 + } 564 + 565 + /** 566 + * strstarts - does @str start with @prefix? 567 + * @str: string to examine 568 + * @prefix: prefix to look for. 569 + */ 570 + static inline bool strstarts(const char *str, const char *prefix) 571 + { 572 + return strncmp(str, prefix, strlen(prefix)) == 0; 553 573 } 554 574 555 575 #endif /* _LINUX_STRING_H_ */
+6 -5
kernel/Makefile
··· 139 139 obj-$(CONFIG_RESOURCE_KUNIT_TEST) += resource_kunit.o 140 140 obj-$(CONFIG_SYSCTL_KUNIT_TEST) += sysctl-test.o 141 141 142 - CFLAGS_stackleak.o += $(DISABLE_STACKLEAK_PLUGIN) 143 - obj-$(CONFIG_GCC_PLUGIN_STACKLEAK) += stackleak.o 144 - KASAN_SANITIZE_stackleak.o := n 145 - KCSAN_SANITIZE_stackleak.o := n 146 - KCOV_INSTRUMENT_stackleak.o := n 142 + CFLAGS_kstack_erase.o += $(DISABLE_KSTACK_ERASE) 143 + CFLAGS_kstack_erase.o += $(call cc-option,-mgeneral-regs-only) 144 + obj-$(CONFIG_KSTACK_ERASE) += kstack_erase.o 145 + KASAN_SANITIZE_kstack_erase.o := n 146 + KCSAN_SANITIZE_kstack_erase.o := n 147 + KCOV_INSTRUMENT_kstack_erase.o := n 147 148 148 149 obj-$(CONFIG_SCF_TORTURE_TEST) += scftorture.o 149 150
+6
kernel/configs/hardening.config
··· 60 60 # Initialize all heap variables to zero on allocation. 61 61 CONFIG_INIT_ON_ALLOC_DEFAULT_ON=y 62 62 63 + # Initialize all heap variables to zero on free to reduce stale data lifetime. 64 + CONFIG_INIT_ON_FREE_DEFAULT_ON=y 65 + 63 66 # Initialize all stack variables to zero on function entry. 64 67 CONFIG_INIT_STACK_ALL_ZERO=y 68 + 69 + # Wipe kernel stack after syscall completion to reduce stale data lifetime. 70 + CONFIG_KSTACK_ERASE=y 65 71 66 72 # Wipe RAM at reboot via EFI. For more details, see: 67 73 # https://trustedcomputinggroup.org/resource/pc-client-work-group-platform-reset-attack-mitigation-specification/
+1 -1
kernel/fork.c
··· 93 93 #include <linux/kcov.h> 94 94 #include <linux/livepatch.h> 95 95 #include <linux/thread_info.h> 96 - #include <linux/stackleak.h> 96 + #include <linux/kstack_erase.h> 97 97 #include <linux/kasan.h> 98 98 #include <linux/scs.h> 99 99 #include <linux/io_uring.h>
+2 -2
kernel/kexec_handover.c
··· 310 310 return -ENOMEM; 311 311 } 312 312 313 - static void deserialize_bitmap(unsigned int order, 314 - struct khoser_mem_bitmap_ptr *elm) 313 + static void __init deserialize_bitmap(unsigned int order, 314 + struct khoser_mem_bitmap_ptr *elm) 315 315 { 316 316 struct kho_mem_phys_bits *bitmap = KHOSER_LOAD_PTR(elm->bitmap); 317 317 unsigned long bit;
+11 -11
kernel/stackleak.c kernel/kstack_erase.c
··· 6 6 * 7 7 * Author: Alexander Popov <alex.popov@linux.com> 8 8 * 9 - * STACKLEAK reduces the information which kernel stack leak bugs can 9 + * KSTACK_ERASE reduces the information which kernel stack leak bugs can 10 10 * reveal and blocks some uninitialized stack variable attacks. 11 11 */ 12 12 13 - #include <linux/stackleak.h> 13 + #include <linux/kstack_erase.h> 14 14 #include <linux/kprobes.h> 15 15 16 - #ifdef CONFIG_STACKLEAK_RUNTIME_DISABLE 16 + #ifdef CONFIG_KSTACK_ERASE_RUNTIME_DISABLE 17 17 #include <linux/jump_label.h> 18 18 #include <linux/string_choices.h> 19 19 #include <linux/sysctl.h> ··· 68 68 #define skip_erasing() static_branch_unlikely(&stack_erasing_bypass) 69 69 #else 70 70 #define skip_erasing() false 71 - #endif /* CONFIG_STACKLEAK_RUNTIME_DISABLE */ 71 + #endif /* CONFIG_KSTACK_ERASE_RUNTIME_DISABLE */ 72 72 73 73 #ifndef __stackleak_poison 74 74 static __always_inline void __stackleak_poison(unsigned long erase_low, ··· 91 91 erase_low = stackleak_find_top_of_poison(task_stack_low, 92 92 current->lowest_stack); 93 93 94 - #ifdef CONFIG_STACKLEAK_METRICS 94 + #ifdef CONFIG_KSTACK_ERASE_METRICS 95 95 current->prev_lowest_stack = erase_low; 96 96 #endif 97 97 ··· 113 113 else 114 114 erase_high = task_stack_high; 115 115 116 - __stackleak_poison(erase_low, erase_high, STACKLEAK_POISON); 116 + __stackleak_poison(erase_low, erase_high, KSTACK_ERASE_POISON); 117 117 118 118 /* Reset the 'lowest_stack' value for the next syscall */ 119 119 current->lowest_stack = task_stack_high; ··· 156 156 __stackleak_erase(false); 157 157 } 158 158 159 - void __used __no_caller_saved_registers noinstr stackleak_track_stack(void) 159 + void __used __no_caller_saved_registers noinstr __sanitizer_cov_stack_depth(void) 160 160 { 161 161 unsigned long sp = current_stack_pointer; 162 162 163 163 /* 164 - * Having CONFIG_STACKLEAK_TRACK_MIN_SIZE larger than 165 - * STACKLEAK_SEARCH_DEPTH makes the poison search in 164 + * Having CONFIG_KSTACK_ERASE_TRACK_MIN_SIZE larger than 165 + * KSTACK_ERASE_SEARCH_DEPTH makes the poison search in 166 166 * stackleak_erase() unreliable. Let's prevent that. 167 167 */ 168 - BUILD_BUG_ON(CONFIG_STACKLEAK_TRACK_MIN_SIZE > STACKLEAK_SEARCH_DEPTH); 168 + BUILD_BUG_ON(CONFIG_KSTACK_ERASE_TRACK_MIN_SIZE > KSTACK_ERASE_SEARCH_DEPTH); 169 169 170 170 /* 'lowest_stack' should be aligned on the register width boundary */ 171 171 sp = ALIGN(sp, sizeof(unsigned long)); ··· 174 174 current->lowest_stack = sp; 175 175 } 176 176 } 177 - EXPORT_SYMBOL(stackleak_track_stack); 177 + EXPORT_SYMBOL(__sanitizer_cov_stack_depth);
+9
lib/Kconfig.debug
··· 2460 2460 2461 2461 If unsure, say N. 2462 2462 2463 + config SEQ_BUF_KUNIT_TEST 2464 + tristate "KUnit test for seq_buf" if !KUNIT_ALL_TESTS 2465 + depends on KUNIT 2466 + default KUNIT_ALL_TESTS 2467 + help 2468 + This builds unit tests for the seq_buf library. 2469 + 2470 + If unsure, say N. 2471 + 2463 2472 config STRING_KUNIT_TEST 2464 2473 tristate "KUnit test string functions at runtime" if !KUNIT_ALL_TESTS 2465 2474 depends on KUNIT
+1 -1
lib/Makefile
··· 337 337 UBSAN_SANITIZE_ubsan.o := n 338 338 KASAN_SANITIZE_ubsan.o := n 339 339 KCSAN_SANITIZE_ubsan.o := n 340 - CFLAGS_ubsan.o := -fno-stack-protector $(DISABLE_STACKLEAK_PLUGIN) 340 + CFLAGS_ubsan.o := -fno-stack-protector $(DISABLE_KSTACK_ERASE) 341 341 342 342 obj-$(CONFIG_SBITMAP) += sbitmap.o 343 343
+1
lib/tests/Makefile
··· 37 37 obj-$(CONFIG_PRINTF_KUNIT_TEST) += printf_kunit.o 38 38 obj-$(CONFIG_RANDSTRUCT_KUNIT_TEST) += randstruct_kunit.o 39 39 obj-$(CONFIG_SCANF_KUNIT_TEST) += scanf_kunit.o 40 + obj-$(CONFIG_SEQ_BUF_KUNIT_TEST) += seq_buf_kunit.o 40 41 obj-$(CONFIG_SIPHASH_KUNIT_TEST) += siphash_kunit.o 41 42 obj-$(CONFIG_SLUB_KUNIT_TEST) += slub_kunit.o 42 43 obj-$(CONFIG_TEST_SORT) += test_sort.o
+2 -2
lib/tests/fortify_kunit.c
··· 1003 1003 { 1004 1004 char one[] = "My mind is going ..."; 1005 1005 char two[] = "My mind is going ... I can feel it."; 1006 - size_t one_len = sizeof(one) - 1; 1007 - size_t two_len = sizeof(two) - 1; 1006 + volatile size_t one_len = sizeof(one) - 1; 1007 + volatile size_t two_len = sizeof(two) - 1; 1008 1008 1009 1009 OPTIMIZER_HIDE_VAR(one_len); 1010 1010 OPTIMIZER_HIDE_VAR(two_len);
+208
lib/tests/seq_buf_kunit.c
··· 1 + // SPDX-License-Identifier: GPL-2.0 2 + /* 3 + * KUnit tests for the seq_buf API 4 + * 5 + * Copyright (C) 2025, Google LLC. 6 + */ 7 + 8 + #include <kunit/test.h> 9 + #include <linux/seq_buf.h> 10 + 11 + static void seq_buf_init_test(struct kunit *test) 12 + { 13 + char buf[32]; 14 + struct seq_buf s; 15 + 16 + seq_buf_init(&s, buf, sizeof(buf)); 17 + 18 + KUNIT_EXPECT_EQ(test, s.size, 32); 19 + KUNIT_EXPECT_EQ(test, s.len, 0); 20 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 21 + KUNIT_EXPECT_EQ(test, seq_buf_buffer_left(&s), 32); 22 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 0); 23 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), ""); 24 + } 25 + 26 + static void seq_buf_declare_test(struct kunit *test) 27 + { 28 + DECLARE_SEQ_BUF(s, 24); 29 + 30 + KUNIT_EXPECT_EQ(test, s.size, 24); 31 + KUNIT_EXPECT_EQ(test, s.len, 0); 32 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 33 + KUNIT_EXPECT_EQ(test, seq_buf_buffer_left(&s), 24); 34 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 0); 35 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), ""); 36 + } 37 + 38 + static void seq_buf_clear_test(struct kunit *test) 39 + { 40 + DECLARE_SEQ_BUF(s, 128); 41 + 42 + seq_buf_puts(&s, "hello"); 43 + KUNIT_EXPECT_EQ(test, s.len, 5); 44 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 45 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello"); 46 + 47 + seq_buf_clear(&s); 48 + 49 + KUNIT_EXPECT_EQ(test, s.len, 0); 50 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 51 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), ""); 52 + } 53 + 54 + static void seq_buf_puts_test(struct kunit *test) 55 + { 56 + DECLARE_SEQ_BUF(s, 16); 57 + 58 + seq_buf_puts(&s, "hello"); 59 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 5); 60 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 61 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello"); 62 + 63 + seq_buf_puts(&s, " world"); 64 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 11); 65 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 66 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello world"); 67 + } 68 + 69 + static void seq_buf_puts_overflow_test(struct kunit *test) 70 + { 71 + DECLARE_SEQ_BUF(s, 10); 72 + 73 + seq_buf_puts(&s, "123456789"); 74 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 75 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 9); 76 + 77 + seq_buf_puts(&s, "0"); 78 + KUNIT_EXPECT_TRUE(test, seq_buf_has_overflowed(&s)); 79 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 10); 80 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "123456789"); 81 + 82 + seq_buf_clear(&s); 83 + KUNIT_EXPECT_EQ(test, s.len, 0); 84 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 85 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), ""); 86 + } 87 + 88 + static void seq_buf_putc_test(struct kunit *test) 89 + { 90 + DECLARE_SEQ_BUF(s, 4); 91 + 92 + seq_buf_putc(&s, 'a'); 93 + seq_buf_putc(&s, 'b'); 94 + seq_buf_putc(&s, 'c'); 95 + 96 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 3); 97 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 98 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "abc"); 99 + 100 + seq_buf_putc(&s, 'd'); 101 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 4); 102 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 103 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "abc"); 104 + 105 + seq_buf_putc(&s, 'e'); 106 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 4); 107 + KUNIT_EXPECT_TRUE(test, seq_buf_has_overflowed(&s)); 108 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "abc"); 109 + 110 + seq_buf_clear(&s); 111 + KUNIT_EXPECT_EQ(test, s.len, 0); 112 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 113 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), ""); 114 + } 115 + 116 + static void seq_buf_printf_test(struct kunit *test) 117 + { 118 + DECLARE_SEQ_BUF(s, 32); 119 + 120 + seq_buf_printf(&s, "hello %s", "world"); 121 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 11); 122 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 123 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello world"); 124 + 125 + seq_buf_printf(&s, " %d", 123); 126 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 15); 127 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 128 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello world 123"); 129 + } 130 + 131 + static void seq_buf_printf_overflow_test(struct kunit *test) 132 + { 133 + DECLARE_SEQ_BUF(s, 16); 134 + 135 + seq_buf_printf(&s, "%lu", 1234567890UL); 136 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 137 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 10); 138 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "1234567890"); 139 + 140 + seq_buf_printf(&s, "%s", "abcdefghij"); 141 + KUNIT_EXPECT_TRUE(test, seq_buf_has_overflowed(&s)); 142 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 16); 143 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "1234567890abcde"); 144 + 145 + seq_buf_clear(&s); 146 + KUNIT_EXPECT_EQ(test, s.len, 0); 147 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 148 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), ""); 149 + } 150 + 151 + static void seq_buf_get_buf_commit_test(struct kunit *test) 152 + { 153 + DECLARE_SEQ_BUF(s, 16); 154 + char *buf; 155 + size_t len; 156 + 157 + len = seq_buf_get_buf(&s, &buf); 158 + KUNIT_EXPECT_EQ(test, len, 16); 159 + KUNIT_EXPECT_PTR_NE(test, buf, NULL); 160 + 161 + memcpy(buf, "hello", 5); 162 + seq_buf_commit(&s, 5); 163 + 164 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 5); 165 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 166 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello"); 167 + 168 + len = seq_buf_get_buf(&s, &buf); 169 + KUNIT_EXPECT_EQ(test, len, 11); 170 + KUNIT_EXPECT_PTR_NE(test, buf, NULL); 171 + 172 + memcpy(buf, " worlds!", 8); 173 + seq_buf_commit(&s, 6); 174 + 175 + KUNIT_EXPECT_EQ(test, seq_buf_used(&s), 11); 176 + KUNIT_EXPECT_FALSE(test, seq_buf_has_overflowed(&s)); 177 + KUNIT_EXPECT_STREQ(test, seq_buf_str(&s), "hello world"); 178 + 179 + len = seq_buf_get_buf(&s, &buf); 180 + KUNIT_EXPECT_EQ(test, len, 5); 181 + KUNIT_EXPECT_PTR_NE(test, buf, NULL); 182 + 183 + seq_buf_commit(&s, -1); 184 + KUNIT_EXPECT_TRUE(test, seq_buf_has_overflowed(&s)); 185 + } 186 + 187 + static struct kunit_case seq_buf_test_cases[] = { 188 + KUNIT_CASE(seq_buf_init_test), 189 + KUNIT_CASE(seq_buf_declare_test), 190 + KUNIT_CASE(seq_buf_clear_test), 191 + KUNIT_CASE(seq_buf_puts_test), 192 + KUNIT_CASE(seq_buf_puts_overflow_test), 193 + KUNIT_CASE(seq_buf_putc_test), 194 + KUNIT_CASE(seq_buf_printf_test), 195 + KUNIT_CASE(seq_buf_printf_overflow_test), 196 + KUNIT_CASE(seq_buf_get_buf_commit_test), 197 + {} 198 + }; 199 + 200 + static struct kunit_suite seq_buf_test_suite = { 201 + .name = "seq_buf", 202 + .test_cases = seq_buf_test_cases, 203 + }; 204 + 205 + kunit_test_suite(seq_buf_test_suite); 206 + 207 + MODULE_DESCRIPTION("Runtime test cases for seq_buf string API"); 208 + MODULE_LICENSE("GPL");
+2 -14
scripts/Makefile.gcc-plugins
··· 8 8 endif 9 9 export DISABLE_LATENT_ENTROPY_PLUGIN 10 10 11 - gcc-plugin-$(CONFIG_GCC_PLUGIN_STACKLEAK) += stackleak_plugin.so 12 - gcc-plugin-cflags-$(CONFIG_GCC_PLUGIN_STACKLEAK) \ 13 - += -DSTACKLEAK_PLUGIN 14 - gcc-plugin-cflags-$(CONFIG_GCC_PLUGIN_STACKLEAK) \ 15 - += -fplugin-arg-stackleak_plugin-track-min-size=$(CONFIG_STACKLEAK_TRACK_MIN_SIZE) 16 - gcc-plugin-cflags-$(CONFIG_GCC_PLUGIN_STACKLEAK) \ 17 - += -fplugin-arg-stackleak_plugin-arch=$(SRCARCH) 18 - gcc-plugin-cflags-$(CONFIG_GCC_PLUGIN_STACKLEAK_VERBOSE) \ 19 - += -fplugin-arg-stackleak_plugin-verbose 20 - ifdef CONFIG_GCC_PLUGIN_STACKLEAK 21 - DISABLE_STACKLEAK_PLUGIN += -fplugin-arg-stackleak_plugin-disable 22 - endif 23 - export DISABLE_STACKLEAK_PLUGIN 24 - 25 11 # All the plugin CFLAGS are collected here in case a build target needs to 26 12 # filter them out of the KBUILD_CFLAGS. 27 13 GCC_PLUGINS_CFLAGS := $(strip $(addprefix -fplugin=$(objtree)/scripts/gcc-plugins/, $(gcc-plugin-y)) $(gcc-plugin-cflags-y)) -DGCC_PLUGINS ··· 20 34 # be included in GCC_PLUGIN so they can get built. 21 35 gcc-plugin-external-$(CONFIG_GCC_PLUGIN_RANDSTRUCT) \ 22 36 += randomize_layout_plugin.so 37 + gcc-plugin-external-$(CONFIG_GCC_PLUGIN_STACKLEAK) \ 38 + += stackleak_plugin.so 23 39 24 40 # All enabled GCC plugins are collected here for building in 25 41 # scripts/gcc-scripts/Makefile.
+21
scripts/Makefile.kstack_erase
··· 1 + # SPDX-License-Identifier: GPL-2.0 2 + 3 + ifdef CONFIG_GCC_PLUGIN_STACKLEAK 4 + kstack-erase-cflags-y += -fplugin=$(objtree)/scripts/gcc-plugins/stackleak_plugin.so 5 + kstack-erase-cflags-y += -fplugin-arg-stackleak_plugin-track-min-size=$(CONFIG_KSTACK_ERASE_TRACK_MIN_SIZE) 6 + kstack-erase-cflags-y += -fplugin-arg-stackleak_plugin-arch=$(SRCARCH) 7 + kstack-erase-cflags-$(CONFIG_GCC_PLUGIN_STACKLEAK_VERBOSE) += -fplugin-arg-stackleak_plugin-verbose 8 + DISABLE_KSTACK_ERASE := -fplugin-arg-stackleak_plugin-disable 9 + endif 10 + 11 + ifdef CONFIG_CC_IS_CLANG 12 + kstack-erase-cflags-y += -fsanitize-coverage=stack-depth 13 + kstack-erase-cflags-y += -fsanitize-coverage-stack-depth-callback-min=$(CONFIG_KSTACK_ERASE_TRACK_MIN_SIZE) 14 + DISABLE_KSTACK_ERASE := -fno-sanitize-coverage=stack-depth 15 + endif 16 + 17 + KSTACK_ERASE_CFLAGS := $(kstack-erase-cflags-y) 18 + 19 + export STACKLEAK_CFLAGS DISABLE_KSTACK_ERASE 20 + 21 + KBUILD_CFLAGS += $(KSTACK_ERASE_CFLAGS)
+26 -26
scripts/gcc-plugins/stackleak_plugin.c
··· 9 9 * any of the gcc libraries 10 10 * 11 11 * This gcc plugin is needed for tracking the lowest border of the kernel stack. 12 - * It instruments the kernel code inserting stackleak_track_stack() calls: 12 + * It instruments the kernel code inserting __sanitizer_cov_stack_depth() calls: 13 13 * - after alloca(); 14 14 * - for the functions with a stack frame size greater than or equal 15 15 * to the "track-min-size" plugin parameter. ··· 33 33 34 34 static int track_frame_size = -1; 35 35 static bool build_for_x86 = false; 36 - static const char track_function[] = "stackleak_track_stack"; 36 + static const char track_function[] = "__sanitizer_cov_stack_depth"; 37 37 static bool disable = false; 38 38 static bool verbose = false; 39 39 ··· 58 58 cgraph_node_ptr node; 59 59 basic_block bb; 60 60 61 - /* Insert calling stackleak_track_stack() */ 61 + /* Insert calling __sanitizer_cov_stack_depth() */ 62 62 stmt = gimple_build_call(track_function_decl, 0); 63 63 gimple_call = as_a_gcall(stmt); 64 64 if (after) ··· 120 120 gcc_assert(build_for_x86); 121 121 122 122 /* 123 - * Insert calling stackleak_track_stack() in asm: 124 - * asm volatile("call stackleak_track_stack" 123 + * Insert calling __sanitizer_cov_stack_depth() in asm: 124 + * asm volatile("call __sanitizer_cov_stack_depth" 125 125 * :: "r" (current_stack_pointer)) 126 126 * Use ASM_CALL_CONSTRAINT trick from arch/x86/include/asm/asm.h. 127 127 * This constraint is taken into account during gcc shrink-wrapping 128 - * optimization. It is needed to be sure that stackleak_track_stack() 128 + * optimization. It is needed to be sure that __sanitizer_cov_stack_depth() 129 129 * call is inserted after the prologue of the containing function, 130 130 * when the stack frame is prepared. 131 131 */ ··· 137 137 input = build_tree_list(NULL_TREE, build_const_char_string(2, "r")); 138 138 input = chainon(NULL_TREE, build_tree_list(input, sp_decl)); 139 139 vec_safe_push(inputs, input); 140 - asm_call = gimple_build_asm_vec("call stackleak_track_stack", 140 + asm_call = gimple_build_asm_vec("call __sanitizer_cov_stack_depth", 141 141 inputs, NULL, NULL, NULL); 142 142 gimple_asm_set_volatile(asm_call, true); 143 143 if (after) ··· 151 151 { 152 152 /* 153 153 * The 'no_caller_saved_registers' attribute is used for 154 - * stackleak_track_stack(). If the compiler supports this attribute for 155 - * the target arch, we can add calling stackleak_track_stack() in asm. 154 + * __sanitizer_cov_stack_depth(). If the compiler supports this attribute for 155 + * the target arch, we can add calling __sanitizer_cov_stack_depth() in asm. 156 156 * That improves performance: we avoid useless operations with the 157 157 * caller-saved registers in the functions from which we will remove 158 - * stackleak_track_stack() call during the stackleak_cleanup pass. 158 + * __sanitizer_cov_stack_depth() call during the stackleak_cleanup pass. 159 159 */ 160 160 if (lookup_attribute_spec(get_identifier("no_caller_saved_registers"))) 161 161 add_stack_tracking_gasm(gsi, after); ··· 165 165 166 166 /* 167 167 * Work with the GIMPLE representation of the code. Insert the 168 - * stackleak_track_stack() call after alloca() and into the beginning 168 + * __sanitizer_cov_stack_depth() call after alloca() and into the beginning 169 169 * of the function if it is not instrumented. 170 170 */ 171 171 static unsigned int stackleak_instrument_execute(void) ··· 205 205 DECL_NAME_POINTER(current_function_decl)); 206 206 } 207 207 208 - /* Insert stackleak_track_stack() call after alloca() */ 208 + /* Insert __sanitizer_cov_stack_depth() call after alloca() */ 209 209 add_stack_tracking(&gsi, true); 210 210 if (bb == entry_bb) 211 211 prologue_instrumented = true; ··· 241 241 return 0; 242 242 } 243 243 244 - /* Insert stackleak_track_stack() call at the function beginning */ 244 + /* Insert __sanitizer_cov_stack_depth() call at the function beginning */ 245 245 bb = entry_bb; 246 246 if (!single_pred_p(bb)) { 247 247 /* gcc_assert(bb_loop_depth(bb) || ··· 270 270 rtx_insn *insn, *next; 271 271 272 272 /* 273 - * Find stackleak_track_stack() calls. Loop through the chain of insns, 273 + * Find __sanitizer_cov_stack_depth() calls. Loop through the chain of insns, 274 274 * which is an RTL representation of the code for a function. 275 275 * 276 276 * The example of a matching insn: 277 - * (call_insn 8 4 10 2 (call (mem (symbol_ref ("stackleak_track_stack") 278 - * [flags 0x41] <function_decl 0x7f7cd3302a80 stackleak_track_stack>) 279 - * [0 stackleak_track_stack S1 A8]) (0)) 675 {*call} (expr_list 280 - * (symbol_ref ("stackleak_track_stack") [flags 0x41] <function_decl 281 - * 0x7f7cd3302a80 stackleak_track_stack>) (expr_list (0) (nil))) (nil)) 277 + * (call_insn 8 4 10 2 (call (mem (symbol_ref ("__sanitizer_cov_stack_depth") 278 + * [flags 0x41] <function_decl 0x7f7cd3302a80 __sanitizer_cov_stack_depth>) 279 + * [0 __sanitizer_cov_stack_depth S1 A8]) (0)) 675 {*call} (expr_list 280 + * (symbol_ref ("__sanitizer_cov_stack_depth") [flags 0x41] <function_decl 281 + * 0x7f7cd3302a80 __sanitizer_cov_stack_depth>) (expr_list (0) (nil))) (nil)) 282 282 */ 283 283 for (insn = get_insns(); insn; insn = next) { 284 284 rtx body; ··· 318 318 if (SYMBOL_REF_DECL(body) != track_function_decl) 319 319 continue; 320 320 321 - /* Delete the stackleak_track_stack() call */ 321 + /* Delete the __sanitizer_cov_stack_depth() call */ 322 322 delete_insn_and_edges(insn); 323 323 #if BUILDING_GCC_VERSION < 8000 324 324 if (GET_CODE(next) == NOTE && ··· 340 340 gcc_assert(build_for_x86); 341 341 342 342 /* 343 - * Find stackleak_track_stack() asm calls. Loop through the chain of 343 + * Find __sanitizer_cov_stack_depth() asm calls. Loop through the chain of 344 344 * insns, which is an RTL representation of the code for a function. 345 345 * 346 346 * The example of a matching insn: 347 347 * (insn 11 5 12 2 (parallel [ (asm_operands/v 348 - * ("call stackleak_track_stack") ("") 0 348 + * ("call __sanitizer_cov_stack_depth") ("") 0 349 349 * [ (reg/v:DI 7 sp [ current_stack_pointer ]) ] 350 350 * [ (asm_input:DI ("r")) ] []) 351 351 * (clobber (reg:CC 17 flags)) ]) -1 (nil)) ··· 375 375 continue; 376 376 377 377 if (strcmp(ASM_OPERANDS_TEMPLATE(body), 378 - "call stackleak_track_stack")) { 378 + "call __sanitizer_cov_stack_depth")) { 379 379 continue; 380 380 } 381 381 ··· 389 389 390 390 /* 391 391 * Work with the RTL representation of the code. 392 - * Remove the unneeded stackleak_track_stack() calls from the functions 392 + * Remove the unneeded __sanitizer_cov_stack_depth() calls from the functions 393 393 * which don't call alloca() and don't have a large enough stack frame size. 394 394 */ 395 395 static unsigned int stackleak_cleanup_execute(void) ··· 474 474 return track_frame_size >= 0; 475 475 } 476 476 477 - /* Build the function declaration for stackleak_track_stack() */ 477 + /* Build the function declaration for __sanitizer_cov_stack_depth() */ 478 478 static void stackleak_start_unit(void *gcc_data __unused, 479 479 void *user_data __unused) 480 480 { 481 481 tree fntype; 482 482 483 - /* void stackleak_track_stack(void) */ 483 + /* void __sanitizer_cov_stack_depth(void) */ 484 484 fntype = build_function_type_list(void_type_node, NULL_TREE); 485 485 track_function_decl = build_fn_decl(track_function, fntype); 486 486 DECL_ASSEMBLER_NAME(track_function_decl); /* for LTO */
+26 -19
security/Kconfig.hardening
··· 82 82 83 83 endchoice 84 84 85 - config GCC_PLUGIN_STACKLEAK 85 + config CC_HAS_SANCOV_STACK_DEPTH_CALLBACK 86 + def_bool $(cc-option,-fsanitize-coverage-stack-depth-callback-min=1) 87 + 88 + config KSTACK_ERASE 86 89 bool "Poison kernel stack before returning from syscalls" 87 - depends on GCC_PLUGINS 88 - depends on HAVE_ARCH_STACKLEAK 90 + depends on HAVE_ARCH_KSTACK_ERASE 91 + depends on GCC_PLUGINS || CC_HAS_SANCOV_STACK_DEPTH_CALLBACK 89 92 help 90 93 This option makes the kernel erase the kernel stack before 91 94 returning from system calls. This has the effect of leaving ··· 106 103 are advised to test this feature on your expected workload before 107 104 deploying it. 108 105 106 + config GCC_PLUGIN_STACKLEAK 107 + def_bool KSTACK_ERASE 108 + depends on GCC_PLUGINS 109 + help 109 110 This plugin was ported from grsecurity/PaX. More information at: 110 111 * https://grsecurity.net/ 111 112 * https://pax.grsecurity.net/ ··· 124 117 instrumented. This is useful for comparing coverage between 125 118 builds. 126 119 127 - config STACKLEAK_TRACK_MIN_SIZE 128 - int "Minimum stack frame size of functions tracked by STACKLEAK" 120 + config KSTACK_ERASE_TRACK_MIN_SIZE 121 + int "Minimum stack frame size of functions tracked by KSTACK_ERASE" 129 122 default 100 130 123 range 0 4096 131 - depends on GCC_PLUGIN_STACKLEAK 124 + depends on KSTACK_ERASE 132 125 help 133 - The STACKLEAK gcc plugin instruments the kernel code for tracking 126 + The KSTACK_ERASE option instruments the kernel code for tracking 134 127 the lowest border of the kernel stack (and for some other purposes). 135 - It inserts the stackleak_track_stack() call for the functions with 136 - a stack frame size greater than or equal to this parameter. 128 + It inserts the __sanitizer_cov_stack_depth() call for the functions 129 + with a stack frame size greater than or equal to this parameter. 137 130 If unsure, leave the default value 100. 138 131 139 - config STACKLEAK_METRICS 140 - bool "Show STACKLEAK metrics in the /proc file system" 141 - depends on GCC_PLUGIN_STACKLEAK 132 + config KSTACK_ERASE_METRICS 133 + bool "Show KSTACK_ERASE metrics in the /proc file system" 134 + depends on KSTACK_ERASE 142 135 depends on PROC_FS 143 136 help 144 - If this is set, STACKLEAK metrics for every task are available in 145 - the /proc file system. In particular, /proc/<pid>/stack_depth 137 + If this is set, KSTACK_ERASE metrics for every task are available 138 + in the /proc file system. In particular, /proc/<pid>/stack_depth 146 139 shows the maximum kernel stack consumption for the current and 147 140 previous syscalls. Although this information is not precise, it 148 - can be useful for estimating the STACKLEAK performance impact for 149 - your workloads. 141 + can be useful for estimating the KSTACK_ERASE performance impact 142 + for your workloads. 150 143 151 - config STACKLEAK_RUNTIME_DISABLE 144 + config KSTACK_ERASE_RUNTIME_DISABLE 152 145 bool "Allow runtime disabling of kernel stack erasing" 153 - depends on GCC_PLUGIN_STACKLEAK 146 + depends on KSTACK_ERASE 154 147 help 155 148 This option provides 'stack_erasing' sysctl, which can be used in 156 149 runtime to control kernel stack erasing for kernels built with 157 - CONFIG_GCC_PLUGIN_STACKLEAK. 150 + CONFIG_KSTACK_ERASE. 158 151 159 152 config INIT_ON_ALLOC_DEFAULT_ON 160 153 bool "Enable heap memory zeroing on allocation by default"
+2 -2
tools/objtool/check.c
··· 1193 1193 "__ubsan_handle_type_mismatch_v1", 1194 1194 "__ubsan_handle_shift_out_of_bounds", 1195 1195 "__ubsan_handle_load_invalid_value", 1196 - /* STACKLEAK */ 1197 - "stackleak_track_stack", 1196 + /* KSTACK_ERASE */ 1197 + "__sanitizer_cov_stack_depth", 1198 1198 /* TRACE_BRANCH_PROFILING */ 1199 1199 "ftrace_likely_update", 1200 1200 /* STACKPROTECTOR */
+1 -1
tools/testing/selftests/lkdtm/config
··· 2 2 CONFIG_DEBUG_LIST=y 3 3 CONFIG_SLAB_FREELIST_HARDENED=y 4 4 CONFIG_FORTIFY_SOURCE=y 5 - CONFIG_GCC_PLUGIN_STACKLEAK=y 5 + CONFIG_KSTACK_ERASE=y 6 6 CONFIG_HARDENED_USERCOPY=y 7 7 CONFIG_RANDOMIZE_KSTACK_OFFSET_DEFAULT=y 8 8 CONFIG_INIT_ON_FREE_DEFAULT_ON=y