ET9中ETTask传递新的Context原理

ET9中ETTask传递新的Context原理

前言

每一个异步函数都会创建两个对象,
1个是当前异步函数返回值(ETTASK)对应的ETAsyncTaskMethodBuilder,通过这个类的静态方法Create创建返回,这个builder类中会有一个Task对象,用于当返回值返回;
2个是编译器为我们创建的对应的状态机对象。其中状态机对象包裹了当前异步函数的所有代码。
在这里插入图片描述

对应的源码
在这里插入图片描述
以及包裹的状态机代码:
在这里插入图片描述

一、ETTask传递上下文的关键代码

如上图中红框所示,只要在源码中调用了await,就会执行对应的ETAsyncTaskMethodBuilder的AwaitUnsafeOnCompleted函数,这里就是传递上下文的入口。在一个异步函数(父异步)中,每次await调用另外一个异步函数(称为子异步吧),都会获得这个子异步函数对应的builder中的Task,又是通过父异步函数的builder对象的AwaitUnsafeOnCompleted来实现的。所以此时可以拿到此时父异步函数builder中的Task的上下文对象,传递给AwaitUnsafeOnCompleted中的子异步函数builder返回的builder中的Task。
ET9中的源码:

public void AwaitUnsafeOnCompleted<TAwaiter, TStateMachine>(ref TAwaiter awaiter, ref TStateMachine stateMachine) where TAwaiter : ICriticalNotifyCompletion where TStateMachine : IAsyncStateMachine{this.iStateMachineWrap ??= StateMachineWrap<TStateMachine>.Fetch(ref stateMachine);awaiter.UnsafeOnCompleted(this.iStateMachineWrap.MoveNext);if (awaiter is not IETTask task){return;}if (this.tcs.TaskType == TaskType.WithContext){task.SetContext(this.tcs.Context);return;}this.tcs.Context = task;}

可以看到获取当前tcs(也就是builder中的Task)的类型是附带有上下文的,那么就进行一次设置子Task的上下文设置,如果不是携带上下文,就把当前Task上下文设置为这个子Task,用于后续上下文传递。
SetContext这是个Task的扩展函数,内部是循环,设置当前Task的上下文同时,找到对应的子Task,如果子Task不存在,或者已经是附带上下文了,就返回。

