仰天大笑出门去,我辈岂是蓬蒿人。这篇文章主要讲述Linux 内核 内存管理分区伙伴分配器 ⑦ ( z->watermark[WMARK_MIN] 最低水位计算 | min_free_kbytes 初始化 )相关的知识,希望能为你提供帮助。
文章目录
- ??一、z-> watermark[WMARK_MIN] 最低水位计算??
- ??二、min_free_kbytes 初始化过程??
- ??三、最低水位计算过程??
- ??四、nr_free_buffer_pages 函数原型??
- ??五、nr_free_zone_pages 函数原型??
?zone?
?? 结构体中的 ??watermark?
? 成员 表示 " 页分配器 " 使用的 区域水线 ;
struct zone
/* Read-mostly fields */
/* zone watermarks, access with *_wmark_pages(zone) macros */
unsigned long watermark[NR_WMARK];
源码路径 : linux-4.12\\include\\linux\\mmzone.h#255
其中涉及到的 ?
?NR_WMARK?
?? 值为 enum zone_watermarks
WMARK_MIN,
WMARK_LOW,
WMARK_HIGH,
NR_WMARK
;
#define min_wmark_pages(z) (z-> watermark[WMARK_MIN])
#define low_wmark_pages(z) (z-> watermark[WMARK_LOW])
#define high_wmark_pages(z) (z-> watermark[WMARK_HIGH])
源码路径 : linux-4.12\\include\\linux\\mmzone.h#255
其中 ?
?min_wmark_pages(z)?
?? 宏定义对应的 ??z->
watermark[WMARK_MIN]?
?? 需要通过 ??min_free_kbytes?
? 值进行计算 ,?
?min_free_kbytes?
? 表示 " 系统保留的最低空闲内存数 " ,二、min_free_kbytes 初始化过程
?
?min_free_kbytes?
?? 值在 ??init_per_zone_wmark_min?
? 函数中进行初始化 ,?
?lowmem_kbytes ?
? 用于统计 低内存 中超过 高水位 物理页的个数 ;
?
?lowmem_kbytes ?
? 是 高水位线 之上的内存 ;
内存区域 的 整体 物理页个数 是 zone 结构体中的 ?
?managed_pages ?
? 成员 ;
下图是整个内存区域的图 ;
lowmem_kbytes = nr_free_buffer_pages() * (PAGE_SIZE > > 10);
new_min_free_kbytes = int_sqrt(lowmem_kbytes * 16);
?
?min_free_kbytes ?
?? 值的范围是 if (new_min_free_kbytes > user_min_free_kbytes)
min_free_kbytes = new_min_free_kbytes;
if (min_free_kbytes < 128)
min_free_kbytes = 128;
if (min_free_kbytes > 65536)
min_free_kbytes = 65536;
?
?init_per_zone_wmark_min?
? 函数源码如下 :/*
* Initialise min_free_kbytes.
*
* For small machines we want it small (128k min).For large machines
* we want it large (64MB max).But it is not linear, because network
* bandwidth does not increase linearly with machine size.We use
*
*min_free_kbytes = 4 * sqrt(lowmem_kbytes), for better accuracy:
*min_free_kbytes = sqrt(lowmem_kbytes * 16)
*
* which yields
*
* 16MB:512k
* 32MB:724k
* 64MB:1024k
* 128MB: 1448k
* 256MB: 2048k
* 512MB: 2896k
* 1024MB:4096k
* 2048MB:5792k
* 4096MB:8192k
* 8192MB:11584k
* 16384MB: 16384k
*/
int __meminit init_per_zone_wmark_min(void)
unsigned long lowmem_kbytes;
int new_min_free_kbytes;
lowmem_kbytes = nr_free_buffer_pages() * (PAGE_SIZE > > 10);
new_min_free_kbytes = int_sqrt(lowmem_kbytes * 16);
if (new_min_free_kbytes > user_min_free_kbytes)
min_free_kbytes = new_min_free_kbytes;
if (min_free_kbytes < 128)
min_free_kbytes = 128;
if (min_free_kbytes > 65536)
min_free_kbytes = 65536;
else
pr_warn("min_free_kbytes is not updated to %d because user defined value %d is preferred\\n",
new_min_free_kbytes, user_min_free_kbytes);
setup_per_zone_wmarks();
refresh_zone_stat_thresholds();
setup_per_zone_lowmem_reserve();
#ifdef CONFIG_NUMA
setup_min_unmapped_ratio();
setup_min_slab_ratio();
#endif
return 0;
源码路径 : linux-4.12\\mm\\page_alloc.c#6976
三、最低水位计算过程先调用 linux-4.12\\mm\\page_alloc.c#4331 位置的 ?
?nr_free_buffer_pages?
? 函数 ,/**
* nr_free_buffer_pages - count number of pages beyond high watermark
*
* nr_free_buffer_pages() counts the number of pages which are beyond the high
* watermark within ZONE_DMA and ZONE_NORMAL.
*/
unsigned long nr_free_buffer_pages(void)
在该函数中调用了 linux-4.12\\mm\\page_alloc.c#4305 位置的 ?
?nr_free_zone_pages?
? 函数 ;
/**
* nr_free_zone_pages - count number of pages beyond high watermark
* @offset: The zone index of the highest zone
*
* nr_free_zone_pages() counts the number of counts pages which are beyond the
* high watermark within all zones at or below a given zone index.For each
* zone, the number of pages is calculated as:
*
*nr_free_zone_pages = managed_pages - high_pages
*/
static unsigned long nr_free_zone_pages(int offset)
四、nr_free_buffer_pages 函数原型
/**
* nr_free_buffer_pages - count number of pages beyond high watermark
*
* nr_free_buffer_pages() counts the number of pages which are beyond the high
* watermark within ZONE_DMA and ZONE_NORMAL.
*/
unsigned long nr_free_buffer_pages(void)
return nr_free_zone_pages(gfp_zone(GFP_USER));
源码路径 : linux-4.12\\mm\\page_alloc.c#4331
五、nr_free_zone_pages 函数原型【Linux 内核 内存管理分区伙伴分配器 ⑦ ( z->watermark[WMARK_MIN] 最低水位计算 | min_free_kbytes 初始化 )】
/**
* nr_free_zone_pages - count number of pages beyond high watermark
* @offset: The zone index of the highest zone
*
* nr_free_zone_pages() counts the number of counts pages which are beyond the
* high watermark within all zones at or below a given zone index.For each
* zone, the number of pages is calculated as:
*
*nr_free_zone_pages = managed_pages - high_pages
推荐阅读
- 从面试角度一文学完Kafka
- Redis实现并发阻塞锁方案
- Linux 内核 内存管理memblock 分配器 ③ ( memblock_region 内存块区域 | memblock_region 结构体成员分析 | memblock 分配器标志位 )
- 带你彻底吃透Spring
- redis优化系列高可用集群Redis Cluster的认识
- Linux 内核 内存管理伙伴分配器 ② ( 伙伴分配器分配内存流程 )
- [C++]C++入门到入土篇 HelloWorld 解析 && C++入门
- Python基础知识自检,离深入掌握 Python 还有多远
- [ 数据结构--C语言 ]不收藏必后悔系列--二叉树初阶