[Crash-utility] [PATCH 3/5] memory: skip compound pages when using search filter

Yu Zhao yuzhao at google.com
Thu Feb 5 21:06:46 UTC 2015


By default struct page.flags filter checks flags of every page. For
compound pages, some flags are only set to head page. The -g option
allows search to skip the whole compound page when the flags of head
page match the conditions.
---
 help.c   |  3 +++
 memory.c | 21 +++++++++++++++++----
 2 files changed, 20 insertions(+), 4 deletions(-)

diff --git a/help.c b/help.c
index 8d45667..716de33 100644
--- a/help.c
+++ b/help.c
@@ -2855,6 +2855,9 @@ char *help_search[] = {
 "              the mask is preceded by a letter n. When used multiple times, only",
 "              pages that meet all conditions will be searched. Only works for",
 "              virtual address space (either user or kernel).",
+"     -g",
+"              Skip whole compound page instead of only skipping head pages when",
+"              using with -f. Only has effect with -f.",
 "          -c  Search for character string values instead of unsigned longs.  If",
 "              the string contains any space(s), it must be encompassed by double",
 "              quotes.",
diff --git a/memory.c b/memory.c
index 70649a2..db7dddb 100644
--- a/memory.c
+++ b/memory.c
@@ -110,6 +110,7 @@ struct searchinfo {
 	ulong vaddr_end;
 	ulonglong paddr_start;
 	ulonglong paddr_end;
+	char pg_skip_compound_page;
 	int pg_nmasks;
 	char pg_mask_neg[MAXARGS];
 	ulong pg_mask[MAXARGS];
@@ -13514,7 +13515,7 @@ cmd_search(void)
 
 	searchinfo.mode = SEARCH_ULONG;	/* default search */
 
-	while ((c = getopt(argcnt, args, "tl:ukKVps:e:v:m:f:hwcx:")) != EOF) {
+	while ((c = getopt(argcnt, args, "tl:ukKVps:e:v:m:f:ghwcx:")) != EOF) {
                 switch(c)
                 {
 		case 'u':
@@ -13597,6 +13598,10 @@ cmd_search(void)
 			searchinfo.pg_nmasks++;
 			break;
 
+		case 'g':
+			searchinfo.pg_skip_compound_page = 1;
+			break;
+
 		case 'l':
 			len = stol(optarg, FAULT_ON_ERROR, NULL);
 			break;
@@ -14439,6 +14444,7 @@ skip_pages(struct searchinfo *si, struct mem_map_cache *mmc, ulong page, ulong *
 {
 	int i;
 	ulong flags;
+	int order;
 
 	if (page < mmc->start || page > mmc->end) {
 		mmc->start = page;
@@ -14461,11 +14467,18 @@ skip_pages(struct searchinfo *si, struct mem_map_cache *mmc, ulong page, ulong *
 	return 0;
 
 skip:
+	if (si->pg_skip_compound_page)
+		order = page + SIZE(page) < mmc->end ?
+		        __compound_order(mmc->cache + page - mmc->start) :
+		        compound_order(page);
+	else
+		order = 0;
+
 	if (CRASHDEBUG(5))
-		fprintf(fp, "ignore page: struct %lx, vaddr %lx, flags %lx\n",
-		        page, *pp, flags);
+		fprintf(fp, "ignore page: struct %lx, vaddr %lx, flags %lx, order %d\n",
+		        page, *pp, flags, order);
 
-	*pp += PAGESIZE();
+	*pp += PAGESIZE() * (1 << order);
 
 	return 1;
 }
-- 
2.2.0.rc0.207.ga3a616c




More information about the Crash-utility mailing list