while (true){if (task.TaskType == TaskType.ContextTask){((ETTask<object>)task).SetResult(context);break;}// cancellationToken传下去task.TaskType = TaskType.WithContext;object child = task.Context;task.Context = context;task = child as IETTask;if (task == null){break;} 传递到WithContext为止,因为可能这一层设置了新的contextif (task.TaskType == TaskType.WithContext){break;}}

通过上面的代码,就可以理解为,当前异步函数中,只要await了一个ETTask,那么就会把当前异步函数ETTask(由对应的builder创建的)的上下文,传递给这个ETTask(没有设置自己的上下文),无论这个ETTask是由新的异步函数创建返回的,还是我们手动ETTask.Create的。

二、GetContextAsync怎么获取到当前上下文的

有了上面的介绍,我们就能知道,ETTask的上下文如何进行传递的。那么在一个异步函数中,要获取当前异步函数的上下文,那么就可以await ETTaskHelper.GetContextAsync来获取。
源码如下:

public static async ETTask<T> GetContextAsync<T>() where T: class{ETTask<object> tcs = ETTask<object>.Create(true);tcs.TaskType = TaskType.ContextTask;object ret = await tcs;if (ret == null){return null;}return (T)ret;}

当一个异步函数await这个GetContextAsync,那么进入这个函数时,外层的异步函数的ETTask上下文就传递到这个异步函数中(强调一下,由这个异步函数对应的Builder的创建的ETTask中)。然后内部创建了一个ETTask,再一次Await,那么上下文就由builder的Task传递到内部这个创建的ETTask。
要注意的是,内部创建的ETTask类型是ContextTask,那么在await–>AwaitUnsafeOnCompleted->SetContext,最终调用到SetContext时,有如下代码:

			if (task.TaskType == TaskType.ContextTask){((ETTask<object>)task).SetResult(context);break;}

即立刻调用此ETTask的SetResult的结果为上下文,然后ETTask会调用callback(由AwaitUnsafeOnCompleted传给ETTask的,状态机的MoveNext委托),就会返回到GetContextAsync函数中,获取结果并返回,这个结果就是当前异步函数的上下文信息了。

总结

ET9作者猫大的创新以及设计能力确实强,新版的ETTask也确实牛逼,有了上下文确实能搞出很多花样了。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/35495.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

idea 自动生成序列化数字

目标&#xff1a;当类继承Serializable后自动生成序列化Uid 网上查了很多说勾选class without ‘serialVersionUID’ 但是我勾选没用 最后发现&#xff0c;我勾选的是Serialization issues里面的配置&#xff0c;要勾选的是JVM languages下的 如下图所示&#xff0c;记录一下…

技术干货|SimLab 电子产品热流体仿真

电子产品热仿真特点有哪些&#xff1f; 结构复杂&#xff0c;电子设备包含几十~上千个元器件 体积小&#xff0c;功率密度高、关注热敏感元器件 多种冷却方式&#xff0c;自然冷却、风扇冷却、液冷、热管等 多维度&#xff0c;芯片级&#xff0c;板级&#xff0c;系统级 单…

Unity在屏幕上输出文字

为了使文本显示功能更加模块化和可重用&#xff0c;我们可以将其封装成一个独立的C#类&#xff0c;这样其他脚本可以方便地调用它来显示文本。下面是如何封装这个功能并使其易于从其他脚本中调用的步骤&#xff1a; 步骤 1: 创建一个新的C#脚本 在Unity的Project视图中&#…

昇思25天学习打卡营第03天|张量Tensor

何为张量&#xff1f; 张量&#xff08;Tensor&#xff09;是一个可用来表示在一些矢量、标量和其他张量之间的线性关系的多线性函数&#xff0c;这些线性关系的基本例子有内积、外积、线性映射以及笛卡儿积。其坐标在 &#x1d45b;维空间内&#xff0c;有  &#x1d45b;&a…

ppt模版免费下载网站大全

PPT是我们传达信息、分享知识、展示项目和进行商务沟通的重要工具。一个设计精美、布局合理的PPT不仅能吸引观众的注意力&#xff0c;还能有效提升演讲者的专业形象。PPT模版可以帮助我们高效制作出精美的PPT&#xff0c;下面小编就来和大家分享一些免费无需注册登录就可以直接…

Mysql进阶-索引-使用规则-索引失效情况二(or连接的条件、数据分布影响)

文章目录 1、or连接的条件1.1、展示 tb_user 索引1.2、查询 id10 or age231.3、执行计划 id10 or age231.4、给 age 创建 索引1.4、执行计划 phone17799990004 or age23 2、数据分布影响2.1、查询 tb_user2.2、查询 phone >177999900202.3、执行计划 phone >177999900202…

Python学习打卡:day17

day17 笔记来源于&#xff1a;黑马程序员python教程&#xff0c;8天python从入门到精通&#xff0c;学python看这套就够了 目录 day17121、Python 操作 MySQL 基础使用pymysql创建到 MySQL 的数据库链接执行 SQL 语句执行非查询性质的SQL语句执行查询性质的SQL语句 122、Pyth…

Python爬虫实战之爬取京东商品数据

在数字化时代&#xff0c;数据如同黄金般珍贵&#xff0c;而电商数据&#xff0c;尤其是像京东这样的大型电商平台上的信息&#xff0c;更是商家、市场分析师和数据科学家眼中的瑰宝。本文将带您走进Python爬虫的世界&#xff0c;探索如何高效、合法地采集京东商品数据&#xf…

c# 容器笔记2 查找 DataGrid中的行向上移动

struct info{ int A;int B;};c# 从 List中查找A与5相等的对象 在C#中&#xff0c;如果你有一个List&#xff08;其中info是一个结构体&#xff0c;类似于你给出的C语言结构体定义&#xff09;&#xff0c;并且你想从这个列表中查找所有A属性等于5的info对象&#xff0c;你可以…

幻兽帕鲁Palworld樱花版本服务器一键开服联机

1、登录服务器&#xff08;百度莱卡云&#xff09; 1.1、第一次购买服务器会安装游戏端&#xff0c;大约5分钟左右&#xff0c;如果长时间处于安装状态请联系客服 2、在启动中调整游戏参数 2.1、重启服务器&#xff0c;等待running出现&#xff0c;或者运行时间变为灰色&#x…

Linux0.12内核源码解读(5)-head.s

大家好&#xff0c;我是呼噜噜&#xff0c;好久没有更新old linux了&#xff0c;本文接着上一篇文章图解CPU的实模式与保护模式&#xff0c;继续向着操作系统内核的世界前进&#xff0c;一起来看看heads.s as86 与GNU as 首先我们得了解一个事实&#xff0c;在Linux0.12内核源…

2024年6月27日 (周四) 叶子游戏新闻

老板键工具来唤去: 它可以为常用程序自定义快捷键&#xff0c;实现一键唤起、一键隐藏的 Windows 工具&#xff0c;并且支持窗口动态绑定快捷键&#xff08;无需设置自动实现&#xff09;。 喜马拉雅下载工具: 字面意思 Steam国产“类8番”游戏《永恒逃脱&#xff1a;暗影城堡》…

单片机串口uart学习

参考文章 https://blog.csdn.net/Reed_redd/article/details/126098506 https://blog.csdn.net/AriesPIG/article/details/119840979 前言 OK&#xff0c;又是新一期的温故而知新&#xff01;串口UART想必大家都用过&#xff0c;我记得我最早的时候用它来打印单片机的调试数…

【JD-GUI】MacOS 中使用Java反编译工具JD-GUI

希望文章能给到你启发和灵感&#xff5e; 如果觉得文章对你有帮助的话&#xff0c;点赞 关注 收藏 支持一下博主吧&#xff5e; 阅读指南 开篇说明概念理解一、基础环境说明1.1 硬件环境1.2 软件环境 二、下载与安装2.1 选择对应版本2.2 解压运行排除异常&#xff1a;2.3 关于…

16进制数按位修改

16进制数需要按位修改,特别是在修改寄存器的时候 16进制数转换为2进制 #16进制数转换为2进制 def hex_to_binary(hex_value):return bin((hex_value))二进制数转换为列表 def bin_to_array(bin_str):integer = int(bin_str, 2)array

GuiLite C语言实现版本

简介 本项目是idea4good/GuiLite的C语言实现版本&#xff0c;基于2024-06-20节点的版本&#xff08;提交ID&#xff1a;e9c4b57&#xff09;。 本项目仓库&#xff1a;GuiLite_C 需求说明 作为芯片从业人员&#xff0c;国产芯片普遍资源有限&#xff08;ROM和RAM比较少-都是…

[Vulnhub] wallabysnightmare LFI+RCE+Irssi聊天服务RCE

信息收集 Server IP AddressOpening Ports192.168.8.105TCP:22,80,6667,60080 $ nmap -p- -sC -sV 192.168.8.105 --min-rate 1000 -Pn 基础Shell http://192.168.8.105/?page../../../../../etc/shadow 当再次尝试访问已经关闭 $ nmap -p- -sC -sV 192.168.8.105 --min-rat…

c++实现web服务器数据收发

利用微软标准API实现web服务器数据的发送和接受,遇到的问题点: 1.句柄创建 CString strMsg; int iError 0; HINTERNET hint; HINTERNET hftp; HINTERNET hconnect; HINTERNET Openhconnect; hint InternetOpen(0, INTERNET_OPEN_TYPE_PRECONFIG_WITH_NO_AUTOPROXY/INTERNET_O…

7、广告-用户识别与ID映射

一、用户识别原理 程序化广告生态系统是以数据为核心的生态系统&#xff0c;要实现精准的受众定向&#xff0c;首先需要进行单用户的识别。在PC端&#xff0c;常用Cookie作为用户标识&#xff0c;为用户打上标签的技术被称为“种Cookie”。 Cookie的作用与局限性 生命周期短&a…

ms17-010 ms12-020 ms-08-067

MS17-010是一个由微软发布的安全公告编号&#xff0c;它指代了一个严重级别的安全漏洞&#xff0c;该漏洞存在于Microsoft Windows的Server Message Block 1.0 (SMBv1)协议处理中。这个漏洞被命名为“永恒之蓝”&#xff08;EternalBlue&#xff09;&#xff0c;因为它最初是由…