[kernel/f16] Better watermark the number of pages used by hibernation I/O (Bojan Smojver) (rhbz 785384)

Dave Jones davej at fedoraproject.org
Thu Apr 5 15:47:05 UTC 2012


commit 489a5d6586eb887cd65d44f45784fe8d1f480c7e
Author: Dave Jones <davej at redhat.com>
Date:   Thu Apr 5 11:46:57 2012 -0400

    Better watermark the number of pages used by hibernation I/O (Bojan Smojver) (rhbz 785384)

 hibernate-watermark.patch |   99 +++++++++++++++++++++++++++++++++++++++++++++
 kernel.spec               |    5 ++
 2 files changed, 104 insertions(+), 0 deletions(-)
---
diff --git a/hibernate-watermark.patch b/hibernate-watermark.patch
new file mode 100644
index 0000000..2cb75e6
--- /dev/null
+++ b/hibernate-watermark.patch
@@ -0,0 +1,99 @@
+
+--- a/kernel/power/swap.c	
++++ a/kernel/power/swap.c	
+@@ -6,7 +6,7 @@ 
+  *
+  * Copyright (C) 1998,2001-2005 Pavel Machek <pavel at ucw.cz>
+  * Copyright (C) 2006 Rafael J. Wysocki <rjw at sisk.pl>
+- * Copyright (C) 2010 Bojan Smojver <bojan at rexursive.com>
++ * Copyright (C) 2010-2012 Bojan Smojver <bojan at rexursive.com>
+  *
+  * This file is released under the GPLv2.
+  *
+@@ -51,6 +51,15 @@ 
+ 
+ #define MAP_PAGE_ENTRIES	(PAGE_SIZE / sizeof(sector_t) - 1)
+ 
++/*
++ * Number of pages required to be kept free while writing the image. Always
++ * three quarters of all available pages before the writing starts.
++ */
++static inline unsigned long reqd_free_pages(void)
++{
++	return (nr_free_pages() / 4) * 3;
++}
++
+ struct swap_map_page {
+ 	sector_t entries[MAP_PAGE_ENTRIES];
+ 	sector_t next_swap;
+@@ -72,7 +81,7 @@ struct swap_map_handle {
+ 	sector_t cur_swap;
+ 	sector_t first_sector;
+ 	unsigned int k;
+-	unsigned long nr_free_pages, written;
++	unsigned long reqd_free_pages;
+ 	u32 crc32;
+ };
+ 
+@@ -316,8 +325,7 @@ static int get_swap_writer(struct swap_map_handle *handle)
+ 		goto err_rel;
+ 	}
+ 	handle->k = 0;
+-	handle->nr_free_pages = nr_free_pages() >> 1;
+-	handle->written = 0;
++	handle->reqd_free_pages = reqd_free_pages();
+ 	handle->first_sector = handle->cur_swap;
+ 	return 0;
+ err_rel:
+@@ -352,11 +360,15 @@ static int swap_write_page(struct swap_map_handle *handle, void *buf,
+ 		handle->cur_swap = offset;
+ 		handle->k = 0;
+ 	}
+-	if (bio_chain && ++handle->written > handle->nr_free_pages) {
++	if (bio_chain && nr_free_pages() <= handle->reqd_free_pages) {
+ 		error = hib_wait_on_bio_chain(bio_chain);
+ 		if (error)
+ 			goto out;
+-		handle->written = 0;
++		/*
++		 * Recalculate the number of required free pages, to make sure
++		 * we never take more than a quarter.
++		 */
++		handle->reqd_free_pages = reqd_free_pages();
+ 	}
+  out:
+ 	return error;
+@@ -404,7 +416,7 @@ static int swap_writer_finish(struct swap_map_handle *handle,
+ #define LZO_THREADS	3
+ 
+ /* Maximum number of pages for read buffering. */
+-#define LZO_READ_PAGES	(MAP_PAGE_ENTRIES * 8)
++#define LZO_READ_PAGES	8192
+ 
+ 
+ /**
+@@ -615,10 +627,10 @@ static int save_image_lzo(struct swap_map_handle *handle,
+ 	}
+ 
+ 	/*
+-	 * Adjust number of free pages after all allocations have been done.
+-	 * We don't want to run out of pages when writing.
++	 * Adjust the number of required free pages after all allocations have
++	 * been done. We don't want to run out of pages when writing.
+ 	 */
+-	handle->nr_free_pages = nr_free_pages() >> 1;
++	handle->reqd_free_pages = reqd_free_pages();
+ 
+ 	/*
+ 	 * Start the CRC32 thread.
+@@ -1129,8 +1141,9 @@ static int load_image_lzo(struct swap_map_handle *handle,
+ 
+ 	/*
+ 	 * Adjust number of pages for read buffering, in case we are short.
++	 * Never take more than a quarter of all available pages.
+ 	 */
+-	read_pages = (nr_free_pages() - snapshot_get_image_size()) >> 1;
++	read_pages = (nr_free_pages() - snapshot_get_image_size()) / 4;
+ 	read_pages = clamp_val(read_pages, LZO_CMP_PAGES, LZO_READ_PAGES);
+ 
+ 	for (i = 0; i < read_pages; i++) {
diff --git a/kernel.spec b/kernel.spec
index a636cb9..220bafc 100644
--- a/kernel.spec
+++ b/kernel.spec
@@ -731,6 +731,7 @@ Patch12303: dmar-disable-when-ricoh-multifunction.patch
 Patch13003: efi-dont-map-boot-services-on-32bit.patch
 
 Patch14000: hibernate-freeze-filesystems.patch
+Patch14001: hibernate-watermark.patch
 
 Patch14010: lis3-improve-handling-of-null-rate.patch
 
@@ -1426,6 +1427,7 @@ ApplyPatch efi-dont-map-boot-services-on-32bit.patch
 
 # FIXME
 #ApplyPatch hibernate-freeze-filesystems.patch
+ApplyPatch hibernate-watermark.patch
 
 ApplyPatch lis3-improve-handling-of-null-rate.patch
 
@@ -2228,6 +2230,9 @@ fi
 # and build.
 
 %changelog
+* Thu Apr 05 2012 Dave Jones <davej at redhat.com>
+- Better watermark the number of pages used by hibernation I/O (Bojan Smojver) (rhbz 785384)
+
 * Wed Apr 04 2012 Josh Boyer <jwboyer at redhat.com> - 3.3.1-3
 - Disable runtime PM for hotpluggable ATA ports (rhbz 806676 807632)
 - Disable MID_PTI driver (rhbz 783561)


More information about the scm-commits mailing list