重写Sylar基于协程的服务器(5、IO协程调度模块的设计)

2024-02-04 10:36

本文主要是介绍重写Sylar基于协程的服务器(5、IO协程调度模块的设计),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

重写Sylar基于协程的服务器(5、IO协程调度模块的设计)

重写Sylar基于协程的服务器系列:

重写Sylar基于协程的服务器(0、搭建开发环境以及项目框架 || 下载编译简化版Sylar)

重写Sylar基于协程的服务器(1、日志模块的架构)

重写Sylar基于协程的服务器(2、配置模块的设计)

重写Sylar基于协程的服务器(3、协程模块的设计)

重写Sylar基于协程的服务器(4、协程调度模块的设计)

重写Sylar基于协程的服务器(5、IO协程调度模块的设计)

简述

sylar的IOManager模块本质上就是一个事件池,主要负责向epoll中注册事件和回调。实现了Idle协程的回调,回调是一个阻塞在epoll_wait上的事件循环,将有IO事件发生的协程唤醒。

核心数据结构

将socketfd封装成一个结构体FdContext,对于fd上的读写事件封装成EventContext,提供的TrigleEvent函数,在fd有读写事件发生时,将相应读写事件的EventContext::m_fiber成员放到EventContext::m_scheduler调度器中,可以唤醒阻塞的协程。FdContext结构体定义如下。

struct FdContext {typedef Mutex MutexType;struct EventContext{void reset();Fiber::ptr m_fiber = nullptr;std::function<void(void)> m_cb = nullptr;//记录协程调度器,表示,当事件发生,fiber or callback应该使用哪个协程调度器调度。Scheduler* m_scheduler = nullptr;   };// nolockvoid TrigleEvent(Event event);EventContext& getEventContext(Event event);void resetEventContext(Event event);EventContext read;  //读事件HandleEventContext write; //写事件HandleEvent m_events = NONE;  //记录当前FdContext哪些事件有效int m_fd = -1;MutexType m_mutex;
};

IOManager成员变量

IOManager的成员变量中有一个类型为std::vector<FdContext*>的数组,以每个socketfd作为数组下标,每个fd都能对应一个FdContext。如下。

class IOManager: public Scheduler, public TimerManager{/*...*/
private:std::vector<FdContext*> m_fdContexts;   // fd -> FdContext(和muduo的channel类似)std::atomic<uint32_t> m_penddingEventCount = { 0 }; // epoll监听的事件数int m_pipfd[2]; // 管道fd、也称ticklefd,也称wakefd(Muduo)int m_epollfd;MutexType m_mutex;  // 全局锁
};

IO协程调度器的设计

IO协程调度模块继承自协程调度模块,重新实现了协程调度的idle函数、isStop函数、tickle函数(功能和Muduo中EventLoop的wakeup函数一样)等。因为IO协程调度器继承自协程调度器,所以,现约定以下出现的协程调度器也指IO协程调度器。

  1. 构造函数,创建一对个管道和一个epollfd,并将管道的读端注册到epollfd上,作用是:通知和唤醒阻塞在idle协程的epoll_wait函数上的线程,每次在向调度器任务队列中添加任务时,向管道的写端写入一个字符,以唤醒阻塞的线程,开始处理任务。在构造函数里面会自动启动协程调度器。

  2. addEvent,向epollfd注册一个fd的读写事件,并记录到IOManager::m_fdContexts数组里面,等待事件的触发。

  3. delEvent / cancelEvent, 向epollfd取消或删除一个fd的读写事件,并记录到IOManager::m_fdContexts数组里面。

