背景
终端产品给客户部署时,客户提出程序占用内存非常大,担心安装部署后对终端自身性能有较大的影响!
具体查看后实际是虚拟内存占用比较大。实际中如何解释这一现象。
原理
Linux系统,程序的虚拟内存与物理内存之所以可能表现出很大的差异,主要是因为Linux内存管理机制的设计。
以下是几个关键点解释这一现象,这里先一句话总结:程序编译中引入的任何三方库,打开的文件,访问的共享内存资源,自身及三方代码等等这些都需要有唯一的虚拟地址对应。所以虚拟内存大,只能说这个程序依赖多或者映射文件,映射共享之类。但有一点,虚拟内存不一定访问,如果一个库8G大,但我们只用其中两个函数,那么实际运行物理内存也只是用的时候给这两个函数分配物理内存。这一点后边还会说。
原理背景之虚拟内存
虚拟内存是操作系统为每个进程提供的一个独立的地址空间,这个空间远远大于实际可用的物理内存。
虚拟内存通过映射文件、匿名内存以及共享内存等不同的内存区域,为进程提供了一个统一且庞大的地址视图。
一直说32位机器2的32次方4G空间。64位机器寻址范围2的64次方,大型程序空间上t很常见。
原理背景之内存映射与分页
Linux使用分页机制管理内存。每个程序的虚拟地址空间被分割成多个固定大小的页面(通常为4KB)。当程序访问某个虚拟地址时,如果对应的物理页面不在RAM中(即未被缓存),则触发页错误(page fault),此时操作系统会从磁盘(如交换空间swap)加载相应的数据到物理内存,或者如果必要,会先将其他页面从物理内存换出到磁盘以腾出空间。
所以,程序虚拟内存管理是小块的,常规一页4k(大页内存除外),这样一块一块的,就像脚手架。当用的时候方便映射物理内存去使用,而不是说一个程序运行直接全部加载到物理内存。
原理背景之按需分配
物理内存只在程序真正使用到对应虚拟内存页面时才会分配。这意味着,即使程序申请了大量的虚拟内存,实际上并未立即消耗等量的物理内存。只有当程序实际写入数据到这些虚拟地址,导致页错误发生时,才会占用物理内存资源。
所以。用的时候才会分配物理地址映射,占用物理内存,换言之如果不用则永远不会分配物理内存映射,更不会占用物理内存。
原理背景之内存共享
对于共享库和可执行文件等,Linux通过内存映射使得多个进程可以共享同一块物理内存,尽管每个进程的虚拟地址空间中这部分看起来是独立的。这进一步减少了物理内存的使用。
共享库的共享就体现在这,多个程序都对齐进行引用,各自有自己虚拟地址,但操作系统实现物理的内存只映射一份。实现代码共享。
所以这样对设备而言,一次物理映射解决了多个共享该共享库进程的访问问题。这里这个库的虚拟内存只要用到他的都会重复分配虚拟内存,但物理内存是共享,并不会多份。
原理背景之缓存与交换
Linux内核会积极地利用空闲的物理内存作为磁盘缓存,以加速文件读写操作。同时,当物理内存紧张时,会将不活跃的内存页面交换到磁盘的交换空间中,释放物理内存给更活跃的进程使用。
结论
综上所述,Linux系统通过虚拟内存机制和高效的内存管理策略,使得程序能够拥有较大的地址空间,而实际消耗的物理内存则根据运行时的实际需求动态调整,从而实现高效利用有限的物理内存资源。
因此,虚拟内存可能上t单位,但这并不影响物理内存只有2G,所以即使虚拟内存很大,实际仅代表这个程序大、虚拟地址分配的多,和物理内存占用并没直接关系。