什么用了Linux内存?低缓存,低缓冲区,不是虚拟机

Jas*_*son 11 memory linux

首先,是的,我读过LinuxAteMyRAM,这并不能解释我的情况。

# free -tm
             total       used       free     shared    buffers     cached
Mem:         48149      43948       4200          0          4         75
-/+ buffers/cache:      43868       4280
Swap:        38287          0      38287
Total:       86436      43948      42488
#
Run Code Online (Sandbox Code Playgroud)

如上图,-/+ buffers/cache:线条显示表示内存使用率非常高。但是,从 的输出中top,我没有看到任何进程使用了​​超过 100?MB 的内存。

那么,内存有什么用呢?

  PID USER      PR  NI  VIRT  RES  SHR S %CPU %MEM    TIME+  COMMAND
28078 root      18   0  327m  92m  10m S    0  0.2   0:25.06 java
31416 root      16   0  250m  28m  20m S    0  0.1  25:54.59 ResourceMonitor
21598 root     -98   0 26552  25m 8316 S    0  0.1  80:49.54 had
24580 root      16   0 24152  10m  760 S    0  0.0   1:25.87 rsyncd
 4956 root      16   0 62588  10m 3132 S    0  0.0  12:36.54 vxconfigd
26703 root      16   0  139m 7120 2900 S    1  0.0   4359:39 hrmonitor
21873 root      15   0 18764 4684 2152 S    0  0.0  30:07.56 MountAgent
21883 root      15   0 13736 4280 2172 S    0  0.0  25:25.09 SybaseAgent
21878 root      15   0 18548 4172 2000 S    0  0.0  52:33.46 NICAgent
21887 root      15   0 12660 4056 2168 S    0  0.0  25:07.80 SybaseBkAgent
17798 root      25   0 10652 4048 1160 S    0  0.0   0:00.04 vxconfigbackupd
Run Code Online (Sandbox Code Playgroud)

这是一台运行 x84_64 Linux 的 x86_64 机器(不是普通品牌服务器),而不是虚拟机中的容器。?内核(uname -a):

Linux 2.6.16.60-0.99.1-smp #1 SMP Fri Oct 12 14:24:23 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux
Run Code Online (Sandbox Code Playgroud)

内容/proc/meminfo

MemTotal:     49304856 kB
MemFree:       4066708 kB
Buffers:         35688 kB
Cached:         132588 kB
SwapCached:          0 kB
Active:       26536644 kB
Inactive:     17296272 kB
HighTotal:           0 kB
HighFree:            0 kB
LowTotal:     49304856 kB
LowFree:       4066708 kB
SwapTotal:    39206624 kB
SwapFree:     39206528 kB
Dirty:             200 kB
Writeback:           0 kB
AnonPages:      249592 kB
Mapped:          52712 kB
Slab:          1049464 kB
CommitLimit:  63859052 kB
Committed_AS:   659384 kB
PageTables:       3412 kB
VmallocTotal: 34359738367 kB
VmallocUsed:    478420 kB
VmallocChunk: 34359259695 kB
HugePages_Total:     0
HugePages_Free:      0
HugePages_Rsvd:      0
Hugepagesize:     2048 kB
Run Code Online (Sandbox Code Playgroud)

df报告没有来自tmpfs文件系统的大量内存消耗。

Maj*_*nko 4

Linux 上的内存对于诊断和理解来说可能是一个奇怪的野兽。

在正常操作下,大多数(如果不是全部)您的内存将被分配给一个或另一个任务。有些将分配给当前正在运行的前台进程。有些将存储从磁盘缓存的数据。有些将保存与在该特定时刻未主动执行的进程相关的数据。

Linux 中的进程有自己的虚拟地址空间(输出中的 VIRT top)。这包含与流程相关的所有数据,可以认为流程有多大。然而,所有内存都成为“真实”内存映射(输出中的 RES)的主动部分的情况很少见top。RES(常驻内存)是当时可以在 RAM 中直接访问的数据。除此之外还有共享内存(SHR)。它可以在同一进程的多个实例之间共享。因此,进程使用的内存在任何一个时间点都是 RES 加上 SHR,但如果有多个进程实例使用共享内存,则使用量是 RES 加上 RES 加上 RES ... 加上 SHR。

那么为什么 RES 和 VIRT 之间有区别呢?当然,如果一个进程有一块已分配的内存,那么它就已经分配了内存,不是吗?不会。内存是按页分配的,页可以是活动的,也可以是非活动的。活跃的就是 RES 中的内容。不活跃的是“其余的”。它们可以被推到一侧,因为它们目前未被访问。这意味着如果内存紧张,它们可以交换到磁盘。但它们不只是直接进入磁盘。首先,它们位于缓存中。您不想一直进行交换,因此应用程序和交换空间之间有一个缓冲区。当交换器选择不同的进程来执行并且不同的页面变得活动和非活动时,这些缓冲区不断变化。而这一切发生的速度对于人类来说是难以跟上的。

最重要的是磁盘缓冲区。非活动内存不仅会进入缓存,而且当该缓存被交换到磁盘时,它首先会进入磁盘缓冲区以排队等待写入。这是混合中的第二层缓存。这些磁盘缓冲区也被系统的其他部分用于一般 IO 缓冲。所以它们也在不断变化。

top因此,您在诸如此类的东西中看到的free要么是机器当前状态的即时快照,要么是一段时间内的聚合统计数据。当您阅读数据时,它已经过时了。

任何一个进程都可以访问大量内存,但这样做很少明智。无论如何,它无法一次访问所有内存,因此当前未查看的内存会被移至缓存,除非它被明确标记为“锁定在核心中”。

因此,应用程序“使用”的内存量和它“拥有”的内存量是完全不同的两件事。应用程序的大部分数据空间实际上都在缓存中,而不是在“核心”内存中,但由于缓存大部分时间都在 RAM 中,因此它可以立即可用,只需要“激活”即可成为“核心”内存。除非它已被换出到磁盘,否则当它需要取消交换时(如果它在缓冲区中,这可能会很快)。

由于野兽的高速特性以及数字总是在变化的事实,数字甚至可能在计算它们的过程中部分改变,因此永远不可能准确地说“这是正在使用的内存量”用户的视角。meminfo 是内核提供的及时快照,但由于它是正在执行的内核,因此它不一定显示任何一个进程内存使用情况的真实状态,因为当时没有进程主动执行 - 它位于进程之间。

就像我说的,这一切都非常令人困惑。

但归根结底,这真的不重要。重要的不是您有多少“可用”内存,而是您已使用了多少交换空间,以及交换空间被访问的频率。是交换导致系统速度减慢,而不是内存不足(尽管内存不足会导致过多的交换)。如果您有大量已用内存,但没有使用任何(或很少)交换空间,那么一切都是正常的。一般来说,空闲内存是不可取的,并且通常纯粹是过渡性的,因为它已用于一个目的,但尚未分配给另一个目的 - 例如它是缓存内存,并且已被交换到磁盘,但它还没有被用于其他任何用途,或者它是磁盘缓冲区,缓冲区已刷新到磁盘,但还没有应用程序请求它进行缓存。

  • 这确实很有趣,但并没有回答为什么OP会观察到这种特定差异的问题。 (6认同)
  • 您应该将其发布到您的博客上。这很好,但与这里无关。发生了一些奇怪的事情(我的意思是来自理解你所写内容的人的奇怪),因为进程的 VIRT 不考虑所有 RAM 使用情况,并且尽管有压力,系统也不会进行交换。 (5认同)