vm/min_free_kbytes - 为什么要保留最小保留内存?

use*_*877 21 linux operating-system memory-management

根据这篇文章:

/ proc/sys/vm/min_free_kbytes:它控制特殊储备可以免费使用的内存量,包括"原子"分配(那些不能等待回收的分配)

我的问题是"那些不能等待收回的人"是什么意思?换句话说,我想理解为什么需要告诉系统始终保持一定的最小内存空间以及在什么情况下使用这个内存?[必须用某种东西; 看不出其他的需要]

我的第二个问题:将此内存设置为高于4MB(在我的系统上)会导致更好的性能吗?我们有一台服务器偶尔表现出非常糟糕的shell性能(例如ls -l需要10-15秒才能执行),当某些进程开始运行时,如果将这个数字设置得更高将导致更好的shell性能?

小智 12

(链接已死,看起来现在在这里)

该文本指的是原子分配,它是对内存的请求,必须在不放弃控制的情况下满足(即当前线程不能被挂起).这种情况最常发生在中断例程中,但它适用于在保持基本锁定时需要内存的所有情况.这些分配必须是立即的,因为您无法等待交换器释放内存.

有关更全面的解释,请参阅Linux-MM,但这里是内存分配过程:

  • _alloc_pages首先遍历每个内存区域,查找包含符合条件的免费页面的第一个内存区域
  • _alloc_pages然后唤醒kswapd任务[..to ..]点击为每个区域维护的保留内存池.
  • 如果内存分配仍然不成功,_alloc页面将放弃[..] 在此过程中_alloc_pages执行cond_resched(),这可能会导致睡眠,这就是为什么禁止使用GFP_ATOMIC分配此分支的原因.

min_free_kbytes不太可能对描述的"ls -l需要10-15秒执行"提供很多帮助; 这可能是由一般记忆压力和交换而非区域耗尽引起的.min_free_kbytes设置只需要允许足够的空闲页面来处理即时请求.一旦恢复正常操作,就可以运行交换器进程来重新平衡内存区域.我不得不增加min_free_kbytes的唯一一次是在不支持dma散射的网卡上启用巨型帧之后.

要稍微扩展您的第二个问题,您将有更好的结果调整vm.swappiness和链接文章中提到的脏比率.但是,请注意,优化"ls -l"性能可能会导致其他进程变慢.永远不要针对非主要用例进行优化.

  • 当几乎所有的内存都被占用并且没有可用的交换空间时,Linux的性能对我来说往往会下降(例如,仅使用TTY1杀死Firefox就需要15分钟);将`/ proc / sys / vm / vfs_cache_pressure`提高到6000(默认是100)似乎有助于防止这种情况。但是,我不会在生产服务器上这样做。内核文档警告“将vfs_cache_pressure大大增加到100以上可能会对性能造成负面影响。” (2认同)

小智 7

所有Linux系统都会尝试利用系统可用的所有物理内存,通常是通过创建文件系统缓冲区缓存来实现的,该缓存只是一个I/O缓冲区,有助于提高系统性能.从技术上讲,即使将内存分配用于缓存,也不会使用此内存.

"等待回收",在您的问题中,指的是回收"未使用"的高速缓存存储器的过程,以便可以将其分配给进程.这应该是透明的,但在现实世界中有许多进程不等待这个内存变得可用.Java就是一个很好的例子,尤其是在设置了较大的最小堆大小的情况下.该进程尝试分配内存,如果它不能立即在一个大的连续(原子?)块中可用,则进程终止.

保留一定量的内存min_free_kbytes允许此内存立即可用,并在新进程需要启动,运行和完成时降低内存压力,同时存在高内存负载和完整缓冲区缓存.

4MB确实看起来相当低,因为如果缓冲区缓存已满,任何想要立即分配超过4MB的进程都可能会失败.该设置非常可调,并且特定于系统,但是如果你有几GB的可用内存,那么将备用内存提升到128MB就不会有什么坏处.我不确定它对shell交互性会产生什么影响,但可能是积极的.


小智 6

正常进程不会使用此内存.正如@Arno所提到的,可以运行的特殊进程包括必须立即运行的中断例程(因为它是一个中断),并且在任何其他进程可以运行之前完成(原子).这可以包括在内存已满时将内存交换到磁盘等内容.

如果内存已满,则会运行中断(内存管理)进程以将某些内存交换到磁盘中,以便释放一些内存供正常进程使用.但如果vm.min_free_kbytes它太小而无法运行,那么它会锁定系统.这是因为这个中断进程必须首先运行以释放内存,以便其他人可以运行,但之后它会被卡住,因为它没有足够的保留内存vm.min_free_kbytes来执行其任务导致死锁.

另见: