为完整起见, 我们介绍另一个内存分配的接口, 尽管我们不会准备使用它直到 15 章. 现 在, 能够说 struct page 是一个描述一个内存页的内部内核结构. 如同我们将见到的, 在内核中有许多地方有必要使用页结构; 它们是特别有用的, 在任何你可能处理高端内存 的情况下, 高端内存在内核空间中没有一个常量地址.
Linux 页分配器的真正核心是一个称为 alloc_pages_node 的函数:
struct page *alloc_pages_node(int nid, unsigned int flags, unsigned int order);
这个函数页有 2 个变体(是简单的宏); 它们是你最可能用到的版本:
struct page *alloc_pages(unsigned int flags, unsigned int order); struct page *alloc_page(unsigned int flags);
核心函数, alloc_pages_node, 使用 3 个参数, nid 是要分配内存的 NUMA 节点 ID[]30, flags 是通常的 GFP_ 分配标志, 以及 order 是分配的大小. 返回值是一个指向描述分 配的内存的第一个(可能许多)页结构的指针, 或者, 如常, NULL 在失败时.
alloc_pages 简化了情况, 通过在当前 NUMA 节点分配内存( 它使用 numa_node_id 的返 回值作为 nid 参数调用 alloc_pages_node). 并且, 当然, alloc_pages 省略了 order 参数并且分配一个单个页.
为释放这种方式分配的页, 你应当使用下列一个: void free_page(struct page *page);
void free_pages(struct page *page, unsigned int order); void free_hot_page(struct page *page);
void free_cold_page(struct page *page);
如果你对一个单个页的内容是否可能驻留在处理器缓存中有特殊的认识, 你应当使用 free_hot_page (对于缓存驻留的页) 或者 free_cold_page 通知内核. 这个信息帮助内 存分配器在系统中优化它的内存使用.