Re: [PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-05-06 Thread Pingfan Liu
On Thu, Apr 18, 2019 at 8:32 PM Borislav Petkov  wrote:
>
> On Thu, Apr 18, 2019 at 03:56:09PM +0800, Pingfan Liu wrote:
> > Then in my case, either no @offset or invalid argument will keep
> > "*crash_base = 0", and KASLR does not care about either of them.
>
> Ok.
>
> > It is not elegant. Will try a separate patch to fix it firstly.
>
> That's appreciated, thanks. It is about time that whole kexec/kaslr/...
> code gets some much needed cleaning up and streamlining.
>
I had tried it v1 on https://patchwork.kernel.org/patch/10909627/ and
v2 on https://patchwork.kernel.org/patch/10914169/. It seems no more
feed back and hard to push forward.

Since "x86/boot/KASLR: skip the specified crashkernel region" has no
dependency on the above patch, I would like to send the next version
for it.

Regards,
Pingfan


Re: [PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-04-18 Thread Borislav Petkov
On Thu, Apr 18, 2019 at 03:56:09PM +0800, Pingfan Liu wrote:
> Then in my case, either no @offset or invalid argument will keep
> "*crash_base = 0", and KASLR does not care about either of them.

Ok.

> It is not elegant. Will try a separate patch to fix it firstly.

That's appreciated, thanks. It is about time that whole kexec/kaslr/...
code gets some much needed cleaning up and streamlining.

-- 
Regards/Gruss,
Boris.

Good mailing practices for 400: avoid top-posting and trim the reply.


Re: [PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-04-18 Thread Pingfan Liu
On Thu, Apr 18, 2019 at 12:06 AM Borislav Petkov  wrote:
>
> On Wed, Apr 17, 2019 at 01:53:37PM +0800, Pingfan Liu wrote:
> > Take __parse_crashkernel()->parse_crashkernel_simple() for example. If
> > no offset given, then it still return 0, but crash_base is dangling.

Sorry for misleading, I made a mistake. In
parse_crashkernel()->__parse_crashkernel(), { *crash_size = 0;
*crash_base = 0;}. Hence no need to initialize crash_base in
handle_crashkernel_options().
>
> Well, that is bad design. parse_crashkernel_simple() should return a
> *separate* distinct value which denotes that @offset hasn't been passed.

Then in my case, either no @offset or invalid argument will keep
"*crash_base = 0", and KASLR does not care about either of them.
>
> Please fix that by having it return 1 or something else positive to
> denote that there wasn't an [@offset] given.
>
> And then correct that crap here:
>
> static void __init reserve_crashkernel(void)
> {
> ...
>
> ret = parse_crashkernel(boot_command_line, total_mem, _size, 
> _base);
> if (ret != 0 || crash_size <= 0) {
It is not elegant. Will try a separate patch to fix it firstly.

Thanks,
Pingfan
>
> where *two*! variables are used as return values from a single function.
> That's just sloppy.
>
> Thx.
>
> --
> Regards/Gruss,
> Boris.
>
> Good mailing practices for 400: avoid top-posting and trim the reply.


Re: [PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-04-17 Thread Borislav Petkov
On Wed, Apr 17, 2019 at 01:53:37PM +0800, Pingfan Liu wrote:
> Take __parse_crashkernel()->parse_crashkernel_simple() for example. If
> no offset given, then it still return 0, but crash_base is dangling.

Well, that is bad design. parse_crashkernel_simple() should return a
*separate* distinct value which denotes that @offset hasn't been passed.

Please fix that by having it return 1 or something else positive to
denote that there wasn't an [@offset] given.

And then correct that crap here:

static void __init reserve_crashkernel(void)
{
...

ret = parse_crashkernel(boot_command_line, total_mem, _size, 
_base);
if (ret != 0 || crash_size <= 0) {

where *two*! variables are used as return values from a single function.
That's just sloppy.

Thx.

-- 
Regards/Gruss,
Boris.

Good mailing practices for 400: avoid top-posting and trim the reply.


Re: [PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-04-16 Thread Pingfan Liu
On Wed, Apr 17, 2019 at 3:01 AM Borislav Petkov  wrote:
>
> On Mon, Apr 08, 2019 at 01:58:35PM +0800, Pingfan Liu wrote:
> > crashkernel=x@y or or =range1:size1[,range2:size2,...]@offset option may
> > fail to reserve the required memory region if KASLR puts kernel into the
> > region. To avoid this uncertainty, asking KASLR to skip the required
> > region.
> >
> > Signed-off-by: Pingfan Liu 
> > Cc: Thomas Gleixner 
> > Cc: Ingo Molnar 
> > Cc: Borislav Petkov 
> > Cc: "H. Peter Anvin" 
> > Cc: Baoquan He 
> > Cc: Will Deacon 
> > Cc: Nicolas Pitre 
> > Cc: Vivek Goyal 
> > Cc: Chao Fan 
> > Cc: "Kirill A. Shutemov" 
> > Cc: Ard Biesheuvel 
> > CC: Hari Bathini 
> > Cc: linux-kernel@vger.kernel.org
> > ---
> >  arch/x86/boot/compressed/kaslr.c | 40 
> > 
> >  1 file changed, 40 insertions(+)
> >
> > diff --git a/arch/x86/boot/compressed/kaslr.c 
> > b/arch/x86/boot/compressed/kaslr.c
> > index 2e53c05..765a593 100644
> > --- a/arch/x86/boot/compressed/kaslr.c
> > +++ b/arch/x86/boot/compressed/kaslr.c
> > @@ -107,6 +107,7 @@ enum mem_avoid_index {
> >   MEM_AVOID_BOOTPARAMS,
> >   MEM_AVOID_MEMMAP_BEGIN,
> >   MEM_AVOID_MEMMAP_END = MEM_AVOID_MEMMAP_BEGIN + MAX_MEMMAP_REGIONS - 
> > 1,
> > + MEM_AVOID_CRASHKERNEL,
> >   MEM_AVOID_MAX,
> >  };
> >
> > @@ -131,6 +132,11 @@ char *skip_spaces(const char *str)
> >  }
> >  #include "../../../../lib/ctype.c"
> >  #include "../../../../lib/cmdline.c"
> > +#ifdef CONFIG_CRASH_CORE
> > +#define printk
> > +#define _BOOT_KASLR
> > +#include "../../../../lib/parse_crashkernel.c"
> > +#endif
> >
> >  static int
> >  parse_memmap(char *p, unsigned long long *start, unsigned long long *size)
> > @@ -292,6 +298,39 @@ static void handle_mem_options(void)
> >   return;
> >  }
> >
> > +static u64 mem_ram_size(void)
> > +{
> > + struct boot_e820_entry *entry;
> > + u64 total_sz = 0;
> > + int i;
> > +
> > + for (i = 0; i < boot_params->e820_entries; i++) {
> > + entry = _params->e820_table[i];
> > + /* Skip non-RAM entries. */
> > + if (entry->type != E820_TYPE_RAM)
> > + continue;
> > + total_sz += entry->size;
> > + }
> > + return total_sz;
> > +}
> > +
> > +/*
> > + * For crashkernel=size@offset or =range1:size1[,range2:size2,...]@offset
> > + * options, recording mem_avoid for them.
> > + */
> > +static void handle_crashkernel_options(void)
> > +{
> > + unsigned long long crash_size, crash_base = 0;
> > + char *cmdline = (char *)get_cmd_line_ptr();
> > + u64 total_sz = mem_ram_size();
> > +
> > + parse_crashkernel(cmdline, total_sz, _size, _base);
>
> That function has a return value which you could test. And then you
> don't need to set crash_base to 0 above.
>
Take __parse_crashkernel()->parse_crashkernel_simple() for example. If
no offset given, then it still return 0, but crash_base is dangling.

Regards,
Pingfan


Re: [PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-04-16 Thread Borislav Petkov
On Mon, Apr 08, 2019 at 01:58:35PM +0800, Pingfan Liu wrote:
> crashkernel=x@y or or =range1:size1[,range2:size2,...]@offset option may
> fail to reserve the required memory region if KASLR puts kernel into the
> region. To avoid this uncertainty, asking KASLR to skip the required
> region.
> 
> Signed-off-by: Pingfan Liu 
> Cc: Thomas Gleixner 
> Cc: Ingo Molnar 
> Cc: Borislav Petkov 
> Cc: "H. Peter Anvin" 
> Cc: Baoquan He 
> Cc: Will Deacon 
> Cc: Nicolas Pitre 
> Cc: Vivek Goyal 
> Cc: Chao Fan 
> Cc: "Kirill A. Shutemov" 
> Cc: Ard Biesheuvel 
> CC: Hari Bathini 
> Cc: linux-kernel@vger.kernel.org
> ---
>  arch/x86/boot/compressed/kaslr.c | 40 
> 
>  1 file changed, 40 insertions(+)
> 
> diff --git a/arch/x86/boot/compressed/kaslr.c 
> b/arch/x86/boot/compressed/kaslr.c
> index 2e53c05..765a593 100644
> --- a/arch/x86/boot/compressed/kaslr.c
> +++ b/arch/x86/boot/compressed/kaslr.c
> @@ -107,6 +107,7 @@ enum mem_avoid_index {
>   MEM_AVOID_BOOTPARAMS,
>   MEM_AVOID_MEMMAP_BEGIN,
>   MEM_AVOID_MEMMAP_END = MEM_AVOID_MEMMAP_BEGIN + MAX_MEMMAP_REGIONS - 1,
> + MEM_AVOID_CRASHKERNEL,
>   MEM_AVOID_MAX,
>  };
>  
> @@ -131,6 +132,11 @@ char *skip_spaces(const char *str)
>  }
>  #include "../../../../lib/ctype.c"
>  #include "../../../../lib/cmdline.c"
> +#ifdef CONFIG_CRASH_CORE
> +#define printk
> +#define _BOOT_KASLR
> +#include "../../../../lib/parse_crashkernel.c"
> +#endif
>  
>  static int
>  parse_memmap(char *p, unsigned long long *start, unsigned long long *size)
> @@ -292,6 +298,39 @@ static void handle_mem_options(void)
>   return;
>  }
>  
> +static u64 mem_ram_size(void)
> +{
> + struct boot_e820_entry *entry;
> + u64 total_sz = 0;
> + int i;
> +
> + for (i = 0; i < boot_params->e820_entries; i++) {
> + entry = _params->e820_table[i];
> + /* Skip non-RAM entries. */
> + if (entry->type != E820_TYPE_RAM)
> + continue;
> + total_sz += entry->size;
> + }
> + return total_sz;
> +}
> +
> +/*
> + * For crashkernel=size@offset or =range1:size1[,range2:size2,...]@offset
> + * options, recording mem_avoid for them.
> + */
> +static void handle_crashkernel_options(void)
> +{
> + unsigned long long crash_size, crash_base = 0;
> + char *cmdline = (char *)get_cmd_line_ptr();
> + u64 total_sz = mem_ram_size();
> +
> + parse_crashkernel(cmdline, total_sz, _size, _base);

That function has a return value which you could test. And then you
don't need to set crash_base to 0 above.

-- 
Regards/Gruss,
Boris.

Good mailing practices for 400: avoid top-posting and trim the reply.


[PATCH v4 2/2] x86/boot/KASLR: skip the specified crashkernel region

2019-04-07 Thread Pingfan Liu
crashkernel=x@y or or =range1:size1[,range2:size2,...]@offset option may
fail to reserve the required memory region if KASLR puts kernel into the
region. To avoid this uncertainty, asking KASLR to skip the required
region.

Signed-off-by: Pingfan Liu 
Cc: Thomas Gleixner 
Cc: Ingo Molnar 
Cc: Borislav Petkov 
Cc: "H. Peter Anvin" 
Cc: Baoquan He 
Cc: Will Deacon 
Cc: Nicolas Pitre 
Cc: Vivek Goyal 
Cc: Chao Fan 
Cc: "Kirill A. Shutemov" 
Cc: Ard Biesheuvel 
CC: Hari Bathini 
Cc: linux-kernel@vger.kernel.org
---
 arch/x86/boot/compressed/kaslr.c | 40 
 1 file changed, 40 insertions(+)

diff --git a/arch/x86/boot/compressed/kaslr.c b/arch/x86/boot/compressed/kaslr.c
index 2e53c05..765a593 100644
--- a/arch/x86/boot/compressed/kaslr.c
+++ b/arch/x86/boot/compressed/kaslr.c
@@ -107,6 +107,7 @@ enum mem_avoid_index {
MEM_AVOID_BOOTPARAMS,
MEM_AVOID_MEMMAP_BEGIN,
MEM_AVOID_MEMMAP_END = MEM_AVOID_MEMMAP_BEGIN + MAX_MEMMAP_REGIONS - 1,
+   MEM_AVOID_CRASHKERNEL,
MEM_AVOID_MAX,
 };
 
@@ -131,6 +132,11 @@ char *skip_spaces(const char *str)
 }
 #include "../../../../lib/ctype.c"
 #include "../../../../lib/cmdline.c"
+#ifdef CONFIG_CRASH_CORE
+#define printk
+#define _BOOT_KASLR
+#include "../../../../lib/parse_crashkernel.c"
+#endif
 
 static int
 parse_memmap(char *p, unsigned long long *start, unsigned long long *size)
@@ -292,6 +298,39 @@ static void handle_mem_options(void)
return;
 }
 
+static u64 mem_ram_size(void)
+{
+   struct boot_e820_entry *entry;
+   u64 total_sz = 0;
+   int i;
+
+   for (i = 0; i < boot_params->e820_entries; i++) {
+   entry = _params->e820_table[i];
+   /* Skip non-RAM entries. */
+   if (entry->type != E820_TYPE_RAM)
+   continue;
+   total_sz += entry->size;
+   }
+   return total_sz;
+}
+
+/*
+ * For crashkernel=size@offset or =range1:size1[,range2:size2,...]@offset
+ * options, recording mem_avoid for them.
+ */
+static void handle_crashkernel_options(void)
+{
+   unsigned long long crash_size, crash_base = 0;
+   char *cmdline = (char *)get_cmd_line_ptr();
+   u64 total_sz = mem_ram_size();
+
+   parse_crashkernel(cmdline, total_sz, _size, _base);
+   if (crash_base) {
+   mem_avoid[MEM_AVOID_CRASHKERNEL].start = crash_base;
+   mem_avoid[MEM_AVOID_CRASHKERNEL].size = crash_size;
+   }
+}
+
 /*
  * In theory, KASLR can put the kernel anywhere in the range of [16M, 64T).
  * The mem_avoid array is used to store the ranges that need to be avoided
@@ -414,6 +453,7 @@ static void mem_avoid_init(unsigned long input, unsigned 
long input_size,
 
/* Mark the memmap regions we need to avoid */
handle_mem_options();
+   handle_crashkernel_options();
 
/* Enumerate the immovable memory regions */
num_immovable_mem = count_immovable_mem_regions();
-- 
2.7.4