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

简单网站建设方案海拉尔网站设计

简单网站建设方案,海拉尔网站设计,wordpress主题用户中心,北京 个人网站 备案在看这篇文章之前#xff0c;可以先看看下面这几篇文章Linux内存#xff0c;先看这篇文章Linux内存寻址方式Linux虚拟内存TLBLinux物理内存初始化Linux io内存存在的意义~修改cmdline 把内存改成512MB用mtrace定位内存泄漏什么是内存泄漏#xff1f;Linux内存管理slub分配器… 在看这篇文章之前可以先看看下面这几篇文章Linux内存先看这篇文章Linux内存寻址方式Linux虚拟内存TLBLinux物理内存初始化Linux io内存存在的意义~修改cmdline 把内存改成512MB用mtrace定位内存泄漏什么是内存泄漏Linux内存管理slub分配器测试内存对齐对运行速度的影响内存屏障先看这篇文章CPU是如何访问到内存的Android系统下内存使用情况与监测Lowmemorykiller内存泄露分析1 mmap系统调用应用程序和驱动程序之间传递数据时可以通过read、write函数进行。这涉及在用户态buffer和内核态buffer之间传数据如下图所示应用程序不能直接读写驱动程序中的buffer需要在用户态buffer和内核态buffer之间进行一次数据拷贝。这种方式在数据量比较小时没什么问题但是数据量比较大时效率就太低了。比如更新LCD显示时如果每次都让APP传递一帧数据给内核假设LCD采用1024*600*32bpp的格式一帧数据就有1024*600*32/82.3MB左右这无法忍受。改进的方法就是让程序可以直接读写驱动程序中的buffer这可以通过mmap实现(memory map)把内核的buffer映射到用户态让APP在用户态直接读写。1.1 内存映射现象与数据结构假设有这样的程序名为test.c#includestdio.h #includeunistd.hint main(int argc, char **argv) {int a;printf(enter as value: \n);scanf(%d, a);printf(as address  0x%x, as value %d\n, a, a);while (1){sleep(10);}return 0; } 在Ubuntu上如下编译gcc -o test test.c 在2个命令行中分别执行test程序在第3个命令行中执行ps -a可以看到这2个程序同时存在如下图观察到这些现象① 2个程序同时运行它们的变量a的地址是不一样的。② 2个程序同时运行它们的变量a的值是不一样的一个是12另一个是123。疑问来了① 这2个程序同时在内存中运行它们在内存中的地址肯定不同比如变量a的地址肯定不同② 但是打印出来的变量a的地址却是一样的。怎么回事这里要引入虚拟地址的概念CPU发出的地址是虚拟地址它经过MMU(Memory Manage Unit内存管理单元)映射到物理地址上对于不同进程的同一个虚拟地址MMU会把它们映射到不同的物理地址。如下图当前运行的是app1时MMU会把CPU发出的虚拟地址addr映射为物理地址paddr1用paddr1去访问内存。当前运行的是app2时MMU会把CPU发出的虚拟地址addr映射为物理地址paddr2用paddr2去访问内存。MMU负责把虚拟地址映射为物理地址虚拟地址映射到哪个物理地址去映射关系保存在页表中vm_area_struct 结构体可以自行百度看看或者看看代码/** This struct defines a memory VMM memory area. There is one of these* per VM-area/task.  A VM area is any part of the process virtual memory* space that has a special rule for the page-fault handlers (ie a shared* library, the executable area etc).*/ struct vm_area_struct {/* The first cache line has the info for VMA tree walking. */unsigned long vm_start;  /* Our start address within vm_mm. */unsigned long vm_end;  /* The first byte after our end addresswithin vm_mm. *//* linked list of VM areas per task, sorted by address */struct vm_area_struct *vm_next, *vm_prev;struct rb_node vm_rb;/** Largest free memory gap in bytes to the left of this VMA.* Either between this VMA and vma-vm_prev, or between one of the* VMAs below us in the VMA rbtree and its -vm_prev. This helps* get_unmapped_area find a free area of the right size.*/unsigned long rb_subtree_gap;/* Second cache line starts here. */struct mm_struct *vm_mm; /* The address space we belong to. */pgprot_t vm_page_prot;  /* Access permissions of this VMA. */unsigned long vm_flags;  /* Flags, see mm.h. *//** For areas with an address space and backing store,* linkage into the address_space-i_mmap interval tree.** For private anonymous mappings, a pointer to a null terminated string* in the user process containing the name given to the vma, or NULL* if unnamed.*/union {struct {struct rb_node rb;unsigned long rb_subtree_last;} shared;const char __user *anon_name;};/** A files MAP_PRIVATE vma can be in both i_mmap tree and anon_vma* list, after a COW of one of the file pages. A MAP_SHARED vma* can only be in the i_mmap tree.  An anonymous MAP_PRIVATE, stack* or brk vma (with NULL file) can only be in an anon_vma list.*/struct list_head anon_vma_chain; /* Serialized by mmap_sem * page_table_lock */struct anon_vma *anon_vma; /* Serialized by page_table_lock *//* Function pointers to deal with this struct. */const struct vm_operations_struct *vm_ops;/* Information about our backing store: */unsigned long vm_pgoff;  /* Offset (within vm_file) in PAGE_SIZEunits, *not* PAGE_CACHE_SIZE */struct file * vm_file;  /* File we map to (can be NULL). */void * vm_private_data;  /* was vm_pte (shared mem) */#ifndef CONFIG_MMUstruct vm_region *vm_region; /* NOMMU mapping region */ #endif #ifdef CONFIG_NUMAstruct mempolicy *vm_policy; /* NUMA policy for the VMA */ #endifstruct vm_userfaultfd_ctx vm_userfaultfd_ctx; }; 解析如下① 每个APP在内核中都有一个task_struct结构体它用来描述一个进程② 每个APP都要占据内存在task_struct中用mm_struct来管理进程占用的内存内存在虚拟地址、物理地址mm_struct中用mmap来描述虚拟地址用pgd来描述对应的物理地址。注意pgdPage Global Directory页目录。③ 每个APP都有一系列的VMAvirtual memory比如APP含有代码段、数据段、BSS段、栈等等还有共享库。这些单元会保存在内存里它们的地址空间不同权限不同(代码段是只读的可运行的、数据段可读可写)内核用一系列的vm_area_struct来描述它们。vm_area_struct中的vm_start、vm_end是虚拟地址。④ vm_area_struct中虚拟地址如何映射到物理地址去每一个APP的虚拟地址可能相同物理地址不相同这些对应关系保存在pgd中。2 ARM架构内存映射简介ARM架构支持一级页表映射也就是说MMU根据CPU发来的虚拟地址可以找到第1个页表从第1个页表里就可以知道这个虚拟地址对应的物理地址。一级页表里地址映射的最小单位是1M。ARM架构还支持二级页表映射也就是说MMU根据CPU发来的虚拟地址先找到第1个页表从第1个页表里就可以知道第2级页表在哪里再取出第2级页表从第2个页表里才能确定这个虚拟地址对应的物理地址。二级页表地址旺射的最小单位有4K、1KLinux使用4K。一级页表项里的内容决定了它是指向一块物理内存还是指问二级页表如下图2.1一级页表映射过程一线页表中每一个表项用来设置1M的空间对于32位的系统虚拟地址空间有4G4G/1M4096。所以一级页表要映射整个4G空间的话需要4096个页表项。第0个页表项用来表示虚拟地址第0个1M(虚拟地址为00x1FFFFF)对应哪一块物理内存并且有一些权限设置第1个页表项用来表示虚拟地址第1个1M(虚拟地址为0x1000000x2FFFFF)对应哪一块物理内存并且有一些权限设置依次类推。使用一级页表时先在内存里设置好各个页表项然后把页表基地址告诉MMU就可以加动MMU了。以下图为例介绍地址映射过程① CPU发出虚拟地址vaddr假设为0x12345678② MMU根据vaddr[31:20]找到一级页表项虚拟地址0x12345678是虚拟地址空间里第0x123个1M所以找到页表里第0x123项根据此项内容知道它是一个段页表项。段内偏移是0x45678。③ 从这个表项里取出物理基地址Section Base Address假设是0x81000000④ 物理基地址加上段内偏移得到0x81045678所以CPU要访问虚拟地址0x12345678时实际上访问的是0x81045678的物理地址2.2二级页表映射过程首先设置好一级页表、二级页表并且把一级页表的首地址告诉MMU。以下图为例介绍地址映射过程① CPU发出虚拟地址vaddr假设为0x12345678② MMU根据vaddr[31:20]找到一级页表项虚拟地址0x12345678是虚拟地址空间里第0x123个1M所以找到页表里第0x123项。根据此项内容知道它是一个二级页表项。③ 从这个表项里取出地址假设是address这表示的是二级页表项的物理地址④ vaddr[19:12]表示的是二级页表项中的索引index即0x45在二级页表项中找到第0x45项⑤ 二级页表项中含有页基地址page base addr假设是0x81889000它跟vaddr[11:0]组合得到物理地址0x81889000 0x678 0x81889678。所以CPU要访问虚拟地址0x12345678时实际上访问的是0x81889678的物理地址3 怎么给APP新建一块内存映射3.1 mmap调用过程从上面内存映射的过程可以知道要给APP端新开劈一块虚拟内存并且让它指向某块内核buffer我们要做这些事① 得到一个vm_area_struct它表示APP的一块虚拟内存空间很幸运APP调用mmap系统函数时内核就帮我们构造了一个vm_area_stuct结构体。里面含有虚拟地址的地址范围、权限。② 确定物理地址你想映射某个内核buffer你需要得到它的物理地址这得由你提供。③ 给vm_area_struct和物理地址建立映射关系也很幸运内核提供有相关函数。APP里调用mmap时导致的内核相关函数调用过程如下3.2 cache和buffer本小节参考ARM的cache和写缓冲器write bufferhttps://blog.csdn.net/gameit/article/details/13169445使用mmap时需要有cache、buffer的知识。下图是CPU和内存之间的关系有cache、buffer(写缓冲器)。Cache是一块高速内存写缓冲器相当于一个FIFO可以把多个写操作集合起来一次写入内存。程序运行时有“局部性原理”这又分为时间局部性、空间局部性。① 时间局部性在某个时间点访问了存储器的特定位置很可能在一小段时间里会反复地访问这个位置。② 空间局部性访问了存储器的特定位置很可能在不久的将来访问它附近的位置。 而CPU的速度非常快内存的速度相对来说很慢。CPU要读写比较慢的内存时怎样可以加快速度根据“局部性原理”可以引入cache。① 读取内存addr处的数据时先看看cache中有没有addr的数据如果有就直接从cache里返回数据这被称为cache命中。如果cache中没有addr的数据则从内存里把数据读入注意它不是仅仅读入一个数据而是读入一行数据(cache line)。而CPU很可能会再次用到这个addr的数据或是会用到它附近的数据这时就可以快速地从cache中获得数据。 ② 写数据CPU要写数据时可以直接写内存这很慢也可以先把数据写入cache这很快。但是cache中的数据终究是要写入内存的啊这有2种写策略a. 写通(write through)数据要同时写入cache和内存所以cache和内存中的数据保持一致但是它的效率很低。能改进吗可以使用“写缓冲器”cache大哥你把数据给我就可以了我来慢慢写保证帮你写完。有些写缓冲器有“写合并”的功能比如CPU执行了4条写指令写第0、1、2、3个字节每次写1字节写缓冲器会把这4个写操作合并成一个写操作写word。对于内存来说这没什么差别但是对于硬件寄存器这就有可能导致问题。所以对于寄存器操作不会启动buffer功能对于内存操作比如LCD的显存可以启用buffer功能。 b. 写回(write back)新数据只是写入cache不会立刻写入内存cache和内存中的数据并不一致。新数据写入cache时这一行cache被标为“脏”(dirty)当cache不够用时才需要把脏的数据写入内存。使用写回功能可以大幅提高效率。但是要注意cache和内存中的数据很可能不一致。这在很多时间要小心处理比如CPU产生了新数据DMA把数据从内存搬到网卡这时候就要CPU执行命令先把新数据从cache刷到内存。反过来也是一样的DMA从网卡得过了新数据存在内存里CPU读数据之前先把cache中的数据丢弃。 是否使用cache、是否使用buffer就有4种组合(Linux内核文件arch\arm\include\asm\pgtable-2level.h)第1种是不使用cache也不使用buffer读写时都直达硬件这适合寄存器的读写。第2种是不使用cache但是使用buffer写数据时会用buffer进行优化可能会有“写合并”这适合显存的操作。因为对显存很少有读操作基本都是写操作而写操作即使被“合并”也没有关系。第3种是使用cache不使用buffer就是“writethrough”适用于只读设备在读数据时用cache加速基本不需要写。第4种是既使用cache又使用buffer适合一般的内存读写。 3 驱动程序要做的事驱动程序要做的事情有3点① 确定物理地址② 确定属性是否使用cache、buffer③ 建立映射关系 参考Linux源文件示例代码如下 还有一个更简单的函数 4 驱动编程我们在驱动程序中申请一个8K的buffer让APP通过mmap能直接访问。① 使用哪一个函数分配内存函数名说明kmalloc分配到的内存物理地址是连续的kzalloc分配到的内存物理地址是连续的内容清0vmalloc分配到的内存物理地址不保证是连续的vzalloc分配到的内存物理地址不保证是连续的内容清0我们应该使用kmalloc或kzalloc这样得到的内存物理地址是连续的在mmap时后APP才可以使用同一个基地址去访问这块内存。(如果物理地址不连续就要执行多次mmap了)。用一张图来描述mmap做的事情 mmap和malloc有点不同的是mmap在系统调用的时候去确定映射的地址。malloc的话申请到的空间实际上还没有分配物理内存这个是内核的lazy机制只有在真正往这个内存区域存数据的时候内核才会真正的给它分配物理内存。推荐阅读专辑|Linux文章汇总专辑|程序人生专辑|C语言我的知识小密圈关注公众号后台回复「1024」获取学习资料网盘链接。欢迎点赞关注转发在看您的每一次鼓励我都将铭记于心~
http://www.pierceye.com/news/685043/

