summaryrefslogtreecommitdiffstats
path: root/security
diff options
context:
space:
mode:
authorAlexander Potapenko <glider@google.com>2019-07-11 23:59:19 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2019-07-12 14:05:46 -0400
commit6471384af2a6530696fc0203bafe4de41a23c9ef (patch)
treea9c8465080fa6745e4fe9311297816f564124b87 /security
parentba5c5e4a5da443e80a3722e67515de5e37375b18 (diff)
mm: security: introduce init_on_alloc=1 and init_on_free=1 boot options
Patch series "add init_on_alloc/init_on_free boot options", v10. Provide init_on_alloc and init_on_free boot options. These are aimed at preventing possible information leaks and making the control-flow bugs that depend on uninitialized values more deterministic. Enabling either of the options guarantees that the memory returned by the page allocator and SL[AU]B is initialized with zeroes. SLOB allocator isn't supported at the moment, as its emulation of kmem caches complicates handling of SLAB_TYPESAFE_BY_RCU caches correctly. Enabling init_on_free also guarantees that pages and heap objects are initialized right after they're freed, so it won't be possible to access stale data by using a dangling pointer. As suggested by Michal Hocko, right now we don't let the heap users to disable initialization for certain allocations. There's not enough evidence that doing so can speed up real-life cases, and introducing ways to opt-out may result in things going out of control. This patch (of 2): The new options are needed to prevent possible information leaks and make control-flow bugs that depend on uninitialized values more deterministic. This is expected to be on-by-default on Android and Chrome OS. And it gives the opportunity for anyone else to use it under distros too via the boot args. (The init_on_free feature is regularly requested by folks where memory forensics is included in their threat models.) init_on_alloc=1 makes the kernel initialize newly allocated pages and heap objects with zeroes. Initialization is done at allocation time at the places where checks for __GFP_ZERO are performed. init_on_free=1 makes the kernel initialize freed pages and heap objects with zeroes upon their deletion. This helps to ensure sensitive data doesn't leak via use-after-free accesses. Both init_on_alloc=1 and init_on_free=1 guarantee that the allocator returns zeroed memory. The two exceptions are slab caches with constructors and SLAB_TYPESAFE_BY_RCU flag. Those are never zero-initialized to preserve their semantics. Both init_on_alloc and init_on_free default to zero, but those defaults can be overridden with CONFIG_INIT_ON_ALLOC_DEFAULT_ON and CONFIG_INIT_ON_FREE_DEFAULT_ON. If either SLUB poisoning or page poisoning is enabled, those options take precedence over init_on_alloc and init_on_free: initialization is only applied to unpoisoned allocations. Slowdown for the new features compared to init_on_free=0, init_on_alloc=0: hackbench, init_on_free=1: +7.62% sys time (st.err 0.74%) hackbench, init_on_alloc=1: +7.75% sys time (st.err 2.14%) Linux build with -j12, init_on_free=1: +8.38% wall time (st.err 0.39%) Linux build with -j12, init_on_free=1: +24.42% sys time (st.err 0.52%) Linux build with -j12, init_on_alloc=1: -0.13% wall time (st.err 0.42%) Linux build with -j12, init_on_alloc=1: +0.57% sys time (st.err 0.40%) The slowdown for init_on_free=0, init_on_alloc=0 compared to the baseline is within the standard error. The new features are also going to pave the way for hardware memory tagging (e.g. arm64's MTE), which will require both on_alloc and on_free hooks to set the tags for heap objects. With MTE, tagging will have the same cost as memory initialization. Although init_on_free is rather costly, there are paranoid use-cases where in-memory data lifetime is desired to be minimized. There are various arguments for/against the realism of the associated threat models, but given that we'll need the infrastructure for MTE anyway, and there are people who want wipe-on-free behavior no matter what the performance cost, it seems reasonable to include it in this series. [glider@google.com: v8] Link: http://lkml.kernel.org/r/20190626121943.131390-2-glider@google.com [glider@google.com: v9] Link: http://lkml.kernel.org/r/20190627130316.254309-2-glider@google.com [glider@google.com: v10] Link: http://lkml.kernel.org/r/20190628093131.199499-2-glider@google.com Link: http://lkml.kernel.org/r/20190617151050.92663-2-glider@google.com Signed-off-by: Alexander Potapenko <glider@google.com> Acked-by: Kees Cook <keescook@chromium.org> Acked-by: Michal Hocko <mhocko@suse.cz> [page and dmapool parts Acked-by: James Morris <jamorris@linux.microsoft.com>] Cc: Christoph Lameter <cl@linux.com> Cc: Masahiro Yamada <yamada.masahiro@socionext.com> Cc: "Serge E. Hallyn" <serge@hallyn.com> Cc: Nick Desaulniers <ndesaulniers@google.com> Cc: Kostya Serebryany <kcc@google.com> Cc: Dmitry Vyukov <dvyukov@google.com> Cc: Sandeep Patil <sspatil@android.com> Cc: Laura Abbott <labbott@redhat.com> Cc: Randy Dunlap <rdunlap@infradead.org> Cc: Jann Horn <jannh@google.com> Cc: Mark Rutland <mark.rutland@arm.com> Cc: Marco Elver <elver@google.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'security')
-rw-r--r--security/Kconfig.hardening29
1 files changed, 29 insertions, 0 deletions
diff --git a/security/Kconfig.hardening b/security/Kconfig.hardening
index c6cb2d9b2905..a1ffe2eb4d5f 100644
--- a/security/Kconfig.hardening
+++ b/security/Kconfig.hardening
@@ -160,6 +160,35 @@ config STACKLEAK_RUNTIME_DISABLE
160 runtime to control kernel stack erasing for kernels built with 160 runtime to control kernel stack erasing for kernels built with
161 CONFIG_GCC_PLUGIN_STACKLEAK. 161 CONFIG_GCC_PLUGIN_STACKLEAK.
162 162
163config INIT_ON_ALLOC_DEFAULT_ON
164 bool "Enable heap memory zeroing on allocation by default"
165 help
166 This has the effect of setting "init_on_alloc=1" on the kernel
167 command line. This can be disabled with "init_on_alloc=0".
168 When "init_on_alloc" is enabled, all page allocator and slab
169 allocator memory will be zeroed when allocated, eliminating
170 many kinds of "uninitialized heap memory" flaws, especially
171 heap content exposures. The performance impact varies by
172 workload, but most cases see <1% impact. Some synthetic
173 workloads have measured as high as 7%.
174
175config INIT_ON_FREE_DEFAULT_ON
176 bool "Enable heap memory zeroing on free by default"
177 help
178 This has the effect of setting "init_on_free=1" on the kernel
179 command line. This can be disabled with "init_on_free=0".
180 Similar to "init_on_alloc", when "init_on_free" is enabled,
181 all page allocator and slab allocator memory will be zeroed
182 when freed, eliminating many kinds of "uninitialized heap memory"
183 flaws, especially heap content exposures. The primary difference
184 with "init_on_free" is that data lifetime in memory is reduced,
185 as anything freed is wiped immediately, making live forensics or
186 cold boot memory attacks unable to recover freed memory contents.
187 The performance impact varies by workload, but is more expensive
188 than "init_on_alloc" due to the negative cache effects of
189 touching "cold" memory areas. Most cases see 3-5% impact. Some
190 synthetic workloads have measured as high as 8%.
191
163endmenu 192endmenu
164 193
165endmenu 194endmenu