void __init page_ext_init(void) { unsigned long pfn; int nid; if (!invoke_need_callbacks()) return; for_each_node_state(nid, N_MEMORY) { unsigned long start_pfn, end_pfn; start_pfn = node_start_pfn(nid); end_pfn = node_end_pfn(nid); /* * start_pfn and end_pfn may not be aligned to SECTION and the * page->flags of out of node pages are not initialized. So we * scan [start_pfn, the biggest section's pfn < end_pfn) here. */ for (pfn = start_pfn; pfn < end_pfn; pfn = ALIGN(pfn + 1, PAGES_PER_SECTION)) { if (!pfn_valid(pfn)) continue; /* * Nodes's pfns can be overlapping. * We know some arch can have a nodes layout such as * -------------pfn--------------> * N0 | N1 | N2 | N0 | N1 | N2|.... */ if (pfn_to_nid(pfn) != nid) continue; if (init_section_page_ext(pfn, nid)) goto oom; } }
/* IAMROOT-12AB: * ------------- * FLATMEM을 사용하는 32bit ARM에서 사용 */ void __init page_ext_init_flatmem(void) { int nid, fail; /* IAMROOT-12AB: * ------------- * 디버깅을 위해 page_ext 구조체 할당이 필요한지 여부를 체크한다. * * page_ext_ops[]->need에 등록된 함수들에서 하나도 true 발생하지 않으면 return */ if (!invoke_need_callbacks()) return; /* IAMROOT-12AB: * ------------- * 노드가 사용하는 페이지 만큼 page_ext[]를 각 노드에 할당한다. * 각 노드의 node_page_ext는 할당된 메모리를 가리킨다. */ for_each_online_node(nid) { fail = alloc_node_page_ext(nid); if (fail) goto fail; } pr_info("allocated %ld bytes of page_ext\n", total_usage); invoke_init_callbacks(); return; fail: pr_crit("allocation of page_ext failed.\n"); panic("Out of memory"); }
void __init page_ext_init_flatmem(void) { int nid, fail; if (!invoke_need_callbacks()) return; for_each_online_node(nid) { fail = alloc_node_page_ext(nid); if (fail) goto fail; } pr_info("allocated %ld bytes of page_ext\n", total_usage); invoke_init_callbacks(); return; fail: pr_crit("allocation of page_ext failed.\n"); panic("Out of memory"); }