- 1、本文档共6页,可阅读全部内容。
- 2、有哪些信誉好的足球投注网站(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
- 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载。
- 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
linux内核中内存相关的操作函数.
linux内核中内存相关的操作函数
作者:harvey wang
邮箱:harvey.perfect@
新浪博客地址:/harveyperfect ,有关于减肥和学习英语相关的博文,欢迎交流
1、kmalloc()/kfree()
static __always_inline void *kmalloc(size_t size, gfp_t flags)
内核空间申请指定大小的内存区域,返回内核空间虚拟地址。在函数实现中,如果申请的内存空间较大的话,会从buddy系统申请若干内存页面,如果申请的内存空间大小较小的话,会从slab系统中申请内存空间。有关buddy和slab,请参见《linux内核之内存管理.doc》
gfp_t flags 的选项较多。参考内核文件gfp.h。
在函数kmalloc()实现中,如果申请的空间较小,会根据申请空间的大小从slab中获取;如果申请的空间较大,如超过一个页面,会直接从buddy系统中获取。
2、vmalloc()/vfree()
void *vmalloc(unsigned long size)
函数作用:从高端(如果存在,优先从高端)申请内存页面,并把申请的内存页面映射到内核的动态映射空间。vmalloc()函数的功能和alloc_pages(_GFP_HIGHMEM)+kmap() 的功能相似,只所以说是相似而不是相同,原因在于用vmalloc()申请的物理内存页面映射到内核的动态映射区(见下图),并且,用vmalloc()申请的页面的物理地址可能是不连续的。而alloc_pages(_GFP_HIGHMEM)+kmap()申请的页面的物理地址是连续的,被映射到内核的KMAP区。
vmalloc分配的地址则限于vmalloc_start与vmalloc_end之间。每一块vmalloc分配的内核虚拟内存都对应一个vm_struct结构体(可别和vm_area_struct搞混,那可是进程虚拟内存区域的结构),不同的内核虚拟地址被4k大小的空闲区间隔,以防止越界——见下图)。与进程虚拟地址的特性一样,这些虚拟地址与物理内存没有简单的位移关系,必须通过内核页表才可转换为物理地址或物理页。它们有可能尚未被映射,在发生缺页时才真正分配物理页面。如果内存紧张,连续区域无法满足,调用vmalloc分配是必须的,因为它可以将物理不连续的空间组合后分配,所以更能满足分配要求。vmalloc可以映射高端页框,也可以映射底端页框。vmalloc的作用只是为了提供逻辑上连续的地址。。。(分配顺序是HIGH, NORMAL, DMA )free_pages()
内核空间申请指定个数的内存页,内存页数必须是2^order个页。
alloc_pages(gfp_mask, order) 中,gfp_mask 是flag标志,其中可以为_ _GFP_DMA、_GFP_HIGHMEM 分别对应DMA和高端内存。
注:该函数基于buddy系统申请内存,申请的内存空间大小为2^order个内存页面。
参见《linux内核之内存管理.doc》
通过函数alloc_pages()申请的内存,需要使用kmap()函数分配内核的虚拟地址。
4、__get_free_pages()/__free_pages()
unsigned long __get_free_pages(gfp_t gfp_mask, unsigned int order)
作用相当于alloc_pages(NORMAL)+kmap(),但不能申请高端内存页面。
__get_free_page()只申请一个页面。
5、kmap()/kunmap()
返回指定页面对应内核空间的虚拟地址。
#include linux/highmem.h
void *kmap(struct page *page);
void kunmap(struct page *page);
? kmap 为系统中的任何页返回一个内核虚拟地址.?
? ? 对于低端内存页,它只返回页的逻辑地址;?
? ? 对于高端内存页, kmap在内核永久映射空间中创建一个特殊的映射.?这样的映射数目是有限, 因此最好不要持有过长的时间.?
? ? 使用 kmap 创建的映射应当使用 kunmap 来释放;? ??
kmap 调用维护一个计数器, 因此若2个或多个函数都在同一个页上调用kmap也是允许的.?通常情况下,内核永久映射空间是 4M 大小,因此仅仅需要一个页表即可,内核通过来 pkmap_page_table 寻找这个页表。kmalloc()和vmalloc()相比,kmalloc()总是从ZONE_NORMAL(下图中的直接映射区)申请内存。kma
文档评论(0)