6个版本

0.0.6-a2023年4月5日
0.0.5-a2023年3月26日

嵌入式开发 中排名338

MIT许可证

1.5MB
3.5K SLoC

包含 (WOFF字体,99KB) fontawesome-webfont.woff,(WOFF字体,78KB) fontawesome-webfont.woff2,(WOFF字体,45KB) open-sans-v17-all-charsets-300.woff2,(WOFF字体,41KB) open-sans-v17-all-charsets-300italic.woff2,(WOFF字体,45KB) open-sans-v17-all-charsets-600.woff2,(WOFF字体,43KB) open-sans-v17-all-charsets-600italic.woff2 等文件。

CrossBus

无平台、无运行时Actor计算模型

API Document crates.io

概述

CrossBusActor计算模型 的实现,其核心概念为

  • 无运行时

    crossbus 不提供应用程序执行时的运行时,也不访问系统接口抽象。没有内置的运行时,但任何运行时都是允许的,
    系统提供的/第三方的/通过 FFI-绑定都可以工作。最后但同样重要的是,即使是裸机 noop-waker executor 也可以。

    运行时定位的功能,如 concurrencynetworkI/O 都由实现者负责。

  • 裸机兼容

    crossbus 不链接任何系统库,没有 libc,以及一些上游库,使您能够在裸机上运行 rust 代码。

    示例 文件夹中包含了一些使用 crossbus 的演示。

  • 通过无运行时实现无平台

    利用无运行时的优势,crossbus 能够绕过运行时实现者和系统接口抽象的限制,直接操纵任务。只需要一个简单且虚假的 future executor(参见 无std示例)就足够运行 crossbus。这是 crossbus 在多个平台或无平台之间运行的主要概念。

  • 面向未来的例程和事件

    由于 rust,即使在没有运行时的情况下,也保留了 futures 方式执行任务。crossbus 定义了一套类型和特质,以允许异步任务操作。

  • 实时执行控制

    利用未来例程的设计,每个在执行过程中生成的任务都可以拦截每个轮询和事件,从而实现更多的执行控制。

目前crossbus处于alpha版本,所有API和架构尚不稳定,并且发展非常迅速。

文档

功能标志

为了减少代码冗余并加快编译速度,crossbus使用功能标志来标记必要的模块/函数,目前这里有一些支持的功能

  • core/no-std:默认功能,裸机兼容
  • std:依赖rust std库
  • derive:启用 #[derive(Message)]#[crossbus::main(...)]
  • log:在运行时启用状态和信息的日志输出
  • time:使Actor在阻塞/延迟一段时间时知道时间
  • rt:启用使用一些常见的方便的运行时
  • tokio:使用基于tokio的运行时的便利性
  • async-std:使用基于async-std的运行时的便利性
  • wasm32:使用基于wasm-bindgen-futures的运行时的便利性
  • unstable:不稳定功能的标记
  • time-metric:与 unstabletime 一起启用,数值计时功能
  • force-poll:与 unstabletime 一起启用,依赖 time 的周期性唤醒未来轮询

使用方法

首先,将 crossbus 添加到项目的 Cargo.toml

[dependencies]
crossbus = "0.0.6-a"

类型和导入

根据您的业务逻辑定义一些类型和方法。

比如一个actor用来加一些数字,好的,那么消息应该是actor应该知道在加完之后的结果。

use crossbus::prelude::*;

struct Num(uisze);
impl Message for Num {}

struct CrossBus {
    sum: isize
}

Actor 实现

actor在使用之前应该被创建

我们告诉crossbus如何创建它

impl Actor for CrossBus {
    type Message = Num;
...
    fn create(ctx: &mut Context<Self>) -> Self {
        Self { sum: 0, }
    }
...
}

消息动作与反应

好的,actor在收到消息时如何响应?我们应该告诉crossbus。

    ...
    fn action(&mut self, msg: Self::Message, ctx: &mut Context<Self>) {
        self.sum += msg.0;
    }
    ...

到目前为止一切顺利,但如何获得最终结果?

它可以在actor处理完所有消息并停止时使用,对吧?

    ...
    fn stopped(&mut self, _: &mut Context<Self>) {
        println!("final sum: {}", self.sum);
    }
    ...

完成。恭喜!您刚刚了解了使用crossbus的基本流程。完整的代码请见下文。

示例

这里提供了一个简单的演示,用于求和数字。

更多示例,您可以访问 示例 文件夹,克隆仓库并在本地运行。

use crossbus::prelude::*;

struct Num(uisze);
impl Message for Num {}

struct CrossBus {
    sum: isize
}
impl Actor for CrossBus {
    type Message = Num;

    fn create(ctx: &mut Context<Self>) -> Self {
        Self { sum: 0, }
    }

    fn action(&mut self, msg: Self::Message, ctx: &mut Context<Self>) {
        self.sum += msg.0;
    }

    fn stopped(&mut self, _: &mut Context<Self>) {
        println!("final sum: {}", self.sum);
        assert_eq!(self.sum, 7);
    }

}

#[main(runtime = tokio)]
async fn main() {
    let (addr, id) = CrossBus::start();
		println!("actor {} started", id);
    let sender = addr.sender();
    sender.send(Num(1)).unwrap();
    sender.send(Num(2)).unwrap();
    sender.send(Num(4)).unwrap();
}

贡献

请随意贡献!所有问题/错误报告/功能请求等都是受欢迎的!

参考

依赖

~0–15MB
~137K SLoC