为什么我的系统在使用一小时后会使用更多 RAM?

S.G*_*ami 7 performance ram

我将 Arch Linux (5.1.8-arch1-1-ARCH) 与 XFCE DE 和 XFWM4 WM 一起使用。事情非常优雅,RAM 和 CPU 使用率很低。

启动后,当 DE 完全加载时,我看到 665 MiB 的 RAM 使用量。

但是打开 Atom、Code、Firefox、Chromium 等应用程序后,或在 GIMP、Blender 等中工作后,RAM 使用量增加,这是显而易见的。但是在关闭所有应用程序并只剩下一个 gnome-system-monitor 之后,我可以看到 RAM 使用量为 1.2 - 1.4 GiB。/proc/meminfo 与 gnome-system-monitor 一致,但 htop 始终给出不同的结果。

更糟糕的是,当我稍后打开一个占用 RAM 的应用程序时,它再次消耗 1.4 GiB 所需的内存。情况总是如此。/tmp/ 目录中不会存储任何可能增加到兆字节的文件。

另外,如果我查找使用那么多 RAM 的进程(从开始时的 700 MiB 到关闭浏览器后的 1.4 GiB !!),我什么也看不到。事实上,即使在运行 Arch ARM 的树莓派上我也遇到了同样的问题。

这是截图 1 这是截图2

红宝石代码:

#!/usr/bin/ruby -w
STDOUT.sync = true

loop do
    IO.readlines(File.join(%w(/ proc meminfo))).then { |x| [x[0], x[2]] }.map { |x| x.split[1].to_i }.reduce(:-)
        .tap { |x| print "\e[2K\rRAM Usage:".ljust(20), "#{x / 1024.0} MiB".ljust(24), "#{(x / 1000.0)} MB" }
    Kernel.sleep(0.1)
end
Run Code Online (Sandbox Code Playgroud)

cat /proc/meminfo命令具有以下输出:

MemTotal:        3851796 kB
MemFree:         1135680 kB
MemAvailable:    2055708 kB
Buffers:            1048 kB
Cached:          1463960 kB
SwapCached:          284 kB
Active:          1622148 kB
Inactive:         660952 kB
Active(anon):     923580 kB
Inactive(anon):   269360 kB
Active(file):     698568 kB
Inactive(file):   391592 kB
Unevictable:      107012 kB
Mlocked:              32 kB
SwapTotal:       3978216 kB
SwapFree:        3966696 kB
Dirty:               280 kB
Writeback:             0 kB
AnonPages:        924844 kB
Mapped:           563732 kB
Shmem:            374848 kB
KReclaimable:      74972 kB
Slab:             130016 kB
SReclaimable:      74972 kB
SUnreclaim:        55044 kB
KernelStack:        8000 kB
PageTables:        14700 kB
NFS_Unstable:          0 kB
Bounce:                0 kB
WritebackTmp:          0 kB
CommitLimit:     5904112 kB
Committed_AS:    3320548 kB
VmallocTotal:   34359738367 kB
VmallocUsed:           0 kB
VmallocChunk:          0 kB
Percpu:             1456 kB
HardwareCorrupted:     0 kB
AnonHugePages:         0 kB
ShmemHugePages:        0 kB
ShmemPmdMapped:        0 kB
HugePages_Total:       0
HugePages_Free:        0
HugePages_Rsvd:        0
HugePages_Surp:        0
Hugepagesize:       2048 kB
Hugetlb:               0 kB
DirectMap4k:      226736 kB
DirectMap2M:     3778560 kB
DirectMap1G:           0 kB
Run Code Online (Sandbox Code Playgroud)

首先你注意到 htop 从不同意。我对此知之甚少。

其次,您可以看到 xfdesktop 使用 44 MiB,其他一些进程使用一些内存,内核使用 ~150 MiB,除此之外,为什么我看到正在使用 1.5 GiB RAM?这真的会影响系统的性能吗?

the*_*rpy 20

未使用的 RAM 是浪费的 RAM。Linux 内核具有先进的内存管理功能,并试图避免给系统瓶颈、硬盘驱动器/SSD 带来负担。它尝试在内存中缓存文件。

内存管理系统以复杂的方式工作,更好的性能是目标。

您可以通过检查来了解它在做什么/proc/meminfo

cat /proc/meminfo

