linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
@ 2016-08-28 16:35 Chen Yu
  2016-08-28 16:36 ` Pavel Machek
                   ` (2 more replies)
  0 siblings, 3 replies; 22+ messages in thread
From: Chen Yu @ 2016-08-28 16:35 UTC (permalink / raw)
  To: linux-pm
  Cc: Rafael J. Wysocki, Pavel Machek, Thomas Gleixner, Ingo Molnar,
	H. Peter Anvin, x86, linux-kernel, Chen Yu, Lee, Chun-Yi,
	Borislav Petkov

On some platforms, there is occasional panic triggered when trying to
resume from hibernation, a typical panic looks like:

"BUG: unable to handle kernel paging request at ffff880085894000
IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"

This is because e820 map has been changed by BIOS across
hibernation, and one of the page frames from first kernel
is right located in second kernel's unmapped region, so panic
comes out when accessing unmapped kernel address.

In order to expose this issue earlier, the md5 hash of e820 map
is passed from suspend kernel to resume kernel, and the system will
trigger panic once it finds the md5 value of previous kernel is not
the same as current resume kernel.

Note:
1. Without this patch applied, it is possible that BIOS has
   provided an inconsistent memory map, but the resume kernel is still
   able to restore the image anyway(e.g.,  E820_RAM region is the subset
   of the previous one), although the system might be unstable. So this
   patch tries to treat any inconsistent e820 as illegal.

2. Another case is, this patch replies on comparing the e820_saved, but
   currently the e820_save might not be strictly the same across
   hibernation, even if BIOS has provided consistent e820 map - In
   theory mptable might modify the BIOS-provided e820_saved dynamically
   in early_reserve_e820_mpc_new, which would allocate a buffer from
   E820_RAM, and marks it from E820_RAM to E820_RESERVED). 
   This is a potential and rare case we need to deal with in OS in
   the future.

Suggested-by: Pavel Machek <pavel@ucw.cz>
Suggested-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
Cc: Lee, Chun-Yi <jlee@suse.com>
Cc: Borislav Petkov <bp@alien8.de>
Signed-off-by: Chen Yu <yu.c.chen@intel.com>
---
v8:
 - Panic the system once the e820 is found to be inconsistent
   during resume.
   Fix the md5 hash len from 128 bytes to 16 bytes.
v7:
 - Use md5 hash to compare the e820 map.
v6:
 - Fix some compiling errors reported by 0day/LKP, adjust
   Kconfig/variable namings.
v5:
 - Rewrite this patch to just warn user of the broken BIOS
   when panic.
v4:
 - Add __attribute__ ((unused)) for swsusp_page_is_valid,
   to eliminate the warnning of:
   'swsusp_page_is_valid' defined but not used
   on non-x86 platforms.

v3:
 - Adjust the logic to exclude the end_pfn boundary in pfn_mapped
   when invoking mark_valid_pages, because the end_pfn is not
   a mapped page frame, we should not regard it as a valid page.

   Move the sanity check of valid pages to a early stage in resuming
   process(moved to mark_unsafe_pages), in this way, we can avoid
   unnecessarily accessing these invalid pages in later stage(yes,
   move to the original position Joey once introduced in:
   Commit 84c91b7ae07c ("PM / hibernate: avoid unsafe pages in e820
   reserved regions")

   With v3 patch applied, I did 30 cycles on my problematic platform,
   no panic triggered anymore(50% reproducible before patched, by
   plugging/unplugging memory peripheral during hibernation), and it
   just warns of invalid pages.

v2:
 - According to Ingo's suggestion, rewrite this patch.

   New version just checks each page frame according to pfn_mapped array.
   So that we do not need to touch existing code related to
   E820_RESERVED_KERN. And this method can naturely guarantee
   that the system before/after hibernation do not need to be of
   the same memory size on x86_64.

---
 arch/x86/power/hibernate_64.c | 98 +++++++++++++++++++++++++++++++++++++++++++
 kernel/power/Kconfig          |  9 ++++
 2 files changed, 107 insertions(+)

diff --git a/arch/x86/power/hibernate_64.c b/arch/x86/power/hibernate_64.c
index 9634557..7eb27afd 100644
--- a/arch/x86/power/hibernate_64.c
+++ b/arch/x86/power/hibernate_64.c
@@ -11,6 +11,10 @@
 #include <linux/gfp.h>
 #include <linux/smp.h>
 #include <linux/suspend.h>
+#include <linux/scatterlist.h>
+#include <linux/kdebug.h>
+
+#include <crypto/hash.h>
 
 #include <asm/init.h>
 #include <asm/proto.h>
@@ -177,15 +181,100 @@ int pfn_is_nosave(unsigned long pfn)
 	return (pfn >= nosave_begin_pfn) && (pfn < nosave_end_pfn);
 }
 
+#define MD5_DIGEST_SIZE 16
+
 struct restore_data_record {
 	unsigned long jump_address;
 	unsigned long jump_address_phys;
 	unsigned long cr3;
 	unsigned long magic;
+	u8 e820_digest[MD5_DIGEST_SIZE];
 };
 
 #define RESTORE_MAGIC	0x123456789ABCDEF0UL
 
+#ifdef CONFIG_HIBERNATION_CHECK_E820
+
+/**
+ *	get_e820_md5 - calculate md5 according to e820 map
+ *
+ *	@map: the e820 map to be calculated
+ *	@buf: the md5 result to be stored to
+ */
+static int get_e820_md5(struct e820map *map, void *buf)
+{
+	struct scatterlist sg;
+	struct crypto_ahash *tfm;
+	struct ahash_request *req;
+	int ret = 0;
+
+	tfm = crypto_alloc_ahash("md5", 0, CRYPTO_ALG_ASYNC);
+	if (IS_ERR(tfm))
+		return -ENOMEM;
+
+	req = ahash_request_alloc(tfm, GFP_KERNEL);
+	if (!req) {
+		ret = -ENOMEM;
+		goto free_ahash;
+	}
+
+	sg_init_one(&sg, (u8 *)map, sizeof(struct e820map));
+	ahash_request_set_callback(req, 0, NULL, NULL);
+	ahash_request_set_crypt(req, &sg, buf, sizeof(struct e820map));
+
+	if (crypto_ahash_digest(req))
+		ret = -EINVAL;
+
+	ahash_request_free(req);
+ free_ahash:
+	crypto_free_ahash(tfm);
+
+	return ret;
+}
+
+static int hibernation_e820_save(void *buf)
+{
+	int ret;
+	u8 result[MD5_DIGEST_SIZE] = {0};
+
+	ret = get_e820_md5(&e820_saved, result);
+	if (ret)
+		return ret;
+
+	memcpy(buf, result, MD5_DIGEST_SIZE);
+
+	return 0;
+}
+
+static int hibernation_e820_check(void *buf)
+{
+	int ret;
+	u8 result[MD5_DIGEST_SIZE] = {0};
+
+	ret = get_e820_md5(&e820_saved, result);
+	if (ret)
+		return ret;
+
+	if (memcmp(result, buf, MD5_DIGEST_SIZE)) {
+		pr_err("PM: e820 map conflict detected.\n");
+		panic("BIOS is playing funny tricks with us.\n");
+	}
+
+	return 0;
+}
+
+#else
+static int hibernation_e820_save(void *buf)
+{
+	return 0;
+}
+
+static int hibernation_e820_check(void *buf)
+{
+	return 0;
+}
+#endif
+
 /**
  *	arch_hibernation_header_save - populate the architecture specific part
  *		of a hibernation image header
@@ -201,6 +290,9 @@ int arch_hibernation_header_save(void *addr, unsigned int max_size)
 	rdr->jump_address_phys = __pa_symbol(&restore_registers);
 	rdr->cr3 = restore_cr3;
 	rdr->magic = RESTORE_MAGIC;
+
+	hibernation_e820_save(rdr->e820_digest);
+
 	return 0;
 }
 
@@ -216,5 +308,11 @@ int arch_hibernation_header_restore(void *addr)
 	restore_jump_address = rdr->jump_address;
 	jump_address_phys = rdr->jump_address_phys;
 	restore_cr3 = rdr->cr3;
+
+	/*
+	 * Check if suspend e820 map is the same with the resume e820 map.
+	 */
+	hibernation_e820_check(rdr->e820_digest);
+
 	return (rdr->magic == RESTORE_MAGIC) ? 0 : -EINVAL;
 }
diff --git a/kernel/power/Kconfig b/kernel/power/Kconfig
index 68d3ebc..f0ba5e7 100644
--- a/kernel/power/Kconfig
+++ b/kernel/power/Kconfig
@@ -76,6 +76,15 @@ config HIBERNATION
 
 	  For more information take a look at <file:Documentation/power/swsusp.txt>.
 
+config HIBERNATION_CHECK_E820
+	bool "Check the consistence of e820 map across hibernation"
+	depends on ARCH_HIBERNATION_HEADER
+	---help---
+	  Check if the resume kernel has the same BIOS-provided
+	  e820 memory map as the one in suspend kernel(requested
+	  by ACPI spec), by comparing the md5 digest of the two e820
+	  regions.
+
 config ARCH_SAVE_PAGE_KEYS
 	bool
 
-- 
2.7.4

