libevent2-介绍

一.Libevent在window上的实现-->iocp
1.iocp是什么

IOCP (Input/Output Completion Ports) 是 Windows 操作系统提供的一种高性能、可扩展的异步 I/O 模型。这种模型基于事件驱动,可以大幅提升 I/O 操作的效率和并发量,尤其适合处理大量连接和大量数据流的网络应用。IOCP 主要包含三个组件:I/O 端口完成端口工作者线程池。I/O 端口用来描述文件句柄或套接字,完成端口用来存储已完成的 I/O 请求以及通知工作者线程处理请求,工作者线程池则负责执行 I/O 操作和相关的业务逻辑。

2.iocp基本原理

IOCP 的基本原理是通过事件驱动的方式来处理 I/O 请求,以避免传统的阻塞式 I/O 操作带来的性能问题。具体来说,IOCP 通过以下几个步骤完成异步 I/O 操作:

(1)应用程序首先创建一个或多个 I/O 端口,并将它们关联到套接字或文件句柄上。

(2)当应用程序需要进行 I/O 操作时,它调用系统级别的 API,将请求提交到 I/O 端口上。

(3)操作系统内核将 I/O 请求与相应的 I/O 端口关联,并立即返回,使得应用程序可以继续执行其他操作。

(4)内核在后台异步地执行 I/O 操作,并将结果存储在完成队列中。

(5)当 I/O 操作完成时,内核会通知完成端口,并将完成信息添加到完成队列中。

(6)应用程序通过调用 GetQueuedCompletionStatus() 函数获取完成队列中的已完成请求,并按需处理它们。

(7)如果完成队列为空,则应用程序可以等待新的完成事件发生,或者继续执行其他操作。

以上过程中,工作者线程负责从完成队列中取出已完成的 I/O 请求,并进行相应的处理。由于这些线程都是从线程池中获取的,因此可以有效地管理和控制线程的数量和使用情况,从而提高系统的效率和稳定性。

3.应用场景

IOCP 的高性能、可扩展特性使其广泛应用于以下几个领域:

(1)网络编程。IOCP 可以帮助网络应用程序实现高并发、低延迟的数据传输,尤其适合处理大量连接和大量数据流的场景,如网络游戏、在线聊天、视频流媒体等。

(2)数据库操作。IOCP 可以加速数据库操作中的文件读写、网络传输等 I/O 操作,提升数据库系统的性能和稳定性。

(3)高性能服务器开发。IOCP 可以作为一种高效的事件驱动模型,帮助服务器应用程序快速响应客户端请求,提高系统的吞吐量和并发度。

(4)多线程编程。IOCP 可以帮助开发者实现多线程编程中的任务分配和负载均衡,提高代码执行效率和并行度。

总之,IOCP 在需要高性能、高并发、低延迟的应用场景下具有很大的优势,并且可以有效地避免传统阻塞式 I/O 带来的性能问题。

二.reactor简介

reactor最重要的两个元素:IO和事件。既然libevent封装了reactor,那么需要了解reactor中IO、事件以及它们之间的关系。

1、IO

IO处理是同步的;不管是阻塞模式还是非阻塞模式,都是同步操作。reactor中IO分为: (1)IO检测:通过IO多路复用来检测,检测IO是否就绪。 (2)IO操作:从网络协议栈中读取数据、用户层将数据写入网络协议栈中、接收连接、发起建立连接等。

2、事件

事件处理是异步的;reactor中处理事件是先注册事件,然后有一个事件循环,在事件循环中检测事件是否就绪,如果事件就绪了才会处理事件。注册事件和事件循环是在两个不同的流程中进行的。 reactor网络编程的主体思想是将对IO的处理转换为对事件的处理。事件分为: (1)读事件 (2)写事件 (3)异常事件

3、IO与事件的关系

先注册事件,事件就绪时操作IO。IO与事件的关系主要体现在 (1)检测IO是否就绪(通过IO多路复用)是在事件循环中进行的;(2)事件触发之后开始处理事件,处理事件过程中涉及到IO操作。

三 .Libevent工作流程

Libevent 的工作流程可以概括为以下几个步骤:

初始化:

调用 event_base_new()(或旧版本的 event_init())来创建和初始化一个 event_base 实例,这是 Libevent 的核心结构,它代表了一个事件循环。
创建事件:

使用 event_new() 或 event_assign() 创建一个 event 实例,并设置其文件描述符、事件类型(如 EV_READ、EV_WRITE)、事件回调函数以及用户数据。

添加事件:

调用 event_add() 将事件添加到 event_base 中,可以指定一个超时时间,这样事件会在指定的时间后被触发。

事件循环:

调用 event_base_dispatch() 开始事件循环。这个函数会阻塞,直到至少有一个事件准备好。