您可以使用“drop_caches”回收这个缓存的内存。但是,请注意文档说“不建议在测试或调试环境之外使用”,仅仅是因为“当再次需要它们时,重新创建丢弃的对象可能会花费大量的 I/O 和 CPU”:-)。

仅清除 PageCache:

# sync; echo 1 > /proc/sys/vm/drop_caches
Run Code Online (Sandbox Code Playgroud)

清除 dentry 和 inode:

# sync; echo 2 > /proc/sys/vm/drop_caches
Run Code Online (Sandbox Code Playgroud)

清除 PageCache、dentries 和 inode:

# sync; echo 3 > /proc/sys/vm/drop_caches
Run Code Online (Sandbox Code Playgroud)

请注意,sync将刷新文件系统缓冲区以确保已写入所有数据。

内核文档

页面缓存

物理内存是易失性的,将数据放入内存的常见情况是从文件中读取数据。每当读取文件时,都会将数据放入页面缓存中,以避免后续读取时进行昂贵的磁盘访问。类似地,当写入文件时,数据被放置在页面缓存中并最终进入后备存储设备。写入的页面被标记为脏,当 Linux 决定将它们重用于其他目的时,它会确保将设备上的文件内容与更新的数据同步。

回收

在整个系统生命周期中,一个物理页面可用于存储不同类型的数据。它可以是内核内部数据结构、设备驱动程序使用的 DMA 缓冲区、从文件系统读取的数据、用户空间进程分配的内存等。

根据页面使用情况,Linux 内存管理对其进行不同的处理。可以随时释放的页面,要么是因为它们缓存了其他地方可用的数据,例如,在硬盘上,要么是因为它们可以再次交换到硬盘,被称为可回收。最显着的可回收页面类别是页面缓存和匿名内存。

在大多数情况下,保存内部内核数据并用作 DMA 缓冲区的页面不能重新调整用途,并且在被用户释放之前它们将保持固定状态。此类页面称为不可回收。但是,在某些情况下,甚至可以回收被内核数据结构占用的页面。例如,文件系统元数据的内存缓存可以从存储设备中重新读取,因此当系统处于内存压力下时,可以将它们从主内存中丢弃。

释放可回收物理内存页面并重新利用它们的过程称为(惊喜!)回收。Linux 可以异步或同步回收页面,这取决于系统的状态。当系统未加载时,大部分内存是空闲的,分配请求将立即从空闲页面供应中得到满足。随着负载的增加,空闲页面的数量下降,当它达到某个阈值(高水位线)时,分配请求将唤醒 kswapd 守护进程。它将异步扫描内存页,如果它们包含的数据在其他地方可用,则释放它们,或者驱逐到后备存储设备(还记得那些脏页吗?)。随着内存使用量增加更多并达到另一个阈值 - 最小水印 - 分配将触发直接回收。在这种情况下,分配将停止,直到回收足够的内存页面以满足请求。

内存泄漏

现在,有些程序可能会出现“内存泄漏”,即它们“忘记”释放不再使用的内存。如果你让一个程序运行一段时间,你会看到这一点,它的内存使用量不断增加,当你关闭它时,内存永远不会被释放。现在,程序员当然会尽量避免内存泄漏,但程序可以有一些。回收此内存的方法是重新启动。

  • @thecarpy *“当你关闭它时,内存永远不会被释放。”* 这听起来不对。内核应该跟踪它分配给哪些进程的内存,使得在进程退出时回收该内存变得微不足道,而不管该进程是否曾调用过“free”或等价物。 (7认同)
  • Linux 内核在管理操作方面非常懒惰。如果我在新引导系统上分配 1GB 的 RAM,我可以看到我现在少了 1GB 的可用内存。如果之后我释放了内存,我确实释放了它,但是空闲内存量不会增加 1GB,因为内核仅在内存不足时才检查可用内存。上面的这些命令是否也让内核注意到我释放了 1GB 并因此增加了(显示的)可用内存量? (5认同)
  • 这个非常好的问题无法在评论中回答,请在本网站上提问,我或比我更了解的人,本网站上有很多,会回答。在您的问题中,在启动后包含 `cat /proc/meminfo` 的输出,然后在“释放内存/释放它”之后再一次。还提到您用来“释放内存”的命令。 (3认同)