Skip to content

Commit 6dbecfd

Browse files
committed
PM / hibernate: Simplify mark_unsafe_pages()
Rework mark_unsafe_pages() to use a simpler method of clearing all bits in free_pages_map and to set the bits for the "unsafe" pages (ie. pages that were used by the image kernel before hibernation) with the help of duplicate_memory_bitmap(). For this purpose, move the pfn_valid() check from mark_unsafe_pages() to unpack_orig_pfns() where the "unsafe" pages are discovered. Signed-off-by: Rafael J. Wysocki <rafael.j.wysocki@intel.com>
1 parent 9c74448 commit 6dbecfd

File tree

1 file changed

+25
-39
lines changed

1 file changed

+25
-39
lines changed

kernel/power/snapshot.c

Lines changed: 25 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -2019,53 +2019,41 @@ int snapshot_read_next(struct snapshot_handle *handle)
20192019
return PAGE_SIZE;
20202020
}
20212021

2022+
static void duplicate_memory_bitmap(struct memory_bitmap *dst,
2023+
struct memory_bitmap *src)
2024+
{
2025+
unsigned long pfn;
2026+
2027+
memory_bm_position_reset(src);
2028+
pfn = memory_bm_next_pfn(src);
2029+
while (pfn != BM_END_OF_MAP) {
2030+
memory_bm_set_bit(dst, pfn);
2031+
pfn = memory_bm_next_pfn(src);
2032+
}
2033+
}
2034+
20222035
/**
20232036
* mark_unsafe_pages - mark the pages that cannot be used for storing
20242037
* the image during resume, because they conflict with the pages that
20252038
* had been used before suspend
20262039
*/
20272040

2028-
static int mark_unsafe_pages(struct memory_bitmap *bm)
2041+
static void mark_unsafe_pages(struct memory_bitmap *bm)
20292042
{
2030-
struct zone *zone;
2031-
unsigned long pfn, max_zone_pfn;
2043+
unsigned long pfn;
20322044

2033-
/* Clear page flags */
2034-
for_each_populated_zone(zone) {
2035-
max_zone_pfn = zone_end_pfn(zone);
2036-
for (pfn = zone->zone_start_pfn; pfn < max_zone_pfn; pfn++)
2037-
if (pfn_valid(pfn))
2038-
swsusp_unset_page_free(pfn_to_page(pfn));
2045+
/* Clear the "free"/"unsafe" bit for all PFNs */
2046+
memory_bm_position_reset(free_pages_map);
2047+
pfn = memory_bm_next_pfn(free_pages_map);
2048+
while (pfn != BM_END_OF_MAP) {
2049+
memory_bm_clear_current(free_pages_map);
2050+
pfn = memory_bm_next_pfn(free_pages_map);
20392051
}
20402052

2041-
/* Mark pages that correspond to the "original" pfns as "unsafe" */
2042-
memory_bm_position_reset(bm);
2043-
do {
2044-
pfn = memory_bm_next_pfn(bm);
2045-
if (likely(pfn != BM_END_OF_MAP)) {
2046-
if (likely(pfn_valid(pfn)))
2047-
swsusp_set_page_free(pfn_to_page(pfn));
2048-
else
2049-
return -EFAULT;
2050-
}
2051-
} while (pfn != BM_END_OF_MAP);
2053+
/* Mark pages that correspond to the "original" PFNs as "unsafe" */
2054+
duplicate_memory_bitmap(free_pages_map, bm);
20522055

20532056
allocated_unsafe_pages = 0;
2054-
2055-
return 0;
2056-
}
2057-
2058-
static void
2059-
duplicate_memory_bitmap(struct memory_bitmap *dst, struct memory_bitmap *src)
2060-
{
2061-
unsigned long pfn;
2062-
2063-
memory_bm_position_reset(src);
2064-
pfn = memory_bm_next_pfn(src);
2065-
while (pfn != BM_END_OF_MAP) {
2066-
memory_bm_set_bit(dst, pfn);
2067-
pfn = memory_bm_next_pfn(src);
2068-
}
20692057
}
20702058

20712059
static int check_header(struct swsusp_info *info)
@@ -2115,7 +2103,7 @@ static int unpack_orig_pfns(unsigned long *buf, struct memory_bitmap *bm)
21152103
/* Extract and buffer page key for data page (s390 only). */
21162104
page_key_memorize(buf + j);
21172105

2118-
if (memory_bm_pfn_present(bm, buf[j]))
2106+
if (pfn_valid(buf[j]) && memory_bm_pfn_present(bm, buf[j]))
21192107
memory_bm_set_bit(bm, buf[j]);
21202108
else
21212109
return -EFAULT;
@@ -2357,9 +2345,7 @@ prepare_image(struct memory_bitmap *new_bm, struct memory_bitmap *bm)
23572345
buffer = NULL;
23582346

23592347
nr_highmem = count_highmem_image_pages(bm);
2360-
error = mark_unsafe_pages(bm);
2361-
if (error)
2362-
goto Free;
2348+
mark_unsafe_pages(bm);
23632349

23642350
error = memory_bm_create(new_bm, GFP_ATOMIC, PG_SAFE);
23652351
if (error)

0 commit comments

Comments
 (0)