高并发C10K
C10k:服务器同时处理1W个TCP连接。
C10M:服务器同时处理1kw个TCP连接。
实现高并发的本质技术是事件驱动
和异步开发
。协程也是依靠这俩实现高并发的。
什么是事件?
最简单的,就是一个UDP请求
。
因为一个UDP请求通常仅由一个网络报文组成。
请求——事件——回调函数
并不是每个TCP报文都能生成事件
因为常见的HTTP等协议都是基于TCP实现的,TCP是一个面向字节流的协议,所以会导致HTTP请求的大小不受限制。
当一个HTTP请求的大小超过TCP报文的最大长度的时候,就会被拆分为多个报文,然后在接收端的缓冲区重组和排序,所以说,不是每个到达的TCP报文都能生成事件(不完整)。
事件与TCP的关系
事件只有2种类型——
- 读事件:表示有到达的消息需要处理
- 写事件:表示可以发送消息
三次握手建立连接的过程,会产生一读一写两个事件。
TCP是可以双向传输的,所以会一次在连接的2个方向上建立通道。
第二次握手结束,客户端->服务器的通道就建立好了,客户端就会产生写事件。
第三次握手,客户端发送的ACK报文到达服务器后,服务器产生读事件。
写事件比读事件复杂
看着有些多此一举
写缓冲区,write函数,进程
关闭连接
关闭连接的时候,被动方会产生读事件,从而调用close函数关闭连接。
服务器里面对资源的操作从快到慢,依次是CPU,内存,磁盘,网络。
前两个都很快,所以不需要考虑事件驱动。
然而磁盘和网络都需要采用事件驱动的异步方式
来处理。
当下的事件驱动,针对的都是网络事件。
网络事件是由内核产生的,进程使用epoll这样的多路复用技术就可以获取到它们(网络事件)。
多个请求复用了一个进程,叫做多路复用。
epoll是怎么获取到网络事件的?
太复杂了慢慢看
好我们这里直接进入总结——
网络报文到达后,内核就产生了读写事件,epoll函数的作用则是可以让进程高效地收集这些事件
。
还要确保在进程中处理每个事件的时间足够短,从而才能及时地处理所有的请求——这个过程中,要避免使用阻塞socket
,也要把耗时长的操作拆分成多份。
小结
epoll多路复用是一种机制,可以实现C10M的高并发服务。
因为网络消息的传输第一比较慢,第二也不可控,所以用网络事件驱动请求的性价比最高。
TCP报文是如何产生事件的?
在连接上收发消息的时候,也会产生事件,发送消息前的写事件与内核分配的缓冲区有关。
可以用多路复用技术获取事件。epoll的优势在于取消了收集事件的时候重复传递大量的socket参数。