aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJon Tollefson <kniht@linux.vnet.ibm.com>2008-07-24 00:27:52 -0400
committerLinus Torvalds <torvalds@linux-foundation.org>2008-07-24 13:47:19 -0400
commit53ba51d21d6e048424ab8aadfebdb1f25ae07b60 (patch)
tree0d5c5ee420e85f3a86ff7fe9151e7c3d547e7de1
parente11bfbfcb08ef4223b863799897c19cdf7c5bc00 (diff)
hugetlb: allow arch overridden hugepage allocation
Allow alloc_bootmem_huge_page() to be overridden by architectures that can't always use bootmem. This requires huge_boot_pages to be available for use by this function. This is required for powerpc 16G pages, which have to be reserved prior to boot-time. The location of these pages are indicated in the device tree. Acked-by: Adam Litke <agl@us.ibm.com> Signed-off-by: Jon Tollefson <kniht@linux.vnet.ibm.com> Signed-off-by: Nick Piggin <npiggin@suse.de> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
-rw-r--r--include/linux/hugetlb.h10
-rw-r--r--mm/hugetlb.c11
2 files changed, 13 insertions, 8 deletions
diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
index b2c17f62cacb..9a71d4cc88c8 100644
--- a/include/linux/hugetlb.h
+++ b/include/linux/hugetlb.h
@@ -39,6 +39,7 @@ void hugetlb_unreserve_pages(struct inode *inode, long offset, long freed);
39extern unsigned long hugepages_treat_as_movable; 39extern unsigned long hugepages_treat_as_movable;
40extern const unsigned long hugetlb_zero, hugetlb_infinity; 40extern const unsigned long hugetlb_zero, hugetlb_infinity;
41extern int sysctl_hugetlb_shm_group; 41extern int sysctl_hugetlb_shm_group;
42extern struct list_head huge_boot_pages;
42 43
43/* arch callbacks */ 44/* arch callbacks */
44 45
@@ -188,6 +189,14 @@ struct hstate {
188 char name[HSTATE_NAME_LEN]; 189 char name[HSTATE_NAME_LEN];
189}; 190};
190 191
192struct huge_bootmem_page {
193 struct list_head list;
194 struct hstate *hstate;
195};
196
197/* arch callback */
198int __init alloc_bootmem_huge_page(struct hstate *h);
199
191void __init hugetlb_add_hstate(unsigned order); 200void __init hugetlb_add_hstate(unsigned order);
192struct hstate *size_to_hstate(unsigned long size); 201struct hstate *size_to_hstate(unsigned long size);
193 202
@@ -256,6 +265,7 @@ static inline struct hstate *page_hstate(struct page *page)
256 265
257#else 266#else
258struct hstate {}; 267struct hstate {};
268#define alloc_bootmem_huge_page(h) NULL
259#define hstate_file(f) NULL 269#define hstate_file(f) NULL
260#define hstate_vma(v) NULL 270#define hstate_vma(v) NULL
261#define hstate_inode(i) NULL 271#define hstate_inode(i) NULL
diff --git a/mm/hugetlb.c b/mm/hugetlb.c
index 2a2f6e869401..3e1506b808a3 100644
--- a/mm/hugetlb.c
+++ b/mm/hugetlb.c
@@ -31,6 +31,8 @@ static int max_hstate;
31unsigned int default_hstate_idx; 31unsigned int default_hstate_idx;
32struct hstate hstates[HUGE_MAX_HSTATE]; 32struct hstate hstates[HUGE_MAX_HSTATE];
33 33
34__initdata LIST_HEAD(huge_boot_pages);
35
34/* for command line parsing */ 36/* for command line parsing */
35static struct hstate * __initdata parsed_hstate; 37static struct hstate * __initdata parsed_hstate;
36static unsigned long __initdata default_hstate_max_huge_pages; 38static unsigned long __initdata default_hstate_max_huge_pages;
@@ -925,14 +927,7 @@ static struct page *alloc_huge_page(struct vm_area_struct *vma,
925 return page; 927 return page;
926} 928}
927 929
928static __initdata LIST_HEAD(huge_boot_pages); 930__attribute__((weak)) int alloc_bootmem_huge_page(struct hstate *h)
929
930struct huge_bootmem_page {
931 struct list_head list;
932 struct hstate *hstate;
933};
934
935static int __init alloc_bootmem_huge_page(struct hstate *h)
936{ 931{
937 struct huge_bootmem_page *m; 932 struct huge_bootmem_page *m;
938 int nr_nodes = nodes_weight(node_online_map); 933 int nr_nodes = nodes_weight(node_online_map);