diff options
| -rw-r--r-- | include/linux/page_ext.h | 2 | ||||
| -rw-r--r-- | mm/page_owner.c | 26 |
2 files changed, 15 insertions, 13 deletions
diff --git a/include/linux/page_ext.h b/include/linux/page_ext.h index d2a2c84c72d0..c42981cd99aa 100644 --- a/include/linux/page_ext.h +++ b/include/linux/page_ext.h | |||
| @@ -40,7 +40,7 @@ struct page_ext { | |||
| 40 | #ifdef CONFIG_PAGE_OWNER | 40 | #ifdef CONFIG_PAGE_OWNER |
| 41 | unsigned int order; | 41 | unsigned int order; |
| 42 | gfp_t gfp_mask; | 42 | gfp_t gfp_mask; |
| 43 | struct stack_trace trace; | 43 | unsigned int nr_entries; |
| 44 | unsigned long trace_entries[8]; | 44 | unsigned long trace_entries[8]; |
| 45 | #endif | 45 | #endif |
| 46 | }; | 46 | }; |
diff --git a/mm/page_owner.c b/mm/page_owner.c index 9ab4a9b5bc09..0993f5f36b01 100644 --- a/mm/page_owner.c +++ b/mm/page_owner.c | |||
| @@ -59,20 +59,19 @@ void __reset_page_owner(struct page *page, unsigned int order) | |||
| 59 | 59 | ||
| 60 | void __set_page_owner(struct page *page, unsigned int order, gfp_t gfp_mask) | 60 | void __set_page_owner(struct page *page, unsigned int order, gfp_t gfp_mask) |
| 61 | { | 61 | { |
| 62 | struct page_ext *page_ext; | 62 | struct page_ext *page_ext = lookup_page_ext(page); |
| 63 | struct stack_trace *trace; | 63 | struct stack_trace trace = { |
| 64 | 64 | .nr_entries = 0, | |
| 65 | page_ext = lookup_page_ext(page); | 65 | .max_entries = ARRAY_SIZE(page_ext->trace_entries), |
| 66 | .entries = &page_ext->trace_entries[0], | ||
| 67 | .skip = 3, | ||
| 68 | }; | ||
| 66 | 69 | ||
| 67 | trace = &page_ext->trace; | 70 | save_stack_trace(&trace); |
| 68 | trace->nr_entries = 0; | ||
| 69 | trace->max_entries = ARRAY_SIZE(page_ext->trace_entries); | ||
| 70 | trace->entries = &page_ext->trace_entries[0]; | ||
| 71 | trace->skip = 3; | ||
| 72 | save_stack_trace(&page_ext->trace); | ||
| 73 | 71 | ||
| 74 | page_ext->order = order; | 72 | page_ext->order = order; |
| 75 | page_ext->gfp_mask = gfp_mask; | 73 | page_ext->gfp_mask = gfp_mask; |
| 74 | page_ext->nr_entries = trace.nr_entries; | ||
| 76 | 75 | ||
| 77 | __set_bit(PAGE_EXT_OWNER, &page_ext->flags); | 76 | __set_bit(PAGE_EXT_OWNER, &page_ext->flags); |
| 78 | } | 77 | } |
| @@ -84,6 +83,10 @@ print_page_owner(char __user *buf, size_t count, unsigned long pfn, | |||
| 84 | int ret; | 83 | int ret; |
| 85 | int pageblock_mt, page_mt; | 84 | int pageblock_mt, page_mt; |
| 86 | char *kbuf; | 85 | char *kbuf; |
| 86 | struct stack_trace trace = { | ||
| 87 | .nr_entries = page_ext->nr_entries, | ||
| 88 | .entries = &page_ext->trace_entries[0], | ||
| 89 | }; | ||
| 87 | 90 | ||
| 88 | kbuf = kmalloc(count, GFP_KERNEL); | 91 | kbuf = kmalloc(count, GFP_KERNEL); |
| 89 | if (!kbuf) | 92 | if (!kbuf) |
| @@ -121,8 +124,7 @@ print_page_owner(char __user *buf, size_t count, unsigned long pfn, | |||
| 121 | if (ret >= count) | 124 | if (ret >= count) |
| 122 | goto err; | 125 | goto err; |
| 123 | 126 | ||
| 124 | ret += snprint_stack_trace(kbuf + ret, count - ret, | 127 | ret += snprint_stack_trace(kbuf + ret, count - ret, &trace, 0); |
| 125 | &page_ext->trace, 0); | ||
| 126 | if (ret >= count) | 128 | if (ret >= count) |
| 127 | goto err; | 129 | goto err; |
| 128 | 130 | ||
