ITADN
bytedance/monoio
README.md
以下内容由 AI 翻译,如有问题请点此提交 issue 反馈

Monoio

一个基于每核一线程的 Rust 运行时,支持 io_uring/epoll/kqueue。

Crates.io MIT/Apache-2 licensed Build Status Codecov FOSSA Status 中文说明

设计目标

Monoio 是一个纯 io_uring/epoll/kqueue 的 Rust 异步运行时。其部分设计借鉴自 Tokio 和 Tokio-uring。然而,与 Tokio-uring 不同,Monoio 并不运行在另一个运行时之上,从而使其更加高效。

此外,Monoio 的设计以每核一线程模型为核心。用户无需担心任务被 SendSync,因为线程局部存储可以安全使用。换言之,与 Tokio 等工作窃取运行时不同,数据在 await 点不会逃逸出线程。这是因为对于某些用例,特别是本运行时所针对的用例,无需使任务在线程间可调度。例如,如果我们编写一个类似 NGINX 的负载均衡器,我们会以每核一线程的方式编写它。线程局部数据无需在线程间共享,因此 SyncSend 根本无需实现。

您可能已经猜到,此运行时主要面向服务器,其中操作在网络套接字上是 I/O 密集型,因此使用原生异步 I/O API 可以最大化服务器吞吐量。为了使 Monoio 尽可能高效,我们启用了一些不稳定的 Rust 特性,并设计了一套全新的 I/O 抽象,这不幸地可能导致一些兼容性问题。我们的基准测试 证明,对于我们的用例,Monoio 比其他 Rust 运行时具有更好的性能。

快速入门

要使用 monoio,您需要 rust 1.75。如果您已经安装,请确保它是最新版本。

此外,如果你想使用 io_uring,你必须确保你的内核支持它(5.6+)。并且,memlock 已配置为适当的数值。如果你的内核版本不满足要求,你可以尝试使用 legacy driver 启动,目前支持 Linux 和 macOS(参考此处)。

🚧实验性的 Windows 支持正在路上。

以下是如何使用 Monoio 的基本示例。

/// A echo example.
///
/// Run the example and `nc 127.0.0.1 50002` in another shell.
/// All your input will be echoed out.
use monoio::io::{AsyncReadRent, AsyncWriteRentExt};
use monoio::net::{TcpListener, TcpStream};

#[monoio::main]
async fn main() {
    let listener = TcpListener::bind("127.0.0.1:50002").unwrap();
    println!("listening");
    loop {
        let incoming = listener.accept().await;
        match incoming {
            Ok((stream, addr)) => {
                println!("accepted a connection from {}", addr);
                monoio::spawn(echo(stream));
            }
            Err(e) => {
                println!("accepted connection failed: {}", e);
                return;
            }
        }
    }
}

async fn echo(mut stream: TcpStream) -> std::io::Result<()> {
    let mut buf: Vec<u8> = Vec::with_capacity(8 * 1024);
    let mut res;
    loop {
        // read
        (res, buf) = stream.read(buf).await;
        if res? == 0 {
            return Ok(());
        }

        // write all
        (res, buf) = stream.write_all(buf).await;
        res?;

        // clear
        buf.clear();
    }
}

你可以在本仓库的 examples 中找到更多示例代码。

局限性

  1. 在 Linux 5.6 或更高版本上,Monoio 可以使用 uring 或 epoll 作为 io 驱动。在较低版本的 Linux 上,它只能以 epoll 模式运行。在 macOS 上,可以使用 kqueue。目前不支持其他平台。
  2. Monoio 无法解决所有问题。如果工作负载非常不均衡,由于 CPU 核心可能无法被充分利用,它可能会导致性能低于 Tokio。

贡献者

感谢他们的贡献!

关联项目

HTTP 框架和 RPC 框架正在开发中。

许可证

Monoio 采用 MIT 许可证或 Apache 许可证。

在开发过程中,我们大量参考了 Tokio、Mio、Tokio-uring 和其他相关项目。我们想感谢这些项目的作者。

FOSSA Status