Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 78cac48c authored by Borislav Petkov's avatar Borislav Petkov Committed by Ingo Molnar
Browse files

x86/mm/KASLR: Propagate KASLR status to kernel proper



Commit:

  e2b32e67 ("x86, kaslr: randomize module base load address")

made module base address randomization unconditional and didn't regard
disabled KKASLR due to CONFIG_HIBERNATION and command line option
"nokaslr". For more info see (now reverted) commit:

  f47233c2 ("x86/mm/ASLR: Propagate base load address calculation")

In order to propagate KASLR status to kernel proper, we need a single bit
in boot_params.hdr.loadflags and we've chosen bit 1 thus leaving the
top-down allocated bits for bits supposed to be used by the bootloader.

Originally-From: Jiri Kosina <jkosina@suse.cz>
Suggested-by: default avatarH. Peter Anvin <hpa@zytor.com>
Signed-off-by: default avatarBorislav Petkov <bp@suse.de>
Cc: Kees Cook <keescook@chromium.org>
Signed-off-by: default avatarIngo Molnar <mingo@kernel.org>
parent 47091e3c
Loading
Loading
Loading
Loading
+6 −0
Original line number Diff line number Diff line
@@ -406,6 +406,12 @@ Protocol: 2.00+
	- If 0, the protected-mode code is loaded at 0x10000.
	- If 1, the protected-mode code is loaded at 0x100000.

  Bit 1 (kernel internal): ALSR_FLAG
	- Used internally by the compressed kernel to communicate
	  KASLR status to kernel proper.
	  If 1, KASLR enabled.
	  If 0, KASLR disabled.

  Bit 5 (write): QUIET_FLAG
	- If 0, print early messages.
	- If 1, suppress early messages.
+4 −1
Original line number Diff line number Diff line
@@ -295,7 +295,8 @@ static unsigned long find_random_addr(unsigned long minimum,
	return slots_fetch_random();
}

unsigned char *choose_kernel_location(unsigned char *input,
unsigned char *choose_kernel_location(struct boot_params *boot_params,
				      unsigned char *input,
				      unsigned long input_size,
				      unsigned char *output,
				      unsigned long output_size)
@@ -315,6 +316,8 @@ unsigned char *choose_kernel_location(unsigned char *input,
	}
#endif

	boot_params->hdr.loadflags |= KASLR_FLAG;

	/* Record the various known unsafe memory ranges. */
	mem_avoid_init((unsigned long)input, input_size,
		       (unsigned long)output, output_size);
+4 −1
Original line number Diff line number Diff line
@@ -377,6 +377,9 @@ asmlinkage __visible void *decompress_kernel(void *rmode, memptr heap,

	real_mode = rmode;

	/* Clear it for solely in-kernel use */
	real_mode->hdr.loadflags &= ~KASLR_FLAG;

	sanitize_boot_params(real_mode);

	if (real_mode->screen_info.orig_video_mode == 7) {
@@ -401,7 +404,7 @@ asmlinkage __visible void *decompress_kernel(void *rmode, memptr heap,
	 * the entire decompressed kernel plus relocation table, or the
	 * entire decompressed kernel plus .bss and .brk sections.
	 */
	output = choose_kernel_location(input_data, input_len, output,
	output = choose_kernel_location(real_mode, input_data, input_len, output,
					output_len > run_size ? output_len
							      : run_size);

+4 −2
Original line number Diff line number Diff line
@@ -57,7 +57,8 @@ int cmdline_find_option_bool(const char *option);

#if CONFIG_RANDOMIZE_BASE
/* aslr.c */
unsigned char *choose_kernel_location(unsigned char *input,
unsigned char *choose_kernel_location(struct boot_params *boot_params,
				      unsigned char *input,
				      unsigned long input_size,
				      unsigned char *output,
				      unsigned long output_size);
@@ -65,7 +66,8 @@ unsigned char *choose_kernel_location(unsigned char *input,
bool has_cpuflag(int flag);
#else
static inline
unsigned char *choose_kernel_location(unsigned char *input,
unsigned char *choose_kernel_location(struct boot_params *boot_params,
				      unsigned char *input,
				      unsigned long input_size,
				      unsigned char *output,
				      unsigned long output_size)
+5 −0
Original line number Diff line number Diff line
@@ -66,6 +66,11 @@ static inline void x86_ce4100_early_setup(void) { }
 */
extern struct boot_params boot_params;

static inline bool kaslr_enabled(void)
{
	return !!(boot_params.hdr.loadflags & KASLR_FLAG);
}

/*
 * Do NOT EVER look at the BIOS memory size location.
 * It does not work on many machines.
Loading