我有两台redis服务器在同一台机器上运行。第二个日志文件有几个实例,其中包含以下通知:
[50818] 19 Feb 06:41:05.007 * 10 changes in 300 seconds. Saving...
[50818] 19 Feb 06:41:05.007 # Can't save in background: fork: Cannot allocate memory
相比之下,第一个日志文件只包含成功的数据库保存。如果我内存不足,我估计两者都有类似的日志。令我困惑的是,只有一个人有这个问题,另一个没有。任何线索?
此外,研究引导我this blog post,他认为如果我在命令行上sysctl vm.overcommit_memory=1
,问题可以得到改善。没有解释这有何帮助。有人可以在redis的背景下解释这里发生了什么吗?
答案 0 :(得分:23)
按照Redis FAQs:
背景保存在Linux下出现fork()错误,即使我有大量空闲内存也是如此!
简短回答:
echo 1 > /proc/sys/vm/overcommit_memory
:)现在是长篇:
Redis后台保存模式依赖于写时复制的语义 在现代操作系统中分叉:Redis分叉(创建一个孩子 process)是父级的精确副本。子进程转储 磁盘上的DB最终退出。理论上,孩子应该使用as 作为父母的副本有很多记忆,但实际上要归功于 大多数现代操作系统实现的copy-on-write语义 父进程和子进程将共享公共内存页面。一个 页面只有在孩子或孩子中发生变化时才会重复 家长。因为理论上所有页面都可能在孩子时发生变化 进程是保存的,Linux无法预先告诉了多少内存 如果
overcommit_memory
设置为零,则子项将采用 fork将失败,除非真正需要尽可能多的可用RAM 复制所有父内存页面,结果如果你 有一个3 GB的Redis数据集,只有2 GB的可用内存 失败。将overcommit_memory
设置为1表示Linux可以放松并执行 叉子以更乐观的分配方式,这确实是 你想要什么Redis。了解Linux虚拟内存如何工作的好资源
overcommit_memory
和overcommit_ratio
的替代方法就是这样 红帽杂志的经典着作“理解虚拟记忆”。谨防, 本文为overcommit_memory
提供了1和2个配置值 反转:请参阅proc(5)手册页以了解正确的含义 可用的值。