文件描述符为何会耗尽:从内核内存到OOM Killer的三层陷阱

2024年4月,Amazon EKS的一个GitHub issue报告了一个诡异现象:Elixir应用容器频繁被OOMKilled,但监控显示容器的内存使用量远低于限制。排查发现,真正的元凶是容器被配置了过高的文件描述符限制(1048576),每个文件描述符在内核中都会分配相应的数据结构,累积起来消耗了大量的内核内存,最终触发了OOM Killer。 ...

12 min · 5548 words

fsync()不是你想的那样:数据库持久化的致命误解

2018年3月,PostgreSQL开发者Craig Ringer在邮件列表中披露了一个令人震惊的发现:PostgreSQL对fsync()错误处理不当可能导致数据损坏。这个后来被称为"fsyncgate"的事件揭示了一个更深层的问题——许多开发者对fsync()的语义存在根本性误解。 ...

9 min · 4024 words

密码学的阿喀琉斯之踵:为什么「随机数」从来不是真正随机的?

2008年5月13日,Debian项目发布了一份紧急安全公告。公告的核心内容令人不寒而栗:过去近两年间,Debian及其衍生发行版中OpenSSL生成的所有密钥,都可以被轻松预测。 ...

11 min · 5303 words

BPF:一个"过期"技术的十五年逆袭

1992年12月,USENIX冬季会议上发表了一篇题为《The BSD Packet Filter: A New Architecture for User-level Packet Capture》的论文。作者Steven McCanne和Van Jacobson来自劳伦斯伯克利国家实验室,他们设计了一种新的内核架构用于网络数据包捕获。 ...

13 min · 6059 words

NUMA架构下为什么你的多线程程序可能比单线程还慢

在一台双路服务器上,某个开发者写了一个简单的多线程程序来处理内存数据。原本以为增加线程数能线性提升性能,结果却发现:当线程数从1增加到16时,吞吐量不升反降,甚至比单线程还慢了40%。 ...

10 min · 4757 words

OOM Killer 的评判算法为何总是杀错进程?从启发式评分到生产环境的生存指南

凌晨三点,线上告警。你打开监控面板,发现主数据库进程消失了,而那个只占用几兆内存的后台日志收集进程却安然无恙。dmesg 的输出冷酷而简洁: Out of memory: Kill process 18472 (postgres) score 891 or sacrifice child 这不是电影情节,而是无数运维工程师的真实经历。Linux 内核的 OOM Killer 本应是系统安全的最后一道防线,但它那套基于启发式评分的选杀机制,在过去二十多年里"误杀"了无数关键进程。问题来了:这套机制到底是怎么工作的?为什么数据库进程总是第一个被选中?又该如何让关键服务在内存危机中存活下来? ...

6 min · 2857 words

进程调度:为什么Linux放弃了O(1)的完美时间复杂度

2001年,Linus Torvalds在Linux内核邮件列表中写下了这样一句话:“你要意识到,很少有东西能像调度器那样经受住时间的考验。这恰好证明了调度是简单的。” ...

11 min · 5063 words