在内部,Libevent 会根据操作系统的支持选择合适的事件多路复用机制(如 epoll、select、kqueue)来等待事件。

事件处理:

当事件准备好时,Libevent 会调用与之关联的回调函数。

回调函数执行完毕后,Libevent 会继续监听其他事件。

修改或删除事件:

可以通过 event_del() 从 event_base 中删除事件,或者通过 event_add() 修改事件的超时时间或重新添加事件。

清理:

当不再需要事件循环时,可以调用 event_base_free() 来释放 event_base 实例,这将清理所有关联的资源。

在整个工作流程中,Libevent 提供了高效的事件管理机制,使得开发者可以专注于事件的处理,而无需关心底层的IO多路复用细节。此外,Libevent 还提供了缓冲事件(bufferevent)等高级接口,进一步简化了非阻塞IO的处理。

四. libevent解决了网络编程哪些痛点?
1.高效的网络缓冲区

在内核中有读缓冲区和写缓冲区,减少用户态和内核态的切换。

用户态读缓冲区的存在是为了处理粘包的问题,因为网络协议栈是不知道用户界定数据包的格式,没法确定一个完整的数据包。

用户态写缓冲区的存在是因为用户根本不清楚内核写缓存区的状态,需要把没有写出去的数据缓存起来等待下次写事件时把数据写出去。

buffer的设计有三种类型: (1)固定数组,固定长度。限定了处理数据包的能力,没有动态伸缩的能力;需要频繁挪动数据。 (2)ring buffer(环形缓冲区)。可伸缩性差。 (3)chain buffer(链式缓冲区)。解决可伸缩性差的问题,避免频繁挪动数据;同时也引进了新的问题,一个数据可能在多个buffer中都有,即数据分割,这会导致多次系统调用,从而引起中断上下文的切换。解决办法是使用readv()将内核中连续的buffer读到用户态不连续的buffer中,writev()把用户态不连续的buffer写到内核连续的buffer中;从而减少系统调用。

2.IO函数使用与网络原理

(1)有了libevent可以不使用IO函数。因为如果使用IO函数,既需要知道这些IO函数里面的系统调用返回值的含义。 (2)有了libevent就可以不清楚数据拷贝原理。 (3)有了libevent就可以不清楚网络原理以及网络编程流程。 (4)有了libevent只需要知道事件处理,IO操作完全交由libevent处理。

3.多线程

加锁的效果比较好。 一个线程尽量只处理一个reactor的事件。 (1)buffer加锁时,读要读出一个完整的数据包。 (2)buffer加锁时,写要写一个完整的数据包。

总结
  1. libevent是一个事件通知库,目标是对事件编程;它封装了reactor。

  2. reactor需要关注的几个点:IO分为IO检测(IO多路复用检测IO是否就绪)、IO操作;必须明白IO处理是同步到,而事件处理是异步的(注册事件和事件就绪时触发事件回调是不在同一个流程进行的)。

  3. libevent使用层次有:在事件中自己处理IO和只需要处理业务逻辑(libevent内部处理IO)两种方式。

  4. libevent的封装层次:通常,把事件对象绑定到reactor对象上面;需要熟悉事件操作、事件处理、事件循环。

  5. libevent解决了网络编程中IO函数处理的痛点,因为多线程环境下很难处理IO函数的返回值,以及很难控制数据安全性。

6 .libevent具有高效的网络缓冲区,evbuffer采用chain buffer(链式缓冲区)类型的缓冲区,伸缩性好而且不需要频繁挪动数据

相关推荐
巫山老妖12 分钟前
Linux流量分析:tcpdump&wireshark
linux·嵌入式
秃秃秃秃哇14 分钟前
ubuntu18编译RealSense SDK 2.0
linux
神也佑我橙橙16 分钟前
Ubuntu 22.04 安装英伟达驱动
linux·ubuntu·nvidia
不喝水的鱼儿21 分钟前
Ubuntu 25.04安装搜狗输入法
linux·运维·ubuntu
一只小阿乐44 分钟前
window 服务器上部署前端静态资源以及nginx 配置
运维·服务器·nginx
bjzhang751 小时前
docker部署tomcat网站服务器
服务器·docker·tomcat
Jay Kay1 小时前
brpc中后端server挂在同一个命名服务和不同命名服务的区别详解
运维·服务器·brpc
不脱发的程序猿2 小时前
Linux守护进程
linux·嵌入式
落笔画忧愁e8 小时前
扣子Coze飞书多维表插件添加数据记录
java·服务器·飞书
LCG元10 小时前
Windows实时内核驱动的数据捕获接口:高精度时钟与零拷贝的架构剖析
windows·架构