#memory-allocator #allocator #no-std

no-std emballoc

为嵌入式Rust和#![no_std]提供的简单但可靠的内存分配器

5个版本

0.2.0 2023年11月10日
0.1.3 2023年7月9日
0.1.2 2022年8月24日
0.1.1 2022年8月21日
0.1.0 2022年8月20日

132内存管理

Download history 21/week @ 2024-03-27 22/week @ 2024-04-03 1/week @ 2024-04-10 6/week @ 2024-04-17 14/week @ 2024-04-24 2/week @ 2024-05-01 2/week @ 2024-05-08 3/week @ 2024-05-15 9/week @ 2024-05-22 1/week @ 2024-05-29 8/week @ 2024-06-05 8/week @ 2024-06-12 30/week @ 2024-06-19 33/week @ 2024-06-26 46/week @ 2024-07-03

每月109 次下载

MIT/Apache

69KB
716

emballoc — 嵌入式内存分配器

crates.io circleci codecov docs.rs

此仓库提供了 emballoc crate:为小型嵌入式系统开发的一个简单内存分配器。它是支持无标准库的目标(即带有 #![no_std])动态内存的一种可能方法。这是通过提供一个可以注册为二进制全局分配器的 Allocation 类型来实现的。请参见下面的使用说明。

分配器是软件项目的一个相当关键的部分:在使用动态内存时,许多操作隐式地可以或将会分配,有时是意外的。因此,一个表现不佳的分配器可能会以非常神秘的方式“随机”崩溃程序。因此,分配器必须经过良好的测试和实战检验(请参阅更多信息实际示例)。此外,它必须非常简单:算法越简单,正确的实现可能性就越大。

有关算法和用法提示的详细信息,请参阅crate文档

用法

将以下片段复制到您的 Cargo.toml 中,将crate作为依赖项之一引入。

[dependencies.emballoc]
version = "*" # replace with current version from crates.io

之后,用法非常简单:只需将以下代码复制到项目的二进制crate中。将 4096 替换为您希望的堆大小(以字节为单位)。

#[global_allocator]
static ALLOCATOR: emballoc::Allocator<4096> = emballoc::Allocator::new();

extern crate alloc;

现在,这个crate可以使用如std集合中的Vec<T>BTreeMap<K, V>等,以及像Box<T>Rc<T>这样的重要类型。注意,在std-prelude中的内容(例如Vec<T>Box<T>等)必须显式导入。

为什么选择这个crate

这个crate最初是作为嵌入式项目的一部分开始的,但后来被提取出来,以便在其他项目和用户中使用。本节回答了以下问题

为什么你应该考虑在你的项目中使用这个crate?

  • 核心算法非常简单,因此实现错误的可能性较小
  • 进行了严格的测试(见此处
  • 根据miri,crate没有未定义的行为
  • 静态确定堆大小,防止堆增长到栈中
  • 它在实际应用中使用
  • 它甚至在PC上工作(见此处),尽管这并不是主要用例
  • 支持稳定的编译器,因为只使用了稳定的功能
  • 仅依赖于流行的spin-crate(没有任何传递依赖项)

如果这让你感到满意,我将很高兴,但如果你有任何问题,请简单地打开一个issue

有关具有高级内存功能(如MMU和MPU)的系统的用户注意

  • 如果你有一个可用的内存保护单元(MPU)或类似设备,你必须自己配置它,因为这个crate是平台无关的。一个示例用法可能是配置它,允许读取和写入堆,但不允许执行。由于这个分配器永远不会在内部字节数组之外进行读取/写入,因此不可能在堆周围放置保护页面。但是,建议保护栈,以防止其增长到堆(或任何其他变量)。
  • 如果你有一个(活动)的内存管理单元(MMU),这个crate可能不适合你:它没有使用任何重要功能,这使其性能比可能的情况要差得多。在这种情况下,请使用合适的内存分配器(支持分页等)。然而,如果你在启用MMU之前需要动态内存,这个crate当然是一个选择。

平台支持

这个crate不使用任何特定于平台的特性(例如MMU或特定指令),除了需要原子比较和交换指令(CAS),这是广泛可用的。因此,这个crate在大多数架构上都可以直接使用。

然而,某些平台不提供此类指令(例如thumbv6m-none-eabi或RISC-V OpenTitan),或者由于单核特性而完全缺乏原子指令(例如AVR)。在这些CAS指令不可用的平台上,可以使用spin提供的解决方案:你可以在你的Cargo.toml中启用portable_atomic-feature,如下所示

[dependencies.emballoc]
version = "*" # replace with current version from crates.io
features = ["portable_atomic"]

这允许使用 portable_atomic 而不是 core 原子。这在任何平台上都是安全的。

要实际在无硬件支持的平台上启用原子支持,需要在编译时明确启用 --cfg portable_atomic_unsafe_assume_single_core 选项。更多详情请参阅 spin 的文档

最低支持的 Rust 版本

该包对支持的编译器版本有稳定性保证。所谓的最低支持的 Rust 版本目前设置为 1.57,除非语义版本号方案有适当增加,否则不会提高。这个 MSRV 在 Cargo.toml 中指定,并在 CI 中进行测试。

许可证

根据您的选择,许可方式为

依赖项

~135–275KB