the exiting makedumpfile is almost there... :)
Ken'ichi Ohmichi
oomichi at mxs.nes.nec.co.jp
Tue Sep 23 21:09:37 EDT 2008
Hi Dave, Jay,
Dave Anderson wrote:
> We just ran into a similar problem using an older version of makedumpfile,
> but looking at the latest makedumpfile code, it's seems that you could
> run into the same problem.
>
> In exclude_unnecessary_pages(), if a physical page is in a memory
> hole, then it skips the page and continues. In our case, that happened,
> but when it started up again, the next legitimate pfn was well beyond
> the previously-read cache of 512 pages. But since the new legit page
> wasn't modulo-512, it didn't refresh the page cache, and it ended up
> using stale page data (page->flags) and ended up excluding legitimate
> pages:
>
> for (; pfn < mmd->pfn_end;
> pfn++, mem_map += SIZE(page),
> paddr += info->page_size) {
>
> /*
> * Exclude the memory hole.
> */
> if (!is_in_segs(paddr))
> continue;
>
> if ((pfn % PGMM_CACHED) == 0) {
> if (pfn + PGMM_CACHED < mmd->pfn_end)
> pfn_mm = PGMM_CACHED;
> else
> pfn_mm = mmd->pfn_end - pfn;
> if (!readmem(VADDR, mem_map, page_cache,
> SIZE(page) * pfn_mm))
> goto out;
> }
>
> We fixed it by doing something like this:
>
> if (!is_in_segs(paddr)) {
> reset_cache = 1;
> continue;
> }
>
> if (((pfn % PGMM_CACHED) == 0) || reset_cache) {
> reset_cache = 0;
> ...
Great, you are right.
Thank you for fixing it :-)
Jay, could you try Dave's fixing like the attached patch ?
Thanks
Ken'ichi Ohmichi
---
diff -puN backup/makedumpfile-1.2.9/makedumpfile.c makedumpfile/makedumpfile.c
--- backup/makedumpfile-1.2.9/makedumpfile.c 2008-09-04 16:31:58.000000000 +0900
+++ makedumpfile/makedumpfile.c 2008-09-24 10:04:53.000000000 +0900
@@ -4130,6 +4130,7 @@ exclude_zero_pages(void)
int
exclude_unnecessary_pages(void)
{
+ int reset_cache;
unsigned int mm;
unsigned long mem_map;
unsigned long long pfn, paddr, pfn_mm;
@@ -4156,6 +4157,8 @@ exclude_unnecessary_pages(void)
if (mem_map == NOT_MEMMAP_ADDR)
continue;
+ reset_cache = 1;
+
for (; pfn < mmd->pfn_end;
pfn++, mem_map += SIZE(page),
paddr += info->page_size) {
@@ -4163,10 +4166,11 @@ exclude_unnecessary_pages(void)
/*
* Exclude the memory hole.
*/
- if (!is_in_segs(paddr))
+ if (!is_in_segs(paddr)) {
+ reset_cache = 1;
continue;
-
- if ((pfn % PGMM_CACHED) == 0) {
+ }
+ if (((pfn % PGMM_CACHED) == 0) || reset_cache) {
if (pfn + PGMM_CACHED < mmd->pfn_end)
pfn_mm = PGMM_CACHED;
else
@@ -4174,6 +4178,7 @@ exclude_unnecessary_pages(void)
if (!readmem(VADDR, mem_map, page_cache,
SIZE(page) * pfn_mm))
goto out;
+ reset_cache = 0;
}
pcache = page_cache + ((pfn%PGMM_CACHED) * SIZE(page));
flags = ULONG(pcache + OFFSET(page.flags));
More information about the kexec
mailing list