Nginx高效核心

目录

  • Nginx高效核心
  • Introduction
  • I/O特性
  • 同步/异步
  • 阻塞/非阻塞
  • 常见的I/O模型
  • 阻塞型
  • 非阻塞型
  • 多路复用模型(多路阻塞)
  • 信号驱动模型
  • 异步模型
  • Nginx中的I/O模型
  • Reference

Introduction

做最近的软工作业的时候,需要部署网站,比较了多款Web服务器之后,选择了短小精悍的Nginx,本文记录学习Nginx过程中理解到的Nginx高效的核心原因。

Nginx,Engine X简称,是一个高性能的HTTP服务器,和其他同类产品相比,Nginx一直以内存小、高并发闻名。

访问Nginx服务器,大致可以归结为一个网络I/O过程,而网络I/O的本质上是socket流的读取。对于socket流而言,通常分为两步,将数据从磁盘准备好然后从内核缓冲区复制到应用进程缓冲区,然后进行传送过程。

I/O特性

同步/异步

调用者、被调用者的消息的通信机制

  • 同步:调用者等待被调用者返回消息,才能继续执行,通常表现为轮询
  • 异步:被调用者通过状态、通知、回调等机制通知调用者自己的运行状态

阻塞/非阻塞

调用者在调用结束之前所处的状态

  • 阻塞:当调用结束之前,调用者被挂起
  • 非阻塞:无需等到调用结束,调用者可以继续执行其他任务

常见的I/O模型

下面的五种常见模型,前四种都是同步模型

阻塞型

在数据拷贝(内核空间、用户空间之间)完成之前,进程会一直阻塞,直到完成。如下图:

nginx 起别名 nginx nio_数据

发起recvfrom()调用的时候,系统会检查是否有准备好的数据,如果没有则等待(阻塞),当数据准备完成之后,将数据从内核空间复制到用户空间(依然阻塞),然后再返回。

非阻塞型

在数据拷贝(内核空间、用户空间之间)完成之前,进程不会一直阻塞,而是会继续执。如下图:

nginx 起别名 nginx nio_nginx 起别名_02

发起recvfrom()调用的时候,如果没有准备好的数据,进程会继续执行,但是执行过程中会轮询测试系统调用的状态,准备好之后再复制数据(阻塞),尽管比阻塞型有所改善,但轮询会消耗大量计算资源。

多路复用模型(多路阻塞)

多路复用是指对于一个I/O端口,可以多次调用,多次返回。如下图:

nginx 起别名 nginx nio_非阻塞_03

当进程发起select()调用的时候,这个函数也会使进程阻塞,但是和阻塞I/O不同的,它可以同时阻塞多个I/O操作,而且可以同时对多个读/写操作的I/O进行检测,直到有数据可读或可写时,才真正调用I/O操作函数。

信号驱动模型

仍然是多次调用多次返回,如下图:

nginx 起别名 nginx nio_数据_04

I/O伊始,给socket对应一个信号处理函数,然后进程继续执行,当数据准备完成之后,进程会受到一个SIGIO信号,然后调用信号处理函数进程I/O处理(仍然阻塞)。

异步模型

数据复制的时候无需阻塞,如下图:

nginx 起别名 nginx nio_数据_05

当发起aio_read()调用的时候,调用者不会立刻得到结果,二十要等所有操作结束之后才通知信号处理程序。

Nginx中的I/O模型

nginx 支持多种并发模型,并发模型的具体实现根据系统平台而有所不同。在支持多种并发模型的平台上,nginx自动选择最高效的模型,当然也可以手动指定。

Nginx的高并发性能正是因为Nginx采用了异步I/O模型(epoll()),而Apache等服务器采用的多路复用模型(select)。

epoll()优点:

  • 理论并发数无上限
  • 内存映射机制