盘点Linux Epoll那些致命弱点

💡 原文中文,约7600字,阅读约需18分钟。
📝

内容提要

本文讨论了Linux上I/O多路复用技术面临的挑战及问题。在多线程扩展性方面,水平触发模式下存在过度唤醒问题,边缘触发模式下存在过度唤醒和饥饿问题。解决方法包括使用EPOLLEXCLUSIVE标志和EPOLLONESHOT模拟LT + EPOLLEXCLUSIVE效果。在处理大量TCP连接的read(2)方面,水平触发模式下存在数据错乱问题,边缘触发模式下也存在数据错乱问题。正确的做法是使用EPOLLONESHOT标志保证数据落到同一个线程上。另外,还讨论了epoll中文件描述符与文件描述的关系问题。

🎯

关键要点

  • 本文讨论了Linux上I/O多路复用技术面临的挑战及问题。
  • 水平触发模式下存在过度唤醒问题,边缘触发模式下存在过度唤醒和饥饿问题。
  • 解决方法包括使用EPOLLEXCLUSIVE标志和EPOLLONESHOT模拟LT + EPOLLEXCLUSIVE效果。
  • 处理大量TCP连接的read(2)方面,水平触发模式和边缘触发模式下均存在数据错乱问题。
  • 使用EPOLLONESHOT标志可以保证数据落到同一个线程上。
  • 讨论了epoll中文件描述符与文件描述的关系问题。
  • epoll的多线程扩展性问题主要体现在负载均衡上。
  • 在处理大量短连接的HTTP服务器时,epoll无法有效扩展到多个CPU。
  • 水平触发模式存在惊群效应,导致不必要的唤醒。
  • 边缘触发模式也存在不必要的唤醒和饥饿问题。
  • 正确的做法是使用EPOLLEXCLUSIVE标志或在ET模式下使用EPOLLONESHOT。
  • SO_REUSEPORT和BPF相关的socket选项可以作为替代方案。
  • 大量TCP连接的read(2)也面临扩展性问题,建议使用EPOLLEXCLUSIVE。
  • epoll的file descriptor与file description生命周期不一致的问题。
  • 调用close()时需先调用epoll_ctl(EPOLL_CTL_DEL)以避免潜在问题。
🏷️

标签

➡️

继续阅读