Messages in this thread | | | From | Kees Cook <> | Date | Fri, 17 Jun 2016 08:44:17 -0700 | Subject | Re: [PATCH v9 5/5] x86/KASLR: Allow randomization below load address |
| |
On Fri, Jun 17, 2016 at 1:47 AM, Ingo Molnar <mingo@kernel.org> wrote: > > * Kees Cook <keescook@chromium.org> wrote: > >> From: Yinghai Lu <yinghai@kernel.org> >> >> Currently the physical randomization's lower boundary is the original >> kernel load address. For bootloaders that load kernels into very high >> memory (e.g. kexec), this means randomization takes place in a very small >> window at the top of memory, ignoring the large region of physical memory >> below the load address. >> >> Since mem_avoid is already correctly tracking the regions that must be >> avoided, this patch changes the minimum address to whatever is less: >> 512M (to conservatively avoid unknown things in lower memory) or the >> load address. Now, for example, if the kernel is loaded at 8G, [512M, >> 8G) will be added into possible physical memory positions. >> >> Signed-off-by: Yinghai Lu <yinghai@kernel.org> >> [kees: rewrote changelog, refactor to use min()] >> Signed-off-by: Kees Cook <keescook@chromium.org> >> --- >> arch/x86/boot/compressed/kaslr.c | 7 +++++-- >> 1 file changed, 5 insertions(+), 2 deletions(-) >> >> diff --git a/arch/x86/boot/compressed/kaslr.c b/arch/x86/boot/compressed/kaslr.c >> index d0a823df183b..304c5c369aff 100644 >> --- a/arch/x86/boot/compressed/kaslr.c >> +++ b/arch/x86/boot/compressed/kaslr.c >> @@ -492,7 +492,7 @@ void choose_random_location(unsigned long input, >> unsigned long output_size, >> unsigned long *virt_addr) >> { >> - unsigned long random_addr; >> + unsigned long random_addr, min_addr; >> >> /* By default, keep output position unchanged. */ >> *virt_addr = *output; >> @@ -517,8 +517,11 @@ void choose_random_location(unsigned long input, >> /* Record the various known unsafe memory ranges. */ >> mem_avoid_init(input, input_size, *output); >> >> + /* Low end should be the smaller of 512M or initial location. */ >> + min_addr = min(*output, 512UL << 20); >> + >> /* Walk e820 and find a random address. */ >> - random_addr = find_random_phys_addr(*output, output_size); >> + random_addr = find_random_phys_addr(min_addr, output_size); >> if (!random_addr) { >> warn("KASLR disabled: could not find suitable E820 region!"); >> } else { > > There's no explanation in the code or in the changelog of why 512M was picked as > the lower limit.
Yinghai, do you have a rationale for this selection? I understood it to just be a very conservative target to avoid anything in low physical memory, but perhaps there is a better reason?
-Kees
-- Kees Cook Chrome OS & Brillo Security
| |