^ permalink raw reply related	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-28 16:35 [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value Chen Yu
@ 2016-08-28 16:36 ` Pavel Machek
  2016-08-29  4:59 ` Borislav Petkov
  2016-08-31  0:27 ` Rafael J. Wysocki
  2 siblings, 0 replies; 22+ messages in thread
From: Pavel Machek @ 2016-08-28 16:36 UTC (permalink / raw)
  To: Chen Yu
  Cc: linux-pm, Rafael J. Wysocki, Thomas Gleixner, Ingo Molnar,
	H. Peter Anvin, x86, linux-kernel, Lee, Chun-Yi, Borislav Petkov

On Mon 2016-08-29 00:35:40, Chen Yu wrote:
> On some platforms, there is occasional panic triggered when trying to
> resume from hibernation, a typical panic looks like:
> 
> "BUG: unable to handle kernel paging request at ffff880085894000
> IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> 
> This is because e820 map has been changed by BIOS across
> hibernation, and one of the page frames from first kernel
> is right located in second kernel's unmapped region, so panic
> comes out when accessing unmapped kernel address.
> 
> In order to expose this issue earlier, the md5 hash of e820 map
> is passed from suspend kernel to resume kernel, and the system will
> trigger panic once it finds the md5 value of previous kernel is not
> the same as current resume kernel.
> 
> Note:
> 1. Without this patch applied, it is possible that BIOS has
>    provided an inconsistent memory map, but the resume kernel is still
>    able to restore the image anyway(e.g.,  E820_RAM region is the subset
>    of the previous one), although the system might be unstable. So this
>    patch tries to treat any inconsistent e820 as illegal.
> 
> 2. Another case is, this patch replies on comparing the e820_saved, but
>    currently the e820_save might not be strictly the same across
>    hibernation, even if BIOS has provided consistent e820 map - In
>    theory mptable might modify the BIOS-provided e820_saved dynamically
>    in early_reserve_e820_mpc_new, which would allocate a buffer from
>    E820_RAM, and marks it from E820_RAM to E820_RESERVED). 
>    This is a potential and rare case we need to deal with in OS in
>    the future.
> 
> Suggested-by: Pavel Machek <pavel@ucw.cz>
> Suggested-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
> Cc: Lee, Chun-Yi <jlee@suse.com>
> Cc: Borislav Petkov <bp@alien8.de>
> Signed-off-by: Chen Yu <yu.c.chen@intel.com>

Acked-by: Pavel Machek <pavel@ucw.cz>

You might want to verify that panic is actually visible on affected
platform. Thanks for your patience ;-).

									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-28 16:35 [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value Chen Yu
  2016-08-28 16:36 ` Pavel Machek
@ 2016-08-29  4:59 ` Borislav Petkov
  2016-08-29  7:15   ` Pavel Machek
  2016-08-29 13:41   ` Rafael J. Wysocki
  2016-08-31  0:27 ` Rafael J. Wysocki
  2 siblings, 2 replies; 22+ messages in thread
From: Borislav Petkov @ 2016-08-29  4:59 UTC (permalink / raw)
  To: Chen Yu
  Cc: linux-pm, Rafael J. Wysocki, Pavel Machek, Thomas Gleixner,
	Ingo Molnar, H. Peter Anvin, x86, linux-kernel, Lee, Chun-Yi

On Mon, Aug 29, 2016 at 12:35:40AM +0800, Chen Yu wrote:
> On some platforms, there is occasional panic triggered when trying to
> resume from hibernation, a typical panic looks like:
> 
> "BUG: unable to handle kernel paging request at ffff880085894000
> IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> 
> This is because e820 map has been changed by BIOS across
> hibernation, and one of the page frames from first kernel
> is right located in second kernel's unmapped region, so panic
> comes out when accessing unmapped kernel address.
> 
> In order to expose this issue earlier, the md5 hash of e820 map
> is passed from suspend kernel to resume kernel, and the system will
> trigger panic once it finds the md5 value of previous kernel is not
> the same as current resume kernel.

... so basically now even the cases where it managed to resume would
panic because the digests differ, even if the original panic condition
doesn't trigger the bug, i.e. your Note 1 below.

The more important question IMHO would be, can we resume our system
successfully *even* if BIOS fiddled with the e820 map?

We'd still warn the hell out of it and even make that the md5 digest
comparison a default-enabled thing without even having a config option
to disable it but can we try harder not to panic and deal with this next
BIOS f*ckup more intelligently than throwing our hands in the air and
giving up?

Thanks.

-- 
Regards/Gruss,
    Boris.

ECO tip #101: Trim your mails when you reply.
--

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29  4:59 ` Borislav Petkov
@ 2016-08-29  7:15   ` Pavel Machek
  2016-08-29 13:41     ` Borislav Petkov
  2016-08-29 13:41   ` Rafael J. Wysocki
  1 sibling, 1 reply; 22+ messages in thread
From: Pavel Machek @ 2016-08-29  7:15 UTC (permalink / raw)
  To: Borislav Petkov
  Cc: Chen Yu, linux-pm, Rafael J. Wysocki, Thomas Gleixner,
	Ingo Molnar, H. Peter Anvin, x86, linux-kernel, Lee, Chun-Yi

On Mon 2016-08-29 06:59:42, Borislav Petkov wrote:
> On Mon, Aug 29, 2016 at 12:35:40AM +0800, Chen Yu wrote:
> > On some platforms, there is occasional panic triggered when trying to
> > resume from hibernation, a typical panic looks like:
> > 
> > "BUG: unable to handle kernel paging request at ffff880085894000
> > IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> > 
> > This is because e820 map has been changed by BIOS across
> > hibernation, and one of the page frames from first kernel
> > is right located in second kernel's unmapped region, so panic
> > comes out when accessing unmapped kernel address.
> > 
> > In order to expose this issue earlier, the md5 hash of e820 map
> > is passed from suspend kernel to resume kernel, and the system will
> > trigger panic once it finds the md5 value of previous kernel is not
> > the same as current resume kernel.
> 
> ... so basically now even the cases where it managed to resume would
> panic because the digests differ, even if the original panic condition
> doesn't trigger the bug, i.e. your Note 1 below.

Note where?

You can't guarantee that e820 mismatch results in kernel panic, it
could also be endless loop or data corruption. 

> The more important question IMHO would be, can we resume our system
> successfully *even* if BIOS fiddled with the e820 map?

Sounds about as easy as hot unplugging arbitrary memory address. IOW
"not easy".

									Pavel

-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29  7:15   ` Pavel Machek
@ 2016-08-29 13:41     ` Borislav Petkov
  2016-08-30  8:35       ` joeyli
  2016-08-30 11:51       ` Rafael J. Wysocki
  0 siblings, 2 replies; 22+ messages in thread
From: Borislav Petkov @ 2016-08-29 13:41 UTC (permalink / raw)
  To: Pavel Machek
  Cc: Chen Yu, linux-pm, Rafael J. Wysocki, Thomas Gleixner,
	Ingo Molnar, H. Peter Anvin, x86, linux-kernel, Lee, Chun-Yi

On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> Sounds about as easy as hot unplugging arbitrary memory address. IOW
> "not easy".

Regardless, forcibly panicking the system more is still the wrong
approach IMO.

Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
that the user should disable hibernation on that box and never ever
enable it again.

After that, the kernel should *disable* hibernation for the current boot
so any further hibernation runs don't even happen. Maybe even taint
itself.

-- 
Regards/Gruss,
    Boris.

ECO tip #101: Trim your mails when you reply.
--

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29  4:59 ` Borislav Petkov
  2016-08-29  7:15   ` Pavel Machek
@ 2016-08-29 13:41   ` Rafael J. Wysocki
  2016-08-29 15:13     ` Pavel Machek
  1 sibling, 1 reply; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-29 13:41 UTC (permalink / raw)
  To: Borislav Petkov
  Cc: Chen Yu, Linux PM, Rafael J. Wysocki, Pavel Machek,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	the arch/x86 maintainers, Linux Kernel Mailing List, Lee,
	Chun-Yi

On Mon, Aug 29, 2016 at 6:59 AM, Borislav Petkov <bp@alien8.de> wrote:
> On Mon, Aug 29, 2016 at 12:35:40AM +0800, Chen Yu wrote:
>> On some platforms, there is occasional panic triggered when trying to
>> resume from hibernation, a typical panic looks like:
>>
>> "BUG: unable to handle kernel paging request at ffff880085894000
>> IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
>>
>> This is because e820 map has been changed by BIOS across
>> hibernation, and one of the page frames from first kernel
>> is right located in second kernel's unmapped region, so panic
>> comes out when accessing unmapped kernel address.
>>
>> In order to expose this issue earlier, the md5 hash of e820 map
>> is passed from suspend kernel to resume kernel, and the system will
>> trigger panic once it finds the md5 value of previous kernel is not
>> the same as current resume kernel.
>
> ... so basically now even the cases where it managed to resume would
> panic because the digests differ, even if the original panic condition
> doesn't trigger the bug, i.e. your Note 1 below.
>
> The more important question IMHO would be, can we resume our system
> successfully *even* if BIOS fiddled with the e820 map?
>
> We'd still warn the hell out of it and even make that the md5 digest
> comparison a default-enabled thing without even having a config option
> to disable it but can we try harder not to panic and deal with this next
> BIOS f*ckup more intelligently than throwing our hands in the air and
> giving up?

We need not panic in principle and I wouldn't do that.

I would warn and try to continue regardless (which was the original
plan here AFAICS), or we change a possible data loss into a guaranteed
one.

IMO it is sufficient to give up when a PFN we have image data for is
not pfn_valid() during resume, which we do already.

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29 13:41   ` Rafael J. Wysocki
@ 2016-08-29 15:13     ` Pavel Machek
  2016-08-30 12:04       ` Rafael J. Wysocki
  0 siblings, 1 reply; 22+ messages in thread
From: Pavel Machek @ 2016-08-29 15:13 UTC (permalink / raw)
  To: Rafael J. Wysocki
  Cc: Borislav Petkov, Chen Yu, Linux PM, Rafael J. Wysocki,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	the arch/x86 maintainers, Linux Kernel Mailing List, Lee,
	Chun-Yi

On Mon 2016-08-29 15:41:34, Rafael J. Wysocki wrote:
> On Mon, Aug 29, 2016 at 6:59 AM, Borislav Petkov <bp@alien8.de> wrote:
> > On Mon, Aug 29, 2016 at 12:35:40AM +0800, Chen Yu wrote:
> >> On some platforms, there is occasional panic triggered when trying to
> >> resume from hibernation, a typical panic looks like:
> >>
> >> "BUG: unable to handle kernel paging request at ffff880085894000
> >> IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> >>
> >> This is because e820 map has been changed by BIOS across
> >> hibernation, and one of the page frames from first kernel
> >> is right located in second kernel's unmapped region, so panic
> >> comes out when accessing unmapped kernel address.
> >>
> >> In order to expose this issue earlier, the md5 hash of e820 map
> >> is passed from suspend kernel to resume kernel, and the system will
> >> trigger panic once it finds the md5 value of previous kernel is not
> >> the same as current resume kernel.
> >
> > ... so basically now even the cases where it managed to resume would
> > panic because the digests differ, even if the original panic condition
> > doesn't trigger the bug, i.e. your Note 1 below.
> >
> > The more important question IMHO would be, can we resume our system
> > successfully *even* if BIOS fiddled with the e820 map?
> >
> > We'd still warn the hell out of it and even make that the md5 digest
> > comparison a default-enabled thing without even having a config option
> > to disable it but can we try harder not to panic and deal with this next
> > BIOS f*ckup more intelligently than throwing our hands in the air and
> > giving up?
> 
> We need not panic in principle and I wouldn't do that.
> 
> I would warn and try to continue regardless (which was the original
> plan here AFAICS), or we change a possible data loss into a guaranteed
> one.
> 
> IMO it is sufficient to give up when a PFN we have image data for is
> not pfn_valid() during resume, which we do already.

Well... can you guarantee what will be effect of resuming with
different memory map?

Because there's big difference between panic and trying to continue
with corrupted memory.
								Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29 13:41     ` Borislav Petkov
@ 2016-08-30  8:35       ` joeyli
  2016-08-30 11:54         ` Rafael J. Wysocki
  2016-08-30 11:51       ` Rafael J. Wysocki
  1 sibling, 1 reply; 22+ messages in thread
From: joeyli @ 2016-08-30  8:35 UTC (permalink / raw)
  To: Borislav Petkov
  Cc: Pavel Machek, Chen Yu, linux-pm, Rafael J. Wysocki,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin, x86, linux-kernel,
	Lee

On Mon, Aug 29, 2016 at 03:41:23PM +0200, Borislav Petkov wrote:
> On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> > Sounds about as easy as hot unplugging arbitrary memory address. IOW
> > "not easy".
> 
> Regardless, forcibly panicking the system more is still the wrong
> approach IMO.
> 
> Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
> that the user should disable hibernation on that box and never ever
> enable it again.
> 
> After that, the kernel should *disable* hibernation for the current boot
> so any further hibernation runs don't even happen. Maybe even taint
> itself.
>

I support this idea to disable hibernation when kernel detected e820 layout
was changed by BIOS. If system resume luckily then kernel should warn to user
and refuse to hibernate again. User must to know that's better to reboot
system when he saw the warning message after lucky resume.

Not just BIOS doesn't fix e820 layout. There have some machines doesn't provide
_S4_ function, so the hibernation fallbacks to "shutdown" mode because "platform"
mode unavailable. In this situation, user is just lucky to run the hibernation.
Kernel should warn to user and disable hibernation when detected e820 layout
changed.


Thanks a lot!
Joey Lee 

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29 13:41     ` Borislav Petkov
  2016-08-30  8:35       ` joeyli
@ 2016-08-30 11:51       ` Rafael J. Wysocki
  1 sibling, 0 replies; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-30 11:51 UTC (permalink / raw)
  To: Borislav Petkov
  Cc: Pavel Machek, Chen Yu, linux-pm, Thomas Gleixner, Ingo Molnar,
	H. Peter Anvin, x86, linux-kernel, Lee, Chun-Yi

On Monday, August 29, 2016 03:41:23 PM Borislav Petkov wrote:
> On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> > Sounds about as easy as hot unplugging arbitrary memory address. IOW
> > "not easy".
> 
> Regardless, forcibly panicking the system more is still the wrong
> approach IMO.

Agreed.

> Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
> that the user should disable hibernation on that box and never ever
> enable it again.
> 
> After that, the kernel should *disable* hibernation for the current boot
> so any further hibernation runs don't even happen. Maybe even taint
> itself.

Yes, taint the kernel when e820 mismatch is detected.

It may be a good idea to start an emergency shutdown in that case too, but
after getting to a point when it actually has a chance to work.

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-30  8:35       ` joeyli
@ 2016-08-30 11:54         ` Rafael J. Wysocki
  2016-09-08 21:15           ` Pavel Machek
  0 siblings, 1 reply; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-30 11:54 UTC (permalink / raw)
  To: joeyli
  Cc: Borislav Petkov, Pavel Machek, Chen Yu, linux-pm,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin, x86, linux-kernel,
	Lee

On Tuesday, August 30, 2016 04:35:05 PM joeyli wrote:
> On Mon, Aug 29, 2016 at 03:41:23PM +0200, Borislav Petkov wrote:
> > On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> > > Sounds about as easy as hot unplugging arbitrary memory address. IOW
> > > "not easy".
> > 
> > Regardless, forcibly panicking the system more is still the wrong
> > approach IMO.
> > 
> > Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
> > that the user should disable hibernation on that box and never ever
> > enable it again.
> > 
> > After that, the kernel should *disable* hibernation for the current boot
> > so any further hibernation runs don't even happen. Maybe even taint
> > itself.
> >
> 
> I support this idea to disable hibernation when kernel detected e820 layout
> was changed by BIOS. If system resume luckily then kernel should warn to user
> and refuse to hibernate again. User must to know that's better to reboot
> system when he saw the warning message after lucky resume.
> 
> Not just BIOS doesn't fix e820 layout. There have some machines doesn't provide
> _S4_ function, so the hibernation fallbacks to "shutdown" mode because "platform"
> mode unavailable. In this situation, user is just lucky to run the hibernation.
> Kernel should warn to user and disable hibernation when detected e820 layout
> changed.

Well, please see my reply to Boris.

Pavel is right that running after detecting an e820 mismatch is generally risky,
so why don't we shut down the system (but try to do that cleanly instead of
causing it to panic right away) on an e820 mismatch?

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-29 15:13     ` Pavel Machek
@ 2016-08-30 12:04       ` Rafael J. Wysocki
  2016-08-30 19:53         ` Pavel Machek
  0 siblings, 1 reply; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-30 12:04 UTC (permalink / raw)
  To: Pavel Machek
  Cc: Rafael J. Wysocki, Borislav Petkov, Chen Yu, Linux PM,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	the arch/x86 maintainers, Linux Kernel Mailing List, Lee,
	Chun-Yi

On Monday, August 29, 2016 05:13:34 PM Pavel Machek wrote:
> On Mon 2016-08-29 15:41:34, Rafael J. Wysocki wrote:
> > On Mon, Aug 29, 2016 at 6:59 AM, Borislav Petkov <bp@alien8.de> wrote:
> > > On Mon, Aug 29, 2016 at 12:35:40AM +0800, Chen Yu wrote:
> > >> On some platforms, there is occasional panic triggered when trying to
> > >> resume from hibernation, a typical panic looks like:
> > >>
> > >> "BUG: unable to handle kernel paging request at ffff880085894000
> > >> IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> > >>
> > >> This is because e820 map has been changed by BIOS across
> > >> hibernation, and one of the page frames from first kernel
> > >> is right located in second kernel's unmapped region, so panic
> > >> comes out when accessing unmapped kernel address.
> > >>
> > >> In order to expose this issue earlier, the md5 hash of e820 map
> > >> is passed from suspend kernel to resume kernel, and the system will
> > >> trigger panic once it finds the md5 value of previous kernel is not
> > >> the same as current resume kernel.
> > >
> > > ... so basically now even the cases where it managed to resume would
> > > panic because the digests differ, even if the original panic condition
> > > doesn't trigger the bug, i.e. your Note 1 below.
> > >
> > > The more important question IMHO would be, can we resume our system
> > > successfully *even* if BIOS fiddled with the e820 map?
> > >
> > > We'd still warn the hell out of it and even make that the md5 digest
> > > comparison a default-enabled thing without even having a config option
> > > to disable it but can we try harder not to panic and deal with this next
> > > BIOS f*ckup more intelligently than throwing our hands in the air and
> > > giving up?
> > 
> > We need not panic in principle and I wouldn't do that.
> > 
> > I would warn and try to continue regardless (which was the original
> > plan here AFAICS), or we change a possible data loss into a guaranteed
> > one.
> > 
> > IMO it is sufficient to give up when a PFN we have image data for is
> > not pfn_valid() during resume, which we do already.
> 
> Well... can you guarantee what will be effect of resuming with
> different memory map?
> 
> Because there's big difference between panic and trying to continue
> with corrupted memory.

If all of the page frames the image kernel used before hibernation are
available during resume as well, memory won't really get corrupted, at least
not right away.

There may be problems going forward, but whether or not they actually happen
depends on what the differences are.  So while an e820 mismatch indicates that
things may go wrong, it doesn't necessarily mean that they will.

Also, that panic() may cause hibernation to stop working in a sort of hard and
nasty way where it used to work flawlessly previously and that would be a
regression, so not really acceptable.

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-30 12:04       ` Rafael J. Wysocki
@ 2016-08-30 19:53         ` Pavel Machek
  2016-08-30 21:50           ` Rafael J. Wysocki
  0 siblings, 1 reply; 22+ messages in thread
From: Pavel Machek @ 2016-08-30 19:53 UTC (permalink / raw)
  To: Rafael J. Wysocki
  Cc: Rafael J. Wysocki, Borislav Petkov, Chen Yu, Linux PM,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	the arch/x86 maintainers, Linux Kernel Mailing List, Lee,
	Chun-Yi


> > > I would warn and try to continue regardless (which was the original
> > > plan here AFAICS), or we change a possible data loss into a guaranteed
> > > one.
> > > 
> > > IMO it is sufficient to give up when a PFN we have image data for is
> > > not pfn_valid() during resume, which we do already.
> > 
> > Well... can you guarantee what will be effect of resuming with
> > different memory map?
> > 
> > Because there's big difference between panic and trying to continue
> > with corrupted memory.
> 
> If all of the page frames the image kernel used before hibernation are
> available during resume as well, memory won't really get corrupted, at least
> not right away.
> 
> There may be problems going forward, but whether or not they actually happen
> depends on what the differences are.  So while an e820 mismatch indicates that
> things may go wrong, it doesn't necessarily mean that they will.

Well "memory won't get corrupted right away" seems like good reason to
panic the machine ASAP.

You can flip some bits in memory, and it may not cause problems. Still
if you know some bits in memory were flipped, you'd better panic the
machine. Continuing is unsafe.

If you could guarantee that machine will panic down the line, and not
something worse, you'd be right.

But at least the case where there is _less_ memory available after
resume, kernel will write into BIOS reserved memory and bad things
will happen. Yes, it usually panics, but it is quite clear it could
corrupt memory, too.

So I believe we should take the patch, and let users update their
BIOSes. [And I believe it is not too widespread, either.]

If you want to try to cook a patch that determines if new e820 map is
superset of the old one... well... I believe the resulting complexity
will be obviously unreasonable but I guess you (or some interested
person) can try.

> Also, that panic() may cause hibernation to stop working in a sort of hard and
> nasty way where it used to work flawlessly previously and that would be a
> regression, so not really acceptable.

Well, turning memory corruption bug into panic is an improvement, not
a regression.
									Pavel

-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-30 19:53         ` Pavel Machek
@ 2016-08-30 21:50           ` Rafael J. Wysocki
  2016-08-31 11:03             ` Pavel Machek
  0 siblings, 1 reply; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-30 21:50 UTC (permalink / raw)
  To: Pavel Machek
  Cc: Rafael J. Wysocki, Rafael J. Wysocki, Borislav Petkov, Chen Yu,
	Linux PM, Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	the arch/x86 maintainers, Linux Kernel Mailing List, Lee,
	Chun-Yi

On Tue, Aug 30, 2016 at 9:53 PM, Pavel Machek <pavel@ucw.cz> wrote:
>
>> > > I would warn and try to continue regardless (which was the original
>> > > plan here AFAICS), or we change a possible data loss into a guaranteed
>> > > one.
>> > >
>> > > IMO it is sufficient to give up when a PFN we have image data for is
>> > > not pfn_valid() during resume, which we do already.
>> >
>> > Well... can you guarantee what will be effect of resuming with
>> > different memory map?
>> >
>> > Because there's big difference between panic and trying to continue
>> > with corrupted memory.
>>
>> If all of the page frames the image kernel used before hibernation are
>> available during resume as well, memory won't really get corrupted, at least
>> not right away.
>>
>> There may be problems going forward, but whether or not they actually happen
>> depends on what the differences are.  So while an e820 mismatch indicates that
>> things may go wrong, it doesn't necessarily mean that they will.
>
> Well "memory won't get corrupted right away" seems like good reason to
> panic the machine ASAP.
>
> You can flip some bits in memory, and it may not cause problems. Still
> if you know some bits in memory were flipped, you'd better panic the
> machine. Continuing is unsafe.
>
> If you could guarantee that machine will panic down the line, and not
> something worse, you'd be right.
>
> But at least the case where there is _less_ memory available after
> resume, kernel will write into BIOS reserved memory and bad things
> will happen. Yes, it usually panics, but it is quite clear it could
> corrupt memory, too.

That depends a good deal on what those ranges were reserved for.
There very well may not be anything vital in there.

> So I believe we should take the patch, and let users update their
> BIOSes. [And I believe it is not too widespread, either.]
>
> If you want to try to cook a patch that determines if new e820 map is
> superset of the old one... well... I believe the resulting complexity
> will be obviously unreasonable but I guess you (or some interested
> person) can try.
L
>> Also, that panic() may cause hibernation to stop working in a sort of hard and
>> nasty way where it used to work flawlessly previously and that would be a
>> regression, so not really acceptable.
>
> Well, turning memory corruption bug into panic is an improvement, not
> a regression.

Since we don't do anything about these problems today and presumably
people use hibernation on the affected systems, there are reasons to
think that the problem is not quite as grave as you're painting it.

But that aside, adding a panic() like in this patch isn't particularly
useful anyway, because it panics the restore kernel.  It is sufficient
to make arch_hibernation_header_restore() return an error to actually
fail the resume and cause the restore kernel to discard the image.
And that would preserve the information about the failure in the
kernel log at least.

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-28 16:35 [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value Chen Yu
  2016-08-28 16:36 ` Pavel Machek
  2016-08-29  4:59 ` Borislav Petkov
@ 2016-08-31  0:27 ` Rafael J. Wysocki
  2016-08-31 11:07   ` Pavel Machek
  2 siblings, 1 reply; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-31  0:27 UTC (permalink / raw)
  To: Chen Yu
  Cc: linux-pm, Pavel Machek, Thomas Gleixner, Ingo Molnar,
	H. Peter Anvin, x86, linux-kernel, Lee, Chun-Yi, Borislav Petkov

On Monday, August 29, 2016 12:35:40 AM Chen Yu wrote:
> On some platforms, there is occasional panic triggered when trying to
> resume from hibernation, a typical panic looks like:
> 
> "BUG: unable to handle kernel paging request at ffff880085894000
> IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> 
> This is because e820 map has been changed by BIOS across
> hibernation, and one of the page frames from first kernel
> is right located in second kernel's unmapped region, so panic
> comes out when accessing unmapped kernel address.
> 
> In order to expose this issue earlier, the md5 hash of e820 map
> is passed from suspend kernel to resume kernel, and the system will
> trigger panic once it finds the md5 value of previous kernel is not
> the same as current resume kernel.
> 
> Note:
> 1. Without this patch applied, it is possible that BIOS has
>    provided an inconsistent memory map, but the resume kernel is still
>    able to restore the image anyway(e.g.,  E820_RAM region is the subset
>    of the previous one), although the system might be unstable. So this
>    patch tries to treat any inconsistent e820 as illegal.
> 
> 2. Another case is, this patch replies on comparing the e820_saved, but
>    currently the e820_save might not be strictly the same across
>    hibernation, even if BIOS has provided consistent e820 map - In
>    theory mptable might modify the BIOS-provided e820_saved dynamically
>    in early_reserve_e820_mpc_new, which would allocate a buffer from
>    E820_RAM, and marks it from E820_RAM to E820_RESERVED). 
>    This is a potential and rare case we need to deal with in OS in
>    the future.
> 
> Suggested-by: Pavel Machek <pavel@ucw.cz>
> Suggested-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
> Cc: Lee, Chun-Yi <jlee@suse.com>
> Cc: Borislav Petkov <bp@alien8.de>
> Signed-off-by: Chen Yu <yu.c.chen@intel.com>
> ---
> v8:
>  - Panic the system once the e820 is found to be inconsistent
>    during resume.
>    Fix the md5 hash len from 128 bytes to 16 bytes.
> v7:
>  - Use md5 hash to compare the e820 map.
> v6:
>  - Fix some compiling errors reported by 0day/LKP, adjust
>    Kconfig/variable namings.
> v5:
>  - Rewrite this patch to just warn user of the broken BIOS
>    when panic.
> v4:
>  - Add __attribute__ ((unused)) for swsusp_page_is_valid,
>    to eliminate the warnning of:
>    'swsusp_page_is_valid' defined but not used
>    on non-x86 platforms.
> 
> v3:
>  - Adjust the logic to exclude the end_pfn boundary in pfn_mapped
>    when invoking mark_valid_pages, because the end_pfn is not
>    a mapped page frame, we should not regard it as a valid page.
> 
>    Move the sanity check of valid pages to a early stage in resuming
>    process(moved to mark_unsafe_pages), in this way, we can avoid
>    unnecessarily accessing these invalid pages in later stage(yes,
>    move to the original position Joey once introduced in:
>    Commit 84c91b7ae07c ("PM / hibernate: avoid unsafe pages in e820
>    reserved regions")
> 
>    With v3 patch applied, I did 30 cycles on my problematic platform,
>    no panic triggered anymore(50% reproducible before patched, by
>    plugging/unplugging memory peripheral during hibernation), and it
>    just warns of invalid pages.
> 
> v2:
>  - According to Ingo's suggestion, rewrite this patch.
> 
>    New version just checks each page frame according to pfn_mapped array.
>    So that we do not need to touch existing code related to
>    E820_RESERVED_KERN. And this method can naturely guarantee
>    that the system before/after hibernation do not need to be of
>    the same memory size on x86_64.
> 
> ---
>  arch/x86/power/hibernate_64.c | 98 +++++++++++++++++++++++++++++++++++++++++++
>  kernel/power/Kconfig          |  9 ++++
>  2 files changed, 107 insertions(+)
> 
> diff --git a/arch/x86/power/hibernate_64.c b/arch/x86/power/hibernate_64.c
> index 9634557..7eb27afd 100644
> --- a/arch/x86/power/hibernate_64.c
> +++ b/arch/x86/power/hibernate_64.c
> @@ -11,6 +11,10 @@
>  #include <linux/gfp.h>
>  #include <linux/smp.h>
>  #include <linux/suspend.h>
> +#include <linux/scatterlist.h>
> +#include <linux/kdebug.h>
> +
> +#include <crypto/hash.h>
>  
>  #include <asm/init.h>
>  #include <asm/proto.h>
> @@ -177,15 +181,100 @@ int pfn_is_nosave(unsigned long pfn)
>  	return (pfn >= nosave_begin_pfn) && (pfn < nosave_end_pfn);
>  }
>  
> +#define MD5_DIGEST_SIZE 16
> +
>  struct restore_data_record {
>  	unsigned long jump_address;
>  	unsigned long jump_address_phys;
>  	unsigned long cr3;
>  	unsigned long magic;
> +	u8 e820_digest[MD5_DIGEST_SIZE];
>  };
>  
>  #define RESTORE_MAGIC	0x123456789ABCDEF0UL

You're changing the image header format, so RESTORE_MAGIC needs to be updated
too.

>  
> +#ifdef CONFIG_HIBERNATION_CHECK_E820
> +
> +/**
> + *	get_e820_md5 - calculate md5 according to e820 map
> + *
> + *	@map: the e820 map to be calculated
> + *	@buf: the md5 result to be stored to
> + */

Please use spaces instead of tabs in the kerneldoc (note to self: the existing
ones need to be fixed too).

> +static int get_e820_md5(struct e820map *map, void *buf)
> +{
> +	struct scatterlist sg;
> +	struct crypto_ahash *tfm;
> +	struct ahash_request *req;
> +	int ret = 0;
> +
> +	tfm = crypto_alloc_ahash("md5", 0, CRYPTO_ALG_ASYNC);

You need to ensure that crypto_alloc_ahash() and friends are built in.

> +	if (IS_ERR(tfm))
> +		return -ENOMEM;
> +
> +	req = ahash_request_alloc(tfm, GFP_KERNEL);
> +	if (!req) {
> +		ret = -ENOMEM;
> +		goto free_ahash;
> +	}
> +
> +	sg_init_one(&sg, (u8 *)map, sizeof(struct e820map));
> +	ahash_request_set_callback(req, 0, NULL, NULL);
> +	ahash_request_set_crypt(req, &sg, buf, sizeof(struct e820map));
> +
> +	if (crypto_ahash_digest(req))
> +		ret = -EINVAL;
> +
> +	ahash_request_free(req);
> + free_ahash:
> +	crypto_free_ahash(tfm);
> +
> +	return ret;
> +}
> +
> +static int hibernation_e820_save(void *buf)
> +{
> +	int ret;
> +	u8 result[MD5_DIGEST_SIZE] = {0};
> +
> +	ret = get_e820_md5(&e820_saved, result);

Why can't you do it on buf directly without the intermediate buffer on the
stack?

> +	if (ret)
> +		return ret;
> +
> +	memcpy(buf, result, MD5_DIGEST_SIZE);
> +
> +	return 0;

Plus the only caller of this doesn't check the return value of it, so
why is it not void?

> +}
> +
> +static int hibernation_e820_check(void *buf)
> +{
> +	int ret;
> +	u8 result[MD5_DIGEST_SIZE] = {0};
> +
> +	ret = get_e820_md5(&e820_saved, result);
> +	if (ret)
> +		return ret;
> +
> +	if (memcmp(result, buf, MD5_DIGEST_SIZE)) {
> +		pr_err("PM: e820 map conflict detected.\n");
> +		panic("BIOS is playing funny tricks with us.\n");

As I said to Pavel, this doesn't serve any useful purpose.

Make this one a bool function, call it hibernate_e820_mismatch() and then
you can do ->

> +	}
> +
> +	return 0;
> +}
> +
> +#else
> +static int hibernation_e820_save(void *buf)
> +{
> +	return 0;
> +}
> +
> +static int hibernation_e820_check(void *buf)
> +{
> +	return 0;
> +}
> +#endif
> +
>  /**
>   *	arch_hibernation_header_save - populate the architecture specific part
>   *		of a hibernation image header
> @@ -201,6 +290,9 @@ int arch_hibernation_header_save(void *addr, unsigned int max_size)
>  	rdr->jump_address_phys = __pa_symbol(&restore_registers);
>  	rdr->cr3 = restore_cr3;
>  	rdr->magic = RESTORE_MAGIC;
> +
> +	hibernation_e820_save(rdr->e820_digest);
> +
>  	return 0;
>  }
>  
> @@ -216,5 +308,11 @@ int arch_hibernation_header_restore(void *addr)
>  	restore_jump_address = rdr->jump_address;
>  	jump_address_phys = rdr->jump_address_phys;
>  	restore_cr3 = rdr->cr3;
> +
> +	/*
> +	 * Check if suspend e820 map is the same with the resume e820 map.
> +	 */
> +	hibernation_e820_check(rdr->e820_digest);

->
	if (hibernate_e820_mismatch(rdr->e820_digest))
		return -ENODEV;

for example.

> +
>  	return (rdr->magic == RESTORE_MAGIC) ? 0 : -EINVAL;
>  }
> diff --git a/kernel/power/Kconfig b/kernel/power/Kconfig
> index 68d3ebc..f0ba5e7 100644
> --- a/kernel/power/Kconfig
> +++ b/kernel/power/Kconfig
> @@ -76,6 +76,15 @@ config HIBERNATION
>  
>  	  For more information take a look at <file:Documentation/power/swsusp.txt>.
>  
> +config HIBERNATION_CHECK_E820

That is a bit clumsy.

First off, ARM64 uses ARCH_HIBERNATION_HEADER, so depending on this one alone
is not enough.  Moreover, it depends on the hash to be available, so that needs
to be taken into account as well.

Second, I'm not sure if making it user-selectable adds any value.

> +	bool "Check the consistence of e820 map across hibernation"
> +	depends on ARCH_HIBERNATION_HEADER
> +	---help---
> +	  Check if the resume kernel has the same BIOS-provided
> +	  e820 memory map as the one in suspend kernel(requested
> +	  by ACPI spec), by comparing the md5 digest of the two e820
> +	  regions.
> +
>  config ARCH_SAVE_PAGE_KEYS
>  	bool

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-30 21:50           ` Rafael J. Wysocki
@ 2016-08-31 11:03             ` Pavel Machek
  0 siblings, 0 replies; 22+ messages in thread
From: Pavel Machek @ 2016-08-31 11:03 UTC (permalink / raw)
  To: Rafael J. Wysocki
  Cc: Rafael J. Wysocki, Borislav Petkov, Chen Yu, Linux PM,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	the arch/x86 maintainers, Linux Kernel Mailing List, Lee,
	Chun-Yi

Hi!

> >> There may be problems going forward, but whether or not they actually happen
> >> depends on what the differences are.  So while an e820 mismatch indicates that
> >> things may go wrong, it doesn't necessarily mean that they will.
> >
> > Well "memory won't get corrupted right away" seems like good reason to
> > panic the machine ASAP.
> >
> > You can flip some bits in memory, and it may not cause problems. Still
> > if you know some bits in memory were flipped, you'd better panic the
> > machine. Continuing is unsafe.
> >
> > If you could guarantee that machine will panic down the line, and not
> > something worse, you'd be right.
> >
> > But at least the case where there is _less_ memory available after
> > resume, kernel will write into BIOS reserved memory and bad things
> > will happen. Yes, it usually panics, but it is quite clear it could
> > corrupt memory, too.
> 
> That depends a good deal on what those ranges were reserved for.
> There very well may not be anything vital in there.

Umm. Yes, you can also flip some bits in memory, and not hit anything
vital.

> >> Also, that panic() may cause hibernation to stop working in a sort of hard and
> >> nasty way where it used to work flawlessly previously and that would be a
> >> regression, so not really acceptable.
> >
> > Well, turning memory corruption bug into panic is an improvement, not
> > a regression.
> 
> Since we don't do anything about these problems today and presumably
> people use hibernation on the affected systems, there are reasons to
> think that the problem is not quite as grave as you're painting it.
> 
> But that aside, adding a panic() like in this patch isn't particularly
> useful anyway, because it panics the restore kernel.  It is sufficient
> to make arch_hibernation_header_restore() return an error to actually
> fail the resume and cause the restore kernel to discard the image.
> And that would preserve the information about the failure in the
> kernel log at least.

I don't think people are using hibernation today on affected systems
they are getting random oopses/panics, that's how this thread started.

Anyway, I agree that failing the resume is preferable to panic().

Thanks and best regards,
									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-31  0:27 ` Rafael J. Wysocki
@ 2016-08-31 11:07   ` Pavel Machek
  2016-08-31 11:43     ` Pavel Machek
  0 siblings, 1 reply; 22+ messages in thread
From: Pavel Machek @ 2016-08-31 11:07 UTC (permalink / raw)
  To: Rafael J. Wysocki
  Cc: Chen Yu, linux-pm, Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	x86, linux-kernel, Lee, Chun-Yi, Borislav Petkov

On Wed 2016-08-31 02:27:53, Rafael J. Wysocki wrote:
> On Monday, August 29, 2016 12:35:40 AM Chen Yu wrote:
> > On some platforms, there is occasional panic triggered when trying to
> > resume from hibernation, a typical panic looks like:
> > 
> > "BUG: unable to handle kernel paging request at ffff880085894000
> > IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> > 
> > This is because e820 map has been changed by BIOS across
> > hibernation, and one of the page frames from first kernel
> > is right located in second kernel's unmapped region, so panic
> > comes out when accessing unmapped kernel address.
> > 
> > In order to expose this issue earlier, the md5 hash of e820 map
> > is passed from suspend kernel to resume kernel, and the system will
> > trigger panic once it finds the md5 value of previous kernel is not
> > the same as current resume kernel.
> > 
> > Note:
> > 1. Without this patch applied, it is possible that BIOS has
> >    provided an inconsistent memory map, but the resume kernel is still
> >    able to restore the image anyway(e.g.,  E820_RAM region is the subset
> >    of the previous one), although the system might be unstable. So this
> >    patch tries to treat any inconsistent e820 as illegal.
> > 
> > 2. Another case is, this patch replies on comparing the e820_saved, but
> >    currently the e820_save might not be strictly the same across
> >    hibernation, even if BIOS has provided consistent e820 map - In
> >    theory mptable might modify the BIOS-provided e820_saved dynamically
> >    in early_reserve_e820_mpc_new, which would allocate a buffer from
> >    E820_RAM, and marks it from E820_RAM to E820_RESERVED). 
> >    This is a potential and rare case we need to deal with in OS in
> >    the future.
> > 
> > Suggested-by: Pavel Machek <pavel@ucw.cz>
> > Suggested-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
> > Cc: Lee, Chun-Yi <jlee@suse.com>
> > Cc: Borislav Petkov <bp@alien8.de>
> > Signed-off-by: Chen Yu <yu.c.chen@intel.com>
> > ---
> > v8:
> >  - Panic the system once the e820 is found to be inconsistent
> >    during resume.
> >    Fix the md5 hash len from 128 bytes to 16 bytes.
> > v7:
> >  - Use md5 hash to compare the e820 map.
> > v6:
> >  - Fix some compiling errors reported by 0day/LKP, adjust
> >    Kconfig/variable namings.
> > v5:
> >  - Rewrite this patch to just warn user of the broken BIOS
> >    when panic.
> > v4:
> >  - Add __attribute__ ((unused)) for swsusp_page_is_valid,
> >    to eliminate the warnning of:
> >    'swsusp_page_is_valid' defined but not used
> >    on non-x86 platforms.
> > 
> > v3:
> >  - Adjust the logic to exclude the end_pfn boundary in pfn_mapped
> >    when invoking mark_valid_pages, because the end_pfn is not
> >    a mapped page frame, we should not regard it as a valid page.
> > 
> >    Move the sanity check of valid pages to a early stage in resuming
> >    process(moved to mark_unsafe_pages), in this way, we can avoid
> >    unnecessarily accessing these invalid pages in later stage(yes,
> >    move to the original position Joey once introduced in:
> >    Commit 84c91b7ae07c ("PM / hibernate: avoid unsafe pages in e820
> >    reserved regions")
> > 
> >    With v3 patch applied, I did 30 cycles on my problematic platform,
> >    no panic triggered anymore(50% reproducible before patched, by
> >    plugging/unplugging memory peripheral during hibernation), and it
> >    just warns of invalid pages.
> > 
> > v2:
> >  - According to Ingo's suggestion, rewrite this patch.
> > 
> >    New version just checks each page frame according to pfn_mapped array.
> >    So that we do not need to touch existing code related to
> >    E820_RESERVED_KERN. And this method can naturely guarantee
> >    that the system before/after hibernation do not need to be of
> >    the same memory size on x86_64.
> > 
> > ---
> >  arch/x86/power/hibernate_64.c | 98 +++++++++++++++++++++++++++++++++++++++++++
> >  kernel/power/Kconfig          |  9 ++++
> >  2 files changed, 107 insertions(+)
> > 
> > diff --git a/arch/x86/power/hibernate_64.c b/arch/x86/power/hibernate_64.c
> > index 9634557..7eb27afd 100644
> > --- a/arch/x86/power/hibernate_64.c
> > +++ b/arch/x86/power/hibernate_64.c
> > @@ -11,6 +11,10 @@
> >  #include <linux/gfp.h>
> >  #include <linux/smp.h>
> >  #include <linux/suspend.h>
> > +#include <linux/scatterlist.h>
> > +#include <linux/kdebug.h>
> > +
> > +#include <crypto/hash.h>
> >  
> >  #include <asm/init.h>
> >  #include <asm/proto.h>
> > @@ -177,15 +181,100 @@ int pfn_is_nosave(unsigned long pfn)
> >  	return (pfn >= nosave_begin_pfn) && (pfn < nosave_end_pfn);
> >  }
> >  
> > +#define MD5_DIGEST_SIZE 16
> > +
> >  struct restore_data_record {
> >  	unsigned long jump_address;
> >  	unsigned long jump_address_phys;
> >  	unsigned long cr3;
> >  	unsigned long magic;
> > +	u8 e820_digest[MD5_DIGEST_SIZE];
> >  };
> >  
> >  #define RESTORE_MAGIC	0x123456789ABCDEF0UL
> 
> You're changing the image header format, so RESTORE_MAGIC needs to be updated
> too.

With !CONFIG_HIBERNATION_CHECK_E820, magic nothing changes in on-disk
format. (Unused space is now used).

If there's hibernation kernel is CONFIG_HIBERNATION_CHECK_E820, and
restore kernel is !CONFIG_HIBERNATION_CHECK_E820, we won't check the
E820, and that should be acceptable.

If there's hibernation kernel is !CONFIG_HIBERNATION_CHECK_E820, and
restore kernel is CONFIG_HIBERNATION_CHECK_E820, we'll fail the E820
check, and refuse to resume. That is also acceptable (and similar
result we'd get with RESTORE_MAGIC).. but the message will be
confusing.

Ok, so I guess we should change the magic.

Best regards,
									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-31 11:07   ` Pavel Machek
@ 2016-08-31 11:43     ` Pavel Machek
  2016-08-31 11:54       ` Rafael J. Wysocki
  0 siblings, 1 reply; 22+ messages in thread
From: Pavel Machek @ 2016-08-31 11:43 UTC (permalink / raw)
  To: Rafael J. Wysocki
  Cc: Chen Yu, linux-pm, Thomas Gleixner, Ingo Molnar, H. Peter Anvin,
	x86, linux-kernel, Lee, Chun-Yi, Borislav Petkov

On Wed 2016-08-31 13:07:31, Pavel Machek wrote:
> On Wed 2016-08-31 02:27:53, Rafael J. Wysocki wrote:
> > On Monday, August 29, 2016 12:35:40 AM Chen Yu wrote:
> > > On some platforms, there is occasional panic triggered when trying to
> > > resume from hibernation, a typical panic looks like:
> > > 
> > > "BUG: unable to handle kernel paging request at ffff880085894000
> > > IP: [<ffffffff810c5dc2>] load_image_lzo+0x8c2/0xe70"
> > > 
> > > This is because e820 map has been changed by BIOS across
> > > hibernation, and one of the page frames from first kernel
> > > is right located in second kernel's unmapped region, so panic
> > > comes out when accessing unmapped kernel address.
> > > 
> > > In order to expose this issue earlier, the md5 hash of e820 map
> > > is passed from suspend kernel to resume kernel, and the system will
> > > trigger panic once it finds the md5 value of previous kernel is not
> > > the same as current resume kernel.
> > > 
> > > Note:
> > > 1. Without this patch applied, it is possible that BIOS has
> > >    provided an inconsistent memory map, but the resume kernel is still
> > >    able to restore the image anyway(e.g.,  E820_RAM region is the subset
> > >    of the previous one), although the system might be unstable. So this
> > >    patch tries to treat any inconsistent e820 as illegal.
> > > 
> > > 2. Another case is, this patch replies on comparing the e820_saved, but
> > >    currently the e820_save might not be strictly the same across
> > >    hibernation, even if BIOS has provided consistent e820 map - In
> > >    theory mptable might modify the BIOS-provided e820_saved dynamically
> > >    in early_reserve_e820_mpc_new, which would allocate a buffer from
> > >    E820_RAM, and marks it from E820_RAM to E820_RESERVED). 
> > >    This is a potential and rare case we need to deal with in OS in
> > >    the future.
> > > 
> > > Suggested-by: Pavel Machek <pavel@ucw.cz>
> > > Suggested-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
> > > Cc: Lee, Chun-Yi <jlee@suse.com>
> > > Cc: Borislav Petkov <bp@alien8.de>
> > > Signed-off-by: Chen Yu <yu.c.chen@intel.com>
> > > ---
> > > v8:
> > >  - Panic the system once the e820 is found to be inconsistent
> > >    during resume.
> > >    Fix the md5 hash len from 128 bytes to 16 bytes.
> > > v7:
> > >  - Use md5 hash to compare the e820 map.
> > > v6:
> > >  - Fix some compiling errors reported by 0day/LKP, adjust
> > >    Kconfig/variable namings.
> > > v5:
> > >  - Rewrite this patch to just warn user of the broken BIOS
> > >    when panic.
> > > v4:
> > >  - Add __attribute__ ((unused)) for swsusp_page_is_valid,
> > >    to eliminate the warnning of:
> > >    'swsusp_page_is_valid' defined but not used
> > >    on non-x86 platforms.
> > > 
> > > v3:
> > >  - Adjust the logic to exclude the end_pfn boundary in pfn_mapped
> > >    when invoking mark_valid_pages, because the end_pfn is not
> > >    a mapped page frame, we should not regard it as a valid page.
> > > 
> > >    Move the sanity check of valid pages to a early stage in resuming
> > >    process(moved to mark_unsafe_pages), in this way, we can avoid
> > >    unnecessarily accessing these invalid pages in later stage(yes,
> > >    move to the original position Joey once introduced in:
> > >    Commit 84c91b7ae07c ("PM / hibernate: avoid unsafe pages in e820
> > >    reserved regions")
> > > 
> > >    With v3 patch applied, I did 30 cycles on my problematic platform,
> > >    no panic triggered anymore(50% reproducible before patched, by
> > >    plugging/unplugging memory peripheral during hibernation), and it
> > >    just warns of invalid pages.
> > > 
> > > v2:
> > >  - According to Ingo's suggestion, rewrite this patch.
> > > 
> > >    New version just checks each page frame according to pfn_mapped array.
> > >    So that we do not need to touch existing code related to
> > >    E820_RESERVED_KERN. And this method can naturely guarantee
> > >    that the system before/after hibernation do not need to be of
> > >    the same memory size on x86_64.
> > > 
> > > ---
> > >  arch/x86/power/hibernate_64.c | 98 +++++++++++++++++++++++++++++++++++++++++++
> > >  kernel/power/Kconfig          |  9 ++++
> > >  2 files changed, 107 insertions(+)
> > > 
> > > diff --git a/arch/x86/power/hibernate_64.c b/arch/x86/power/hibernate_64.c
> > > index 9634557..7eb27afd 100644
> > > --- a/arch/x86/power/hibernate_64.c
> > > +++ b/arch/x86/power/hibernate_64.c
> > > @@ -11,6 +11,10 @@
> > >  #include <linux/gfp.h>
> > >  #include <linux/smp.h>
> > >  #include <linux/suspend.h>
> > > +#include <linux/scatterlist.h>
> > > +#include <linux/kdebug.h>
> > > +
> > > +#include <crypto/hash.h>
> > >  
> > >  #include <asm/init.h>
> > >  #include <asm/proto.h>
> > > @@ -177,15 +181,100 @@ int pfn_is_nosave(unsigned long pfn)
> > >  	return (pfn >= nosave_begin_pfn) && (pfn < nosave_end_pfn);
> > >  }
> > >  
> > > +#define MD5_DIGEST_SIZE 16
> > > +
> > >  struct restore_data_record {
> > >  	unsigned long jump_address;
> > >  	unsigned long jump_address_phys;
> > >  	unsigned long cr3;
> > >  	unsigned long magic;
> > > +	u8 e820_digest[MD5_DIGEST_SIZE];
> > >  };
> > >  
> > >  #define RESTORE_MAGIC	0x123456789ABCDEF0UL
> > 
> > You're changing the image header format, so RESTORE_MAGIC needs to be updated
> > too.
> 
> With !CONFIG_HIBERNATION_CHECK_E820, magic nothing changes in on-disk
> format. (Unused space is now used).
> 
> If there's hibernation kernel is CONFIG_HIBERNATION_CHECK_E820, and
> restore kernel is !CONFIG_HIBERNATION_CHECK_E820, we won't check the
> E820, and that should be acceptable.
> 
> If there's hibernation kernel is !CONFIG_HIBERNATION_CHECK_E820, and
> restore kernel is CONFIG_HIBERNATION_CHECK_E820, we'll fail the E820
> check, and refuse to resume. That is also acceptable (and similar
> result we'd get with RESTORE_MAGIC).. but the message will be
> confusing.
> 
> Ok, so I guess we should change the magic.

Actually, no, simply changing the magic is not enough. I guess we
should change the magic, and either add "e820_digest_available" field,
or specify that e820_digest == {0,} means that no digest is
available. We should either ignore the digest in
CONFIG_HIBERNATION_CHECK_E820 case if it is not available, or fail
with different message.

Best regards,
									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-31 11:43     ` Pavel Machek
@ 2016-08-31 11:54       ` Rafael J. Wysocki
  0 siblings, 0 replies; 22+ messages in thread
From: Rafael J. Wysocki @ 2016-08-31 11:54 UTC (permalink / raw)
  To: Pavel Machek
  Cc: Rafael J. Wysocki, Chen Yu, Linux PM, Thomas Gleixner,
	Ingo Molnar, H. Peter Anvin, the arch/x86 maintainers,
	Linux Kernel Mailing List, Lee, Chun-Yi, Borislav Petkov

On Wed, Aug 31, 2016 at 1:43 PM, Pavel Machek <pavel@ucw.cz> wrote:
> On Wed 2016-08-31 13:07:31, Pavel Machek wrote:
>> On Wed 2016-08-31 02:27:53, Rafael J. Wysocki wrote:
>> > On Monday, August 29, 2016 12:35:40 AM Chen Yu wrote:

[cut]

>> > >
>> > > +#define MD5_DIGEST_SIZE 16
>> > > +
>> > >  struct restore_data_record {
>> > >   unsigned long jump_address;
>> > >   unsigned long jump_address_phys;
>> > >   unsigned long cr3;
>> > >   unsigned long magic;
>> > > + u8 e820_digest[MD5_DIGEST_SIZE];
>> > >  };
>> > >
>> > >  #define RESTORE_MAGIC    0x123456789ABCDEF0UL
>> >
>> > You're changing the image header format, so RESTORE_MAGIC needs to be updated
>> > too.
>>
>> With !CONFIG_HIBERNATION_CHECK_E820, magic nothing changes in on-disk
>> format. (Unused space is now used).
>>
>> If there's hibernation kernel is CONFIG_HIBERNATION_CHECK_E820, and
>> restore kernel is !CONFIG_HIBERNATION_CHECK_E820, we won't check the
>> E820, and that should be acceptable.
>>
>> If there's hibernation kernel is !CONFIG_HIBERNATION_CHECK_E820, and
>> restore kernel is CONFIG_HIBERNATION_CHECK_E820, we'll fail the E820
>> check, and refuse to resume. That is also acceptable (and similar
>> result we'd get with RESTORE_MAGIC).. but the message will be
>> confusing.
>>
>> Ok, so I guess we should change the magic.
>
> Actually, no, simply changing the magic is not enough. I guess we
> should change the magic, and either add "e820_digest_available" field,
> or specify that e820_digest == {0,} means that no digest is
> available. We should either ignore the digest in
> CONFIG_HIBERNATION_CHECK_E820 case if it is not available, or fail
> with different message.

Something like that.

Kernels with the same RESTORE_MAGIC have to use the same header format
and interpret all of the fields in it in the same way.

Thanks,
Rafael

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-08-30 11:54         ` Rafael J. Wysocki
@ 2016-09-08 21:15           ` Pavel Machek
  2016-09-09  7:36             ` Chen Yu
  0 siblings, 1 reply; 22+ messages in thread
From: Pavel Machek @ 2016-09-08 21:15 UTC (permalink / raw)
  To: Rafael J. Wysocki
  Cc: joeyli, Borislav Petkov, Chen Yu, linux-pm, Thomas Gleixner,
	Ingo Molnar, H. Peter Anvin, x86, linux-kernel, Lee

On Tue 2016-08-30 13:54:44, Rafael J. Wysocki wrote:
> On Tuesday, August 30, 2016 04:35:05 PM joeyli wrote:
> > On Mon, Aug 29, 2016 at 03:41:23PM +0200, Borislav Petkov wrote:
> > > On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> > > > Sounds about as easy as hot unplugging arbitrary memory address. IOW
> > > > "not easy".
> > > 
> > > Regardless, forcibly panicking the system more is still the wrong
> > > approach IMO.
> > > 
> > > Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
> > > that the user should disable hibernation on that box and never ever
> > > enable it again.
> > > 
> > > After that, the kernel should *disable* hibernation for the current boot
> > > so any further hibernation runs don't even happen. Maybe even taint
> > > itself.
> > >
> > 
> > I support this idea to disable hibernation when kernel detected e820 layout
> > was changed by BIOS. If system resume luckily then kernel should warn to user
> > and refuse to hibernate again. User must to know that's better to reboot
> > system when he saw the warning message after lucky resume.
> > 
> > Not just BIOS doesn't fix e820 layout. There have some machines doesn't provide
> > _S4_ function, so the hibernation fallbacks to "shutdown" mode because "platform"
> > mode unavailable. In this situation, user is just lucky to run the hibernation.
> > Kernel should warn to user and disable hibernation when detected e820 layout
> > changed.
> 
> Well, please see my reply to Boris.
> 
> Pavel is right that running after detecting an e820 mismatch is generally risky,
> so why don't we shut down the system (but try to do that cleanly instead of
> causing it to panic right away) on an e820 mismatch?

I don't think that's good idea.

Anything involving userspace is risky at that point, and clean
shutdown means a _lot_ of userspace.

We know the filesystems are reasonably clean as we sync-ed
them; I believe right solution is to panic -- on-disk state is pretty
good and we don't want to do anything risky.

Best regards,

									Pavel
-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-09-09  7:36             ` Chen Yu
@ 2016-09-09  7:33               ` Pavel Machek
  0 siblings, 0 replies; 22+ messages in thread
From: Pavel Machek @ 2016-09-09  7:33 UTC (permalink / raw)
  To: Chen Yu
  Cc: Rafael J. Wysocki, joeyli, Borislav Petkov, linux-pm,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin, x86, linux-kernel,
	Lee

On Fri 2016-09-09 15:36:42, Chen Yu wrote:
> Hi Pavel,
> On Thu, Sep 08, 2016 at 11:15:52PM +0200, Pavel Machek wrote:
> > On Tue 2016-08-30 13:54:44, Rafael J. Wysocki wrote:
> > > On Tuesday, August 30, 2016 04:35:05 PM joeyli wrote:
> > > > On Mon, Aug 29, 2016 at 03:41:23PM +0200, Borislav Petkov wrote:
> > > > > On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> > > > > > Sounds about as easy as hot unplugging arbitrary memory address. IOW
> > > > > > "not easy".
> > > > > 
> > > > > Regardless, forcibly panicking the system more is still the wrong
> > > > > approach IMO.
> > > > > 
> > > > > Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
> > > > > that the user should disable hibernation on that box and never ever
> > > > > enable it again.
> > > > > 
> > > > > After that, the kernel should *disable* hibernation for the current boot
> > > > > so any further hibernation runs don't even happen. Maybe even taint
> > > > > itself.
> > > > >
> > > > 
> > > > I support this idea to disable hibernation when kernel detected e820 layout
> > > > was changed by BIOS. If system resume luckily then kernel should warn to user
> > > > and refuse to hibernate again. User must to know that's better to reboot
> > > > system when he saw the warning message after lucky resume.
> > > > 
> > > > Not just BIOS doesn't fix e820 layout. There have some machines doesn't provide
> > > > _S4_ function, so the hibernation fallbacks to "shutdown" mode because "platform"
> > > > mode unavailable. In this situation, user is just lucky to run the hibernation.
> > > > Kernel should warn to user and disable hibernation when detected e820 layout
> > > > changed.
> > > 
> > > Well, please see my reply to Boris.
> > > 
> > > Pavel is right that running after detecting an e820 mismatch is generally risky,
> > > so why don't we shut down the system (but try to do that cleanly instead of
> > > causing it to panic right away) on an e820 mismatch?
> > 
> > I don't think that's good idea.
> > 
> > Anything involving userspace is risky at that point, and clean
> > shutdown means a _lot_ of userspace.
> > 
> > We know the filesystems are reasonably clean as we sync-ed
> > them; I believe right solution is to panic -- on-disk state is pretty
> > good and we don't want to do anything risky.
> >
> OK, we tried a milder solution that doesn't shutdown the system in the
> latest version, which terminates the restore process if a mismatch is found
> (hope people would be happy with that one :)

Actually, terminating the restore process is fine. Restoring into the
old state with different memory map and then attempting to shut down
would not be.

Best regards,
									Pavel

-- 
(english) http://www.livejournal.com/~pavelmachek
(cesky, pictures) http://atrey.karlin.mff.cuni.cz/~pavel/picture/horses/blog.html

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
  2016-09-08 21:15           ` Pavel Machek
@ 2016-09-09  7:36             ` Chen Yu
  2016-09-09  7:33               ` Pavel Machek
  0 siblings, 1 reply; 22+ messages in thread
From: Chen Yu @ 2016-09-09  7:36 UTC (permalink / raw)
  To: Pavel Machek
  Cc: Rafael J. Wysocki, joeyli, Borislav Petkov, linux-pm,
	Thomas Gleixner, Ingo Molnar, H. Peter Anvin, x86, linux-kernel,
	Lee

Hi Pavel,
On Thu, Sep 08, 2016 at 11:15:52PM +0200, Pavel Machek wrote:
> On Tue 2016-08-30 13:54:44, Rafael J. Wysocki wrote:
> > On Tuesday, August 30, 2016 04:35:05 PM joeyli wrote:
> > > On Mon, Aug 29, 2016 at 03:41:23PM +0200, Borislav Petkov wrote:
> > > > On Mon, Aug 29, 2016 at 09:15:00AM +0200, Pavel Machek wrote:
> > > > > Sounds about as easy as hot unplugging arbitrary memory address. IOW
> > > > > "not easy".
> > > > 
> > > > Regardless, forcibly panicking the system more is still the wrong
> > > > approach IMO.
> > > > 
> > > > Instead, I'd try to issue a big fat warning that BIOS corrupts E820 and
> > > > that the user should disable hibernation on that box and never ever
> > > > enable it again.
> > > > 
> > > > After that, the kernel should *disable* hibernation for the current boot
> > > > so any further hibernation runs don't even happen. Maybe even taint
> > > > itself.
> > > >
> > > 
> > > I support this idea to disable hibernation when kernel detected e820 layout
> > > was changed by BIOS. If system resume luckily then kernel should warn to user
> > > and refuse to hibernate again. User must to know that's better to reboot
> > > system when he saw the warning message after lucky resume.
> > > 
> > > Not just BIOS doesn't fix e820 layout. There have some machines doesn't provide
> > > _S4_ function, so the hibernation fallbacks to "shutdown" mode because "platform"
> > > mode unavailable. In this situation, user is just lucky to run the hibernation.
> > > Kernel should warn to user and disable hibernation when detected e820 layout
> > > changed.
> > 
> > Well, please see my reply to Boris.
> > 
> > Pavel is right that running after detecting an e820 mismatch is generally risky,
> > so why don't we shut down the system (but try to do that cleanly instead of
> > causing it to panic right away) on an e820 mismatch?
> 
> I don't think that's good idea.
> 
> Anything involving userspace is risky at that point, and clean
> shutdown means a _lot_ of userspace.
> 
> We know the filesystems are reasonably clean as we sync-ed
> them; I believe right solution is to panic -- on-disk state is pretty
> good and we don't want to do anything risky.
>
OK, we tried a milder solution that doesn't shutdown the system in the
latest version, which terminates the restore process if a mismatch is found
(hope people would be happy with that one :)
Here's the patch link per yours and Rafael's last comments on the old patch,
and I'm still doing some small adjustment and will send a newer one but it
is approximately similar to the following link:

https://patchwork.kernel.org/patch/9310497/
 

^ permalink raw reply	[flat|nested] 22+ messages in thread

* Re: [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value
@ 2016-08-29 21:08 Prarit Bhargava
  0 siblings, 0 replies; 22+ messages in thread
From: Prarit Bhargava @ 2016-08-29 21:08 UTC (permalink / raw)
  To: linux-kernel; +Cc: pavel, rafael.j.wysocki, jlee, bp, yu.c.chen


[My apologies for breaking threading.  I'm not sub'd to LKML ...]

On Mon 2016-08-29 00:35:40, Chen Yu wrote:
>+	if (memcmp(result, buf, MD5_DIGEST_SIZE)) {
>+		pr_err("PM: e820 map conflict detected.\n");
>+		panic("BIOS is playing funny tricks with us.\n");
>+	}

This should have a better explanation.  Perhaps

	BUG("PM: BIOS e820 map conflicts with map from previous boot.  S4/hibernate is
not supported on this platform.  Please contact your hardware vendor.\n");

or

	pr_crit(FW_BUG "BIOS e820 map conflicts with map from previous boot.");
	BUG("PM: S4/hibernate is broken on this platform.  Please contact your hardware
vendor for support.\n");

is more appropriate rather than having them filing a kernel.org BZ or
contacting an OS company with a bug that cannot be resolved in software.  There
are some other instances in the kernel where we've told them to do the same,
and it is appropriate to do so here.

P.

^ permalink raw reply	[flat|nested] 22+ messages in thread

end of thread, other threads:[~2016-09-09  7:33 UTC | newest]

Thread overview: 22+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-08-28 16:35 [PATCH][v8] PM / hibernate: Verify the consistent of e820 memory map by md5 value Chen Yu
2016-08-28 16:36 ` Pavel Machek
2016-08-29  4:59 ` Borislav Petkov
2016-08-29  7:15   ` Pavel Machek
2016-08-29 13:41     ` Borislav Petkov
2016-08-30  8:35       ` joeyli
2016-08-30 11:54         ` Rafael J. Wysocki
2016-09-08 21:15           ` Pavel Machek
2016-09-09  7:36             ` Chen Yu
2016-09-09  7:33               ` Pavel Machek
2016-08-30 11:51       ` Rafael J. Wysocki
2016-08-29 13:41   ` Rafael J. Wysocki
2016-08-29 15:13     ` Pavel Machek
2016-08-30 12:04       ` Rafael J. Wysocki
2016-08-30 19:53         ` Pavel Machek
2016-08-30 21:50           ` Rafael J. Wysocki
2016-08-31 11:03             ` Pavel Machek
2016-08-31  0:27 ` Rafael J. Wysocki
2016-08-31 11:07   ` Pavel Machek
2016-08-31 11:43     ` Pavel Machek
2016-08-31 11:54       ` Rafael J. Wysocki
2016-08-29 21:08 Prarit Bhargava

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).