协程本质是控制流的主动挂起与恢复,需栈、寄存器上下文和调度逻辑;ucontext.h仅用于教学演示,Boost.Context提供跨平台、异常安全的工业级实现,C++20协程则为无栈状态机方案。
用 C++ 实现一个“简单”的协程库,核心不是从零造轮子(比如手写汇编切换栈),而是理解协程的本质:**控制流的主动挂起与恢复**,并借助系统或标准库提供的上下文切换原语。Boost.Context 是成熟方案,而 ucontext.h(POSIX)是更底层、可教学但已废弃的接口。下面直击重点,不绕弯。
协程不是线程,它不抢占、不依赖内核调度。一次协程切换 = 保存当前函数执行现场(栈指针、指令指针、通用寄存器等)→ 跳转到另一段栈上的函数继续执行。关键不在“多任务”,而在“可控让出”(yield)和“可控唤醒”(resume)。
所以真正要实现的最小闭环是:
char stack[8192])ucontext 或 boost::context::continuation 干的事)注意:ucontext 已被 POSIX 标准弃用,glibc 2.26+ 默认禁用,仅用于理解底层。生产环境请用 Boost.Context 或 C++20 协程。
下面是去掉错误检查、仅保留主干的可运行片段:
#include#include #include struct SimpleCoro { ucontext_t ctx; char stack[8192]; bool is_done = false;
SimpleCoro(std::functionf) { getcontext(&ctx); ctx.uc_stack.ss_sp = stack; ctx.uc_stack.ss_size = sizeof(stack); ctx.uc_link = nullptr; // 挂起后返回到哪?这里设为 null,由我们手动 resume 控制 makecontext(&ctx, [](int) { // 这里是协程体入口,需转成 C 风格函数 auto* self = reinterpret_cast (reinterpret_cast (&self) - sizeof(self)); self->body(); }, 1, reinterpret_cast (&this)); } void body() { // 用户逻辑在此运行 std::cout << "coro running\n"; // 模拟 yield:切回主协程(需提前保存主 ctx) swapcontext(&ctx, &main_ctx); // ⚠️ main_ctx 需在 main 中 setcontext 前 getcontext std::cout << "coro resumed\n"; is_done = true; } void resume() { if (!is_done) swapcontext(&main_ctx, &ctx); } };
ucontext_t main_ctx; // 全局保存主上下文(不推荐,仅示意)
int main() { getcontext(&main_ctx); SimpleCoro c([]{}); c.resume(); // 启动协程 std::cout
⚠️ 缺陷明显:无法传递参数、无异常安全、栈大小固定、
makecontext参数传递靠 hack 地址、不可重入。这正是 Boost.Context 存在的理由。三、用 Boost.Context 实现可工业使用的轻量协程
Boost.Context 封装了平台差异(x86/x64/ARM,Windows Fibers / Linux setjmp / macOS),提供 RAII、异常传播、栈分配策略。最简可用示例:
#include#include namespace ctx = boost::context;
struct Task { ctx::continuation c; bool done = false;
Task(std::functionfn) : c_(ctx::callcc([fn = std::move(fn)](ctx::continuation&& c) { fn(c); // 用户函数接收 continuation,可用来 yield return std::move(c); })) {} void resume() { if (!done_) c_ = std::move(c_).resume(); done_ = c_.fpc_ == nullptr; // 判断是否已结束(内部指针为空) } void yield() { c_ = std::move(c_).resume(); // 切回父协程(即构造时 callcc 的调用方) } };
// 使用示例 int m
ain() { Task t([](ctx::continuation& c) { std::cout
std::cout << "before first resume\n"; t.resume(); // 启动 std::cout << "after first resume\n"; t.resume(); // 继续}
优势一目了然:
continuation是移动语义安全的对象,支持栈上/堆上分配callcc(call-with-current-continuation)天然支持双向跳转- 可指定栈大小、栈分配器(如
fixedsize_stack或protected_fixedsize_stack)- 异常会正常传播(不像 ucontext 可能崩溃)
四、为什么不直接手写汇编?以及 C++20 协程怎么选?
手写汇编(如 x86 的
push/pop所有寄存器 + 修改rsp/rip)理论上可行,但:
- 不同 ABI(System V / Win64)、不同架构(x86-64 / AArch64)寄存器列表和调用约定完全不同
- 编译器优化(如 RVO、尾调用)可能破坏你预设的栈帧布局
- 调试困难、无法和现代 C++ 特性(RAII、异常、lambda 捕获)自然融合
C++20 协程是语言级支持,语法简洁(
co_await,co_yield,co_return),但它是无栈协程(stackless),依赖编译器生成状态机,不能像 Boost.Context 那样自由跳转任意函数。适合 I/O 等待场景,不适合需要完整调用栈的协作式多任务(如游戏逻辑帧、解释器)。结论:学原理看
ucontext;做项目用Boost.Context;新项目且场景匹配,优先评估C++20 coroutines+libunifex或cppcoro。基本上就这些。协程不神秘,难的是跨平台健壮性和与现代 C++ 生态的无缝集成——Boost.Context 已经替你扛住了。
# c++ # linux # windows # mac # 栈 # ai # ios # macos # win # stream # cos # 标准库 # 架构 # 封装 # char # int # Lambda # 指针 # 接口 # 堆 # 线程 # 对象 # 挂起 # 跳转 # 的是 # 闭环 # 在此 # 这就是 # 已被 # 设为 # 而在 # 是从
相关文章: 已有域名如何免费搭建网站? 网站视频制作书签怎么做,ie浏览器怎么将网站固定在书签工具栏? 建站之星×万网:智能建站系统+自助建站平台一键生成 制作宣传网站的软件,小红书可以宣传网站吗? 新网站制作渠道有哪些,跪求一个无线渠道比较强的小说网站,我要发表小说? 网站制作哪家好,cc、.co、.cm哪个域名更适合做网站? 公司网站设计制作厂家,怎么创建自己的一个网站? 免费制作小说封面的网站有哪些,怎么接网站批量的封面单? 在线制作视频的网站有哪些,电脑如何制作视频短片? 如何在搬瓦工VPS快速搭建网站? 如何选择网络建站服务器?高效建站必看指南 头像制作网站在线观看,除了站酷,还有哪些比较好的设计网站? 如何选择高效便捷的WAP商城建站系统? 猪八戒网站制作视频,开发一个猪八戒网站,大约需要多少?或者自己请程序员,需要什么程序员,多少程序员能完成? 如何在IIS中新建站点并配置端口与IP地址? 重庆市网站制作公司,重庆招聘网站哪个好? 建站之星如何通过成品分离优化网站效率? 三星网站视频制作教程下载,三星w23网页如何全屏? Python路径拼接规范_跨平台处理说明【指导】 最好的网站制作公司,网购哪个网站口碑最好,推荐几个?谢谢? 如何设计高效校园网站? 建站之星安装模板失败:服务器环境不兼容? 建站主机助手选型指南:2025年热门推荐与高效部署技巧 JS中使用new Date(str)创建时间对象不兼容firefox和ie的解决方法(两种) 简单实现Android文件上传 如何通过宝塔面板实现本地网站访问? 建站之星后台密码遗忘或太弱?如何重置与强化? 建站主机选虚拟主机还是云服务器更好? 如何通过VPS搭建网站快速盈利? 如何制作网站标识牌,动态网站如何制作(教程)? 图片制作网站免费软件,有没有免费的网站或软件可以将图片批量转为A4大小的pdf? 实现虚拟支付需哪些建站技术支撑? 如何快速选择适合个人网站的云服务器配置? 如何配置FTP站点权限与安全设置? 高端智能建站公司优选:品牌定制与SEO优化一站式服务 北京网站制作网页,网站升级改版需要多久? 如何挑选高效建站主机与优质域名? 青浦网站制作公司有哪些,苹果官网发货地是哪里? 北京营销型网站制作公司,可以用python做一个营销推广网站吗? 网站制作新手教程,新手建设一个网站需要注意些什么? 如何快速搭建自助建站会员专属系统? Swift开发中switch语句值绑定模式 b2c电商网站制作流程,b2c水平综合的电商平台? 婚礼视频制作网站,学习*后期制作的网站有哪些? 如何用美橙互联一键搭建多站合一网站? 武汉网站制作费用多少,在武汉武昌,建面100平方左右的房子,想装暖气片,费用大概是多少啊? 浙江网站制作公司有哪些,浙江栢塑信息技术有限公司定制网站做的怎么样? 如何在阿里云购买域名并搭建网站? 如何通过.red域名打造高辨识度品牌网站? 网站制作大概要多少钱一个,做一个平台网站大概多少钱?
*请认真填写需求信息,我们会在24小时内与您取得联系。