  4. Idle函数(即idle协程的回调函数),既然调度到了idle协程,说明调度器的任务队列里面没任务了,所以,idle函数首先会调用epoll_wait,带超时的阻塞线程一段时间,超时或者有事件发生时,会检查有无定时器超时,如果有定时器超时就会将超时回调函数放到任务队列中去调度,然后去检查有哪些fd发生了哪些事件,将相关的协程唤醒。

Idle函数伪代码如图:

Idle伪代码

Idle函数流程图:

Idle流程图

下一章将介绍HOOK模块。

感兴趣的同学,可以阅读一下本文实现的源码:https://github.com/LunarStore/lunar


本章完结

这篇关于重写Sylar基于协程的服务器(5、IO协程调度模块的设计)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/677196

相关文章

Go语言开发实现查询IP信息的MCP服务器

《Go语言开发实现查询IP信息的MCP服务器》随着MCP的快速普及和广泛应用,MCP服务器也层出不穷,本文将详细介绍如何在Go语言中使用go-mcp库来开发一个查询IP信息的MCP... 目录前言mcp-ip-geo 服务器目录结构说明查询 IP 信息功能实现工具实现工具管理查询单个 IP 信息工具的实现服

Python的time模块一些常用功能(各种与时间相关的函数)

《Python的time模块一些常用功能(各种与时间相关的函数)》Python的time模块提供了各种与时间相关的函数,包括获取当前时间、处理时间间隔、执行时间测量等,:本文主要介绍Python的... 目录1. 获取当前时间2. 时间格式化3. 延时执行4. 时间戳运算5. 计算代码执行时间6. 转换为指

Python正则表达式语法及re模块中的常用函数详解

《Python正则表达式语法及re模块中的常用函数详解》这篇文章主要给大家介绍了关于Python正则表达式语法及re模块中常用函数的相关资料,正则表达式是一种强大的字符串处理工具,可以用于匹配、切分、... 目录概念、作用和步骤语法re模块中的常用函数总结 概念、作用和步骤概念: 本身也是一个字符串,其中

Python中的getopt模块用法小结

《Python中的getopt模块用法小结》getopt.getopt()函数是Python中用于解析命令行参数的标准库函数,该函数可以从命令行中提取选项和参数,并对它们进行处理,本文详细介绍了Pyt... 目录getopt模块介绍getopt.getopt函数的介绍getopt模块的常用用法getopt模

springboot上传zip包并解压至服务器nginx目录方式

《springboot上传zip包并解压至服务器nginx目录方式》:本文主要介绍springboot上传zip包并解压至服务器nginx目录方式,具有很好的参考价值,希望对大家有所帮助,如有错误... 目录springboot上传zip包并解压至服务器nginx目录1.首先需要引入zip相关jar包2.然

Linux之计划任务和调度命令at/cron详解

《Linux之计划任务和调度命令at/cron详解》:本文主要介绍Linux之计划任务和调度命令at/cron的使用,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录linux计划任务和调度命令at/cron一、计划任务二、命令{at}介绍三、命令语法及功能 :at

将Java项目提交到云服务器的流程步骤

《将Java项目提交到云服务器的流程步骤》所谓将项目提交到云服务器即将你的项目打成一个jar包然后提交到云服务器即可,因此我们需要准备服务器环境为:Linux+JDK+MariDB(MySQL)+Gi... 目录1. 安装 jdk1.1 查看 jdk 版本1.2 下载 jdk2. 安装 mariadb(my

python logging模块详解及其日志定时清理方式

《pythonlogging模块详解及其日志定时清理方式》:本文主要介绍pythonlogging模块详解及其日志定时清理方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地... 目录python logging模块及日志定时清理1.创建logger对象2.logging.basicCo

Qt spdlog日志模块的使用详解

《Qtspdlog日志模块的使用详解》在Qt应用程序开发中,良好的日志系统至关重要,本文将介绍如何使用spdlog1.5.0创建满足以下要求的日志系统,感兴趣的朋友一起看看吧... 目录版本摘要例子logmanager.cpp文件main.cpp文件版本spdlog版本:1.5.0采用1.5.0版本主要

基于Python打造一个可视化FTP服务器

《基于Python打造一个可视化FTP服务器》在日常办公和团队协作中,文件共享是一个不可或缺的需求,所以本文将使用Python+Tkinter+pyftpdlib开发一款可视化FTP服务器,有需要的小... 目录1. 概述2. 功能介绍3. 如何使用4. 代码解析5. 运行效果6.相关源码7. 总结与展望1