相关文章:

  • 西安企业做网站贵州毕节建设局网站官网
  • 临沂网站定制室内设计师证书哪个含金量高
  • 国外做化工产品的网站湛江手机网站建设公司
  • 企业网站管理系统如何上传图片湖南网站建设营销推广
  • 网站建设衤金手指花总十五开发平台和开发工具
  • 免费网站安全软件大全游戏网络规划设计师资料及视频教程
  • 怎么把电脑网站做服务器吗做网站的回扣
  • 无锡模板网站设计公司中介网站设计
  • 微网站 手机网站html做一个学校网页
  • 重庆建设工程招标网站电商网站需要哪些备案
  • 有关网页设计与网站建设的文章崇信门户网站留言回复
  • 网站优化有哪些技巧对网站建设的建议
  • wordpress网站管理系统室内设计公司有哪些
  • 域名购买网站个人怎么在百度上打广告
  • 阳江市建设路龙源学校网站物流公司 网站模板
  • 迪庆州建设局网站做营销网站建设挣钱吗
  • 定制网站类似wordpress 简单
  • 数据库对于做网站的重要性商城模板网站模板
  • 梧州高端网站建设服务企业网站建设源码
  • 团购网站优化德州seo排名
  • 网站首页引导页中文简洁网站设计图
  • 娱乐网站排行榜在线商城网站开发代码
  • 手机网站设计通用尺寸上海外贸人才网
  • 智慧团建网站密码格式高端终端网站设计类网站
  • 福田网站设计网站建设平台方案
  • 荆州企业网站建设天津网站优化步骤
  • 网站怎么怎么做关键字长沙网站建设q.479185700強
  • 网站备案万网excel做网站
  • 十堰网站建设怎么做桐乡网站设计
  • 织梦商城网站模板网站设计的逻辑结构