当前位置: 首页 > news >正文

建设个人网站需要备案吗商城网站的模块设计

建设个人网站需要备案吗,商城网站的模块设计,品牌网站建设特色,个人博客ui设计在讲述文件映射的概念时,不可避免的要牵涉到虚存(SVR 4的VM).实际上,文件映射是虚存的中心概念, 文件映射一方面给用户提供了一组措施,好似用户将文件映射到自己地址空间的某个部分,使用简单的内存访问指令读写文件#xff1b;另一方面,它也可以用于内核的基本组织模式,在这种…  在讲述文件映射的概念时,不可避免的要牵涉到虚存(SVR 4的VM).实际上,文件映射是虚存的中心概念, 文件映射一方面给用户提供了一组措施,好似用户将文件映射到自己地址空间的某个部分,使用简单的内存访问指令读写文件另一方面,它也可以用于内核的基本组织模式,在这种模式种,内核将整个地址空间视为诸如文件之类的一组不同对象的映射.中的传统文件访问方式是,首先用open系统调用打开文件,然后使用read, write以及lseek等调用进行顺序或者随即的I/O.这种方式是非常低效的,每一次I/O操作都需要一次系统调用.另外,如果若干个进程访问同一个文件,每个进程都要在自己的地址空间维护一个副本,浪费了内存空间.而如果能够通过一定的机制将页面映射到进程的地址空间中,也就是说首先通过简单的产生某些内存管理数据结构完成映射的创建.当进程访问页面时产生一个缺页中断,内核将页面读入内存并且更新页表指向该页面.而且这种方式非常方便于同一副本的共享. VM是面向对象的方法设计的,这里的对象是指内存对象:内存对象是一个软件抽象的概念,它描述内存区与后备存储之间的映射.系统可以使用多种类型的后备存储,比如交换空间,本地或者远程文件以及帧缓存等等. VM系统对它们统一处理,采用同一操作集操作,比如读取页面或者回写页面等.每种不同的后备存储都可以用不同的方法实现这些操作.这样,系统定义了一套统一的接口,每种后备存储给出自己的实现方法.这样,进程的地址空间就被视为一组映射到不同数据对象上的的映射组成.所有的有效地址就是那些映射到数据对象上的地址.这些对象为映射它的页面提供了持久性的后备存储.映射使得用户可以直接寻址这些对象. 值得提出的是, VM体系结构独立于Unix系统,所有的Unix系统语义,如正文,数据及堆栈区都可以建构在基本VM系统之上.同时, VM体系结构也是独立于存储管理的,存储管理是由操作系统实施的,如:究竟采取什么样的对换和请求调页算法,究竟是采取分段还是分页机制进行存储管理,究竟是如何将虚拟地址转换成为物理地址等等(Linux中是一种叫Three Level Page Table的机制),这些都与内存对象的概念无关. 一、Linux中VM的实现. 一个进程应该包括一个mm_struct(memory manage struct), 该结构是进程虚拟地址空间的抽象描述,里面包括了进程虚拟空间的一些管理信息: start_code, end_code, start_data, end_data, start_brk, end_brk等等信息.另外,也有一个指向进程虚存区表(vm_area_struct: virtual memory area)的指针,该链是按照虚拟地址的增长顺序排列的.在Linux进程的地址空间被分作许多区(vma),每个区(vma)都对应虚拟地址空间上一段连续的区域, vma是可以被共享和保护的独立实体,这里的vma就是前面提到的内存对象.  下面是vm_area_struct的结构,其中,前半部分是公共的,与类型无关的一些数据成员,如:指向mm_struct的指针,地址范围等等,后半部分则是与类型相关的成员,其中最重要的是一个指向vm_operation_struct向量表的指针vm_ops, vm_pos向量表是一组虚函数,定义了与vma类型无关的接口.每一个特定的子类,即每种vma类型都必须在向量表中实现这些操作.这里包括了: open, close, unmap, protect, sync, nopage, wppage, swapout这些操作.  [cpp] view plaincopy struct vm_area_struct {        /*公共的, 与vma类型无关的 */        struct mm_struct * vm_mm;        unsigned long vm_start;        unsigned long vm_end;        struct vm_area_struct *vm_next;        pgprot_t vm_page_prot;        unsigned long vm_flags;        short vm_avl_height;        struct vm_area_struct * vm_avl_left;        struct vm_area_struct * vm_avl_right;        struct vm_area_struct *vm_next_share;        struct vm_area_struct **vm_pprev_share;        /* 与类型相关的 */        struct vm_operations_struct * vm_ops;        unsigned long vm_pgoff;        struct file * vm_file;        unsigned long vm_raend        void * vm_private_data;   };    vm_ops: open, close, no_page, swapin, swapout…… 二、驱动中的mmap()函数解析 设备驱动的mmap实现主要是将一个物理设备的可操作区域设备空间映射到一个进程的虚拟地址空间。这样就可以直接采用指针的方式像访问内存的方式访问设备。在驱动中的mmap实现主要是完成一件事就是实际物理设备的操作区域到进程虚拟空间地址的映射过程。同时也需要保证这段映射的虚拟存储器区域不会被进程当做一般的空间使用因此需要添加一系列的保护方式。 [cpp] view plaincopy /*主要是建立虚拟地址到物理地址的页表关系其他的过程又内核自己完成*/   static int mem_mmap(struct file* filp,struct vm_area_struct *vma)   {       /*间接的控制设备*/       struct mem_dev *dev  filp-private_data;              /*标记这段虚拟内存映射为IO区域并阻止系统将该区域包含在进程的存放转存中*/       vma-vm_flags | VM_IO;       /*标记这段区域不能被换出*/       vma-vm_flags | VM_RESERVED;          /**/       if(remap_pfn_range(vma,/*虚拟内存区域*/           vma-vm_start, /*虚拟地址的起始地址*/           virt_to_phys(dev-data)PAGE_SHIFT, /*物理存储区的物理页号*/        dev-size,    /*映射区域大小*/                   vma-vm_page_prot /*虚拟区域保护属性*/               ))           return -EAGAIN;          return 0;   }   具体的实现分析如下 vma-vm_flags | VM_IO; vma-vm_flags | VM_RESERVED; 上面的两个保护机制就说明了被映射的这段区域具有映射IO的相似性同时保证这段区域不能随便的换出。就是建立一个物理页与虚拟页之间的关联性。具体原理是虚拟页和物理页之间是以页表的方式关联起来虚拟内存通常大于物理内存在使用过程中虚拟页通过页表关联一切对应的物理页当物理页不够时会选择性的牺牲一些页也就是将物理页与虚拟页之间切断重现关联其他的虚拟页保证物理内存够用。在设备驱动中应该具体的虚拟页和物理页之间的关系应该是长期的应该保护起来不能随便被别的虚拟页所替换。具体也可参看关于虚拟存储器的文章。 接下来就是建立物理页与虚拟页之间的关系即采用函数remap_pfn_range(),具体的参数如下 int remap_pfn_range(structvm_area_struct *vma, unsigned long addr,unsigned long pfn, unsigned long size, pgprot_t prot) 1、struct vm_area_struct是一个虚拟内存区域结构体表示虚拟存储器中的一个内存区域。其中的元素vm_start是指虚拟存储器中的起始地址。 2、addr也就是虚拟存储器中的起始地址通常可以选择addr vma-vm_start。 3、pfn是指物理存储器的具体页号通常通过物理地址得到对应的物理页号具体采用virt_to_phys(dev-data)PAGE_SHIFT.首先将虚拟内存转换到物理内存然后得到页号。PAGE_SHIFT通常为12这是因为每一页的大小刚好是4K,这样右移12相当于除以4096得到页号。 4、size区域大小 5、区域保护机制。 返回值如果成功返回0否则正数。 三、系统调用mmap函数解析 介绍完VM的基本概念后,我们可以讲述mmap和munmap系统调用了.mmap调用实际上就是一个内存对象vma的创建过程, 1、mmap函数 Linux提供了内存映射函数mmap,它把文件内容映射到一段内存上(准确说是虚拟内存上),通过对这段内存的读取和修改,实现对文件的读取和修改 。普通文件被映射到进程地址空间后进程可以向访问普通内存一样对文件进行访问不必再调用read()write等操作。 先来看一下mmap的函数声明: [cpp] view plaincopy 头文件:    unistd.h    sys/mman.h       原型: void *mmap(void *addr, size_t length, int prot, int flags, int fd, off_t offsize);       /*  返回值: 成功则返回映射区起始地址, 失败则返回MAP_FAILED(-1).     参数:       addr: 指定映射的起始地址, 通常设为NULL, 由系统指定.       length: 将文件的多大长度映射到内存.       prot: 映射区的保护方式, 可以是:           PROT_EXEC: 映射区可被执行.           PROT_READ: 映射区可被读取.           PROT_WRITE: 映射区可被写入.           PROT_NONE: 映射区不能存取.       flags: 映射区的特性, 可以是:           MAP_SHARED: 对映射区域的写入数据会复制回文件, 且允许其他映射该文件的进程共享.           MAP_PRIVATE: 对映射区域的写入操作会产生一个映射的复制(copy-on-write), 对此区域所做的修改不会写回原文件.           此外还有其他几个flags不很常用, 具体查看linux C函数说明.       fd: 由open返回的文件描述符, 代表要映射的文件.       offset: 以文件开始处的偏移量, 必须是分页大小的整数倍, 通常为0, 表示从文件头开始映射.  */   mmap的作用是映射文件描述符fd指定文件的 [off,off len]区域至调用进程的[addr, addr len]的内存区域, 如下图所示: mmap系统调用的实现过程是 1.先通过文件系统定位要映射的文件 2.权限检查,映射的权限不会超过文件打开的方式,也就是说如果文件是以只读方式打开,那么则不允许建立一个可写映射  3.创建一个vma对象,并对之进行初始化  4.调用映射文件的mmap函数,其主要工作是给vm_ops向量表赋值 5.把该vma链入该进程的vma链表中,如果可以和前后的vma合并则合并 6.如果是要求VM_LOCKED(映射区不被换出)方式映射,则发出缺页请求,把映射页面读入内存中. 2、munmap函数 munmap(void * start, size_t length): 该调用可以看作是mmap的一个逆过程.它将进程中从start开始length长度的一段区域的映射关闭,如果该区域不是恰好对应一个vma,则有可能会分割几个或几个vma. msync(void * start, size_t length, int flags): 把映射区域的修改回写到后备存储中.因为munmap时并不保证页面回写,如果不调用msync,那么有可能在munmap后丢失对映射区的修改.其中flags可以是MS_SYNC, MS_ASYNC, MS_INVALIDATE, MS_SYNC要求回写完成后才返回, MS_ASYNC发出回写请求后立即返回, MS_INVALIDATE使用回写的内容更新该文件的其它映射.该系统调用是通过调用映射文件的sync函数来完成工作的. brk(void * end_data_segement): 将进程的数据段扩展到end_data_segement指定的地址,该系统调用和mmap的实现方式十分相似,同样是产生一个vma,然后指定其属性.不过在此之前需要做一些合法性检查,比如该地址是否大于mm-end_code, end_data_segement和mm-brk之间是否还存在其它vma等等.通过brk产生的vma映射的文件为空,这和匿名映射产生的vma相似,关于匿名映射不做进一步介绍.库函数malloc就是通过brk实现的. 四、实例解析下面这个例子显示了把文件映射到内存的方法源代码是 [cpp] view plaincopy /************关于本文 档********************************************  *filename: mmap.c  *purpose: 说明调用mmap把文件映射到内存的方法  *wrote by: zhoulifa(zhoulifa163.com) 周立发(http://zhoulifa.bokee.com)  Linux爱好者 Linux知识传播者 SOHO族 开发者 最擅长C语言  *date time:2008-01-27 18:59 上海大雪天据说是多年不遇  *Note: 任何人可以任意复制代码并运用这些文档当然包括你的商业用途  * 但请遵循GPL  *Thanks to:  *                Ubuntu 本程序在Ubuntu 7.10系统上测试完全正常  *                Google.com 我通常通过google搜索发现许多有用的资料  *Hope:希望越来越多的人贡献自己的力量为科学技术发展出力  * 科技站在巨人的肩膀上进步更快感谢有开源前辈的贡献  *********************************************************************/   #include sys/mman.h /* for mmap and munmap */   #include sys/types.h /* for open */   #include sys/stat.h /* for open */   #include fcntl.h     /* for open */   #include unistd.h    /* for lseek and write */   #include stdio.h      int main(int argc, char **argv)   {       int fd;       char *mapped_mem, * p;       int flength  1024;       void * start_addr  0;          fd  open(argv[1], O_RDWR | O_CREAT, S_IRUSR | S_IWUSR);       flength  lseek(fd, 1, SEEK_END);       write(fd, \0, 1); /* 在文件最后添加一个空字符以便下面printf正常工作 */       lseek(fd, 0, SEEK_SET);       mapped_mem  mmap(start_addr, flength, PROT_READ,        //允许读           MAP_PRIVATE,       //不允许其它进程访问此内存区域               fd, 0);              /* 使用映射区域. */       printf(%s\n, mapped_mem); /* 为了保证这里工作正常参数传递的文件名最好是一个文本文件 */       close(fd);       munmap(mapped_mem, flength);       return 0;   }   编译运行此程序 gcc -Wall mmap.c ./a.out text_filename 上面的方法因为用了PROT_READ所以只能读取文件里的内容不能修改如果换成PROT_WRITE就可以修改文件的内容了。又由于 用了MAAP_PRIVATE所以只能此进程使用此内存区域如果换成MAP_SHARED则可以被其它进程访问比如下面的 [cpp] view plaincopy #include sys/mman.h /* for mmap and munmap */   #include sys/types.h /* for open */   #include sys/stat.h /* for open */   #include fcntl.h     /* for open */   #include unistd.h    /* for lseek and write */   #include stdio.h   #include string.h /* for memcpy */      int main(int argc, char **argv)   {       int fd;       char *mapped_mem, * p;       int flength  1024;       void * start_addr  0;          fd  open(argv[1], O_RDWR | O_CREAT, S_IRUSR | S_IWUSR);       flength  lseek(fd, 1, SEEK_END);       write(fd, \0, 1); /* 在文件最后添加一个空字符以便下面printf正常工作 */       lseek(fd, 0, SEEK_SET);       start_addr  0x80000;       mapped_mem  mmap(start_addr, flength, PROT_READ|PROT_WRITE,        //允许写入           MAP_SHARED,       //允许其它进程访问此内存区域           fd, 0);          * 使用映射区域. */       printf(%s\n, mapped_mem); /* 为了保证这里工作正常参数传递的文件名最好是一个文本文 */       while((p  strstr(mapped_mem, Hello))) { /* 此处来修改文件 内容 */           memcpy(p, Linux, 5);           p  5;       }              close(fd);       munmap(mapped_mem, flength);       return 0;   }   五、mmap和共享内存对比 共享内存允许两个或多个进程共享一给定的存储区因为数据不需要来回复制所以是最快的一种进程间通信机制。共享内存可以通过mmap()映射普通文件特殊情况下还可以采用匿名映射机制实现也可以通过系统V共享内存机制实现。应用接口和原理很简单内部机制复杂。为了实现更安全通信往往还与信号灯等同步机制共同使用。 对比如下 mmap机制就是在磁盘上建立一个文件每个进程存储器里面单独开辟一个空间来进行映射。如果多进程的话那么不会对实际的物理存储器主存消耗太大。 shm机制每个进程的共享内存都直接映射到实际物理存储器里面。 1、mmap保存到实际硬盘实际存储并没有反映到主存上。优点储存量可以很大多于主存缺点进程间读取和写入速度要比主存的要慢。 2、shm保存到物理存储器主存实际的储存量直接反映到主存上。优点进程间访问速度读写比磁盘要快缺点储存量不能非常大多于主存 使用上看如果分配的存储量不大那么使用shm如果存储量大那么使用mmap。
http://www.huolong8.cn/news/435321/

