]> Gitweb @ Texas Instruments - Open Source Git Repositories - git.TI.com/gitweb - glsdk/meta-ti-glsdk.git/blob - recipes-kernel/linux/linux-ti33x-psp-3.2/3.2.2/0125-mm-fix-NULL-ptr-dereference-in-__count_immobile_page.patch
linux-ti335x-psp 3.2: update to v3.2.11
[glsdk/meta-ti-glsdk.git] / recipes-kernel / linux / linux-ti33x-psp-3.2 / 3.2.2 / 0125-mm-fix-NULL-ptr-dereference-in-__count_immobile_page.patch
1 From a59b11463ac1c9a0baf19cf3e713a6dd5c2e5509 Mon Sep 17 00:00:00 2001
2 From: Michal Hocko <mhocko@suse.cz>
3 Date: Fri, 20 Jan 2012 14:33:55 -0800
4 Subject: [PATCH 125/130] mm: fix NULL ptr dereference in
5  __count_immobile_pages
7 commit 687875fb7de4a95223af20ee024282fa9099f860 upstream.
9 Fix the following NULL ptr dereference caused by
11   cat /sys/devices/system/memory/memory0/removable
13 Pid: 13979, comm: sed Not tainted 3.0.13-0.5-default #1 IBM BladeCenter LS21 -[7971PAM]-/Server Blade
14 RIP: __count_immobile_pages+0x4/0x100
15 Process sed (pid: 13979, threadinfo ffff880221c36000, task ffff88022e788480)
16 Call Trace:
17   is_pageblock_removable_nolock+0x34/0x40
18   is_mem_section_removable+0x74/0xf0
19   show_mem_removable+0x41/0x70
20   sysfs_read_file+0xfe/0x1c0
21   vfs_read+0xc7/0x130
22   sys_read+0x53/0xa0
23   system_call_fastpath+0x16/0x1b
25 We are crashing because we are trying to dereference NULL zone which
26 came from pfn=0 (struct page ffffea0000000000). According to the boot
27 log this page is marked reserved:
28 e820 update range: 0000000000000000 - 0000000000010000 (usable) ==> (reserved)
30 and early_node_map confirms that:
31 early_node_map[3] active PFN ranges
32     1: 0x00000010 -> 0x0000009c
33     1: 0x00000100 -> 0x000bffa3
34     1: 0x00100000 -> 0x00240000
36 The problem is that memory_present works in PAGE_SECTION_MASK aligned
37 blocks so the reserved range sneaks into the the section as well.  This
38 also means that free_area_init_node will not take care of those reserved
39 pages and they stay uninitialized.
41 When we try to read the removable status we walk through all available
42 sections and hope that the zone is valid for all pages in the section.
43 But this is not true in this case as the zone and nid are not initialized.
45 We have only one node in this particular case and it is marked as node=1
46 (rather than 0) and that made the problem visible because page_to_nid will
47 return 0 and there are no zones on the node.
49 Let's check that the zone is valid and that the given pfn falls into its
50 boundaries and mark the section not removable.  This might cause some
51 false positives, probably, but we do not have any sane way to find out
52 whether the page is reserved by the platform or it is just not used for
53 whatever other reasons.
55 Signed-off-by: Michal Hocko <mhocko@suse.cz>
56 Acked-by: Mel Gorman <mgorman@suse.de>
57 Cc: KAMEZAWA Hiroyuki <kamezawa.hiroyu@jp.fujitsu.com>
58 Cc: Andrea Arcangeli <aarcange@redhat.com>
59 Cc: David Rientjes <rientjes@google.com>
60 Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
61 Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
62 Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
63 ---
64  mm/page_alloc.c |   11 +++++++++++
65  1 file changed, 11 insertions(+)
67 diff --git a/mm/page_alloc.c b/mm/page_alloc.c
68 index 2b8ba3a..485be89 100644
69 --- a/mm/page_alloc.c
70 +++ b/mm/page_alloc.c
71 @@ -5608,6 +5608,17 @@ __count_immobile_pages(struct zone *zone, struct page *page, int count)
72  bool is_pageblock_removable_nolock(struct page *page)
73  {
74         struct zone *zone = page_zone(page);
75 +       unsigned long pfn = page_to_pfn(page);
76 +
77 +       /*
78 +        * We have to be careful here because we are iterating over memory
79 +        * sections which are not zone aware so we might end up outside of
80 +        * the zone but still within the section.
81 +        */
82 +       if (!zone || zone->zone_start_pfn > pfn ||
83 +                       zone->zone_start_pfn + zone->spanned_pages <= pfn)
84 +               return false;
85 +
86         return __count_immobile_pages(zone, page, 0);
87  }
88  
89 -- 
90 1.7.9.4