快速业务通道

linux内存管理之非连续物理地址分配(vmalloc)

作者 佚名技术 来源 Linux系统 浏览 发布时间 2012-04-27
,它的程序流程与unmap_vm_area差不多,都是从pgd找到pte,如果同样的映射关系不存在,则新建之.(如:pgd对应的pmd不存在,则新建pmd项,使pgd指向建好的pmd.同理,如果pmd所映射的pte项不存在,则新建pte,然后建立映射),然后将pte映射到相应的页表.代码如下: 拥有帝国一切,皆有可能。欢迎访问phome.net

  int map_vm_area(struct vm_struct *area, pgprot_t prot, struct page ***pages)

  {

  unsigned long address = (unsigned long) area->addr;

  unsigned long end = address (area->size-PAGE_SIZE);

  pgd_t *dir;

  int err = 0;

  //vm 起始地址所在的页目录

  dir = pgd_offset_k(address);

  spin_lock(&init_mm.page_table_lock);

  do {

  pmd_t *pmd = pmd_alloc(&init_mm, dir, address);

  if (!pmd) {

  err = -ENOMEM;

  break;

  }

  //轮到pmd了 ^_^

  if (map_area_pmd(pmd, address, end - address, prot, pages)) {

  err = -ENOMEM;

  break;

  }

  address = (address PGDIR_SIZE) & PGDIR_MASK;

  dir ;

  } while (address && (address < end));

  spin_unlock(&init_mm.page_table_lock);

  flush_cache_vmap((unsigned long) area->addr, end);

  return err;

  }

  static int map_area_pmd(pmd_t *pmd, unsigned long address,

  unsigned long size, pgprot_t prot,

  struct page ***pages)

  {

  unsigned long base, end;

  base = address & PGDIR_MASK;

  address &= ~PGDIR_MASK;

  end = address size;

  if (end > PGDIR_SIZE)

  end = PGDIR_SIZE;

  do {

  pte_t * pte = pte_alloc_kernel(&init_mm, pmd, base address);

  if (!pte)

  return -ENOMEM;

  //轮到pte了 ^_^

  if (map_area_pte(pte, address, end - address, prot, pages))

  return -ENOMEM;

  address = (address PMD_SIZE) & PMD_MASK;

  pmd ;

  } while (address < end);

  return 0;

  }

  //为页表页建立映射关系

  static int map_area_pte(pte_t *pte, unsigned long address,

  unsigned long size, pgprot_t prot,

  struct page ***pages)

  {

  unsigned long end;

  address &= ~PMD_MASK;

  end = address size;

  if (end > PMD_SIZE)

  end = PMD_SIZE;

  do {

  struct page *page = **pages; 拥有帝国一切,皆有可能。欢迎访问phome.net

  其实,不管使用何种方式.线性地址到物理地址的转换最终都要经过硬件的页式管理去完成.所不同的是__get_free_page返回的线性地址是属于(PAGE_OFFSET,HIGH_MEMORY)之间的,这段线性地址在内核初始化的时候就完成了映射.而vmalloc使用的线性地址是属于(VMALLOC_START VMALLOC_END)之间的,也就是说属于一个临时映射区,为其建立映射关系.

原文地址 http://ericxiao.cublog.cn/

拥有帝国一切,皆有可能。欢迎访问phome.net

凌众科技专业提供服务器租用、服务器托管、企业邮局、虚拟主机等服务,公司网站:http://www.lingzhong.cn 为了给广大客户了解更多的技术信息,本技术文章收集来源于网络,凌众科技尊重文章作者的版权,如果有涉及你的版权有必要删除你的文章,请和我们联系。以上信息与文章正文是不可分割的一部分,如果您要转载本文章,请保留以上信息,谢谢!

分享到: 更多

Copyright ©1999-2011 厦门凌众科技有限公司 厦门优通互联科技开发有限公司 All rights reserved

地址(ADD):厦门软件园二期望海路63号701E(东南融通旁) 邮编(ZIP):361008

电话:0592-5908028 传真:0592-5908039 咨询信箱:web@lingzhong.cn 咨询OICQ:173723134

《中华人民共和国增值电信业务经营许可证》闽B2-20100024  ICP备案:闽ICP备05037997号