相关文章:

  • 文件传输协议登陆网站wordpress评论发邮件
  • 网站备案复查四核网站建设
  • 循环视频做网站背景福州正规网站建设公司推荐
  • 全景地图网站开发我的电脑做网站服务器
  • 建设通网站怎么样wordpress微信公众平台开发教程
  • 网站推广是什么岗位怎么做一个软件
  • 网站建设申报书网页设计网站
  • 石家庄做网站裕华区网页设计研究生专业
  • 温州网站定制win2008安装wordpress
  • 高职思政主题网站建设作用房地产东莞网站建设
  • 百度宣传做网站多少钱推荐设计感强的网站
  • 做兼职的网站都有哪些工作影视公司宣传片
  • 怎样跟网站做优化呢店面设计有哪些
  • 女装店网站源码徐州手机模板建站
  • 做网站美工音乐网站开发工具
  • ins做甜品网站申请网站建设费
  • 如何设置网站标题用什么软件做网站hao
  • 网站建设需要钱吗wordpress最新博客主题
  • 关于数据机房建设的网站制作网站的页面设计怎么做
  • 网站注入木马哈尔滨优化调整人员流动管理
  • 快速一体化网站建设网站建设中一般要多久
  • 王野天照片广东网站营销seo费用
  • 建设厅网站上人员怎么导出中简风格wordpress主题
  • 屏蔽ip地址访问网站如何给网站做下载附件
  • 网站开发的软件学影视后期的正规学校
  • 做国外销售都上什么网站wordpress文章类型查询
  • 做网站需要学习什么知识温州地区做网站
  • 热门课程自己做网站沈阳广告设计公司
  • 家装效果图网站菜单设计制作图片
  • 能搜任何网站的浏览器网站制作公司商丘市