{"id":13667893,"url":"https://github.com/js2xxx/ferroc","last_synced_at":"2025-04-26T18:30:43.173Z","repository":{"id":219437251,"uuid":"749054051","full_name":"js2xxx/ferroc","owner":"js2xxx","description":"A lock-free memory allocator","archived":false,"fork":false,"pushed_at":"2024-05-20T03:28:22.000Z","size":2391,"stargazers_count":36,"open_issues_count":2,"forks_count":1,"subscribers_count":1,"default_branch":"master","last_synced_at":"2024-05-22T12:11:16.473Z","etag":null,"topics":["allocator","malloc","memory","rust"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/js2xxx.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE-APACHE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-01-27T13:03:53.000Z","updated_at":"2024-06-06T06:55:37.829Z","dependencies_parsed_at":"2024-02-22T03:26:56.521Z","dependency_job_id":"61228685-f718-413d-b46b-26f0858b32d8","html_url":"https://github.com/js2xxx/ferroc","commit_stats":null,"previous_names":["js2xxx/ferroc"],"tags_count":13,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/js2xxx%2Fferroc","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/js2xxx%2Fferroc/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/js2xxx%2Fferroc/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/js2xxx%2Fferroc/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/js2xxx","download_url":"https://codeload.github.com/js2xxx/ferroc/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":251035124,"owners_count":21526308,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["allocator","malloc","memory","rust"],"created_at":"2024-08-02T07:00:53.785Z","updated_at":"2025-04-26T18:30:43.166Z","avatar_url":"https://github.com/js2xxx.png","language":"Rust","funding_links":[],"categories":["Rust"],"sub_categories":[],"readme":"# Ferroc: A Multithread Lock-free Memory Allocator\n\n[![Build Status](https://img.shields.io/github/actions/workflow/status/js2xxx/ferroc/basic.yml?style=for-the-badge)](https://github.com/js2xxx/ferroc/actions)\n[![Cargo](https://img.shields.io/crates/v/ferroc?style=for-the-badge)](https://crates.io/crates/ferroc)\n[![Coverage](https://img.shields.io/codecov/c/github/js2xxx/ferroc?style=for-the-badge)](https://codecov.io/gh/js2xxx/ferroc)\n[![Documentation](https://img.shields.io/docsrs/ferroc?style=for-the-badge)](https://docs.rs/ferroc)\n[![License](https://img.shields.io/crates/l/ferroc?style=for-the-badge)](https://github.com/js2xxx/ferroc)\n\nFerroc (combined from \"ferrum\" and \"malloc\") is a lock-free concurrent memory allocator written in Rust, primarily inspired by [`mimalloc`](https://github.com/microsoft/mimalloc).\n\nThis memory allocator is designed to work as fast as other mainstream memory allocators while providing flexible configurations such as embedded/bare-metal environment integrations.\n\n## Examples\n\nIf you simply want to utilize another memory allocator, you can use Ferroc as the global allocator with default features:\n\n```rust\nuse ferroc::Ferroc;\n\n#[global_allocator]\nstatic FERROC: Ferroc = Ferroc;\n\nfn main() {\n    // Using the global allocator API.\n    let _vec = vec![10; 100];\n\n    // Manually allocate memory.\n    let layout = std::alloc::Layout::new::\u003cu8\u003e();\n    let ptr = Ferroc.allocate(layout).unwrap();\n    unsafe { Ferroc.deallocate(ptr, layout) };\n\n    // Immediately run some delayed clean-up operations.\n    Ferroc.collect(/* force */false);\n}\n```\n\nIf you want more control over the allocator, you can disable the default features and enable the ones you need:\n\n```toml\nferroc = {version = \"*\", default-features = false, features = [\"base-mmap\"]}\n```\n\n```rust\n#![feature(allocator_api)]\n\nuse core::pin::pin;\nuse ferroc::{\n    arena::Arenas,\n    heap::{Heap, Context},\n    base::Mmap,\n};\n\nfn main() {\n    let arenas = Arenas::new(Mmap); // `Arenas` are `Send` \u0026 `Sync`...\n    let cx = pin!(Context::new(\u0026arenas));\n    let heap = Heap::new(cx.as_ref()); // ...while `Context`s and `Heap`s are not.\n\n    // Using the allocator API.\n    let mut vec = Vec::new_in(\u0026heap);\n    vec.extend([1, 2, 3, 4]);\n    assert_eq!(vec.iter().sum::\u003ci32\u003e(), 10);\n\n    // Manually allocate memory.\n    let layout = std::alloc::Layout::new::\u003cu8\u003e();\n    let ptr = heap.allocate(layout).unwrap();\n    unsafe { heap.deallocate(ptr.cast(), layout) }.unwrap();\n\n    // Immediately run some delayed clean-up operations.\n    heap.collect(/* force */false);\n}\n```\n\n## Cargo Features\n\n- Basic features: generic `Arenas`, `Context`s and `Heap`s;\n- `\"base-static\"`: Base allocator `Static`;\n- `\"base-mmap\"`: Base allocator `Mmap` based on os-specific virtual memory managers (`std` and `libc` required);\n- `\"global\"`: Global allocator instantiation macros `config!` and `config_mod!` (inner thread local statics are leaked by default);\n- `\"libc\"`: `libc` dependency (currently required by `pthread` option in `config*!` if you want a `pthread` thread-local destructor);\n- `\"default\"`: The default global allocator `Ferroc` provided by `Mmap` and `pthread` thread-local destructor (consisting of all the features above);\n- `\"c\"`: `fe_*` C functions for C/C++ targets;\n- `\"c-bindgen\"`: A generated C/C++ header `\"ferroc.h\"` in the root directory;\n- `\"c-override\"`: Override default allocator functions such as `malloc/free` and `operator new/delete`, which can be useful for embedding Ferroc in a C/C++ project (see [this section](#building-process-for-cc-users) for more details);\n- `\"track-valgrind\"`: Valgrind memory tracking support based on [`crabgrind`](https://github.com/2dav/crabgrind), which requires Valgrind's version of at least 3.22;\n- `\"finer-grained\"`: Add more object size types to small bins, decreasing fragmentation but also the minimal alignment from 16 to 8, potentially leading some programs that need SIMD to fail for misalignment.\n\n## Compile-time Environment variables\n\nThere are several additional configurations that can be set via environment variables to control the behavior of Ferroc:\n\n- `FE_SLAB_SHIFT`: Set the slab size (in bits) for all the data structures, a.k.a. the minimal allocation unit of arenas. Default is 22.\n- `FE_SHARD_SHIFT`: Set the shard size (in bits) for all the data structures, a.k.a. the minimal allocation unit of slabs. Default is 16.\n\nThose configurations are not exported as cargo features due to the requirement of additiveness.\n\n## Building process for CMake users\n\n1. Download and install the latest nightly Rust toolchain:\n\n```bash\ncurl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs |\\\n    sh -- -y --toolchain nightly --profile minimal -c rust-src\n```\n\n2. Just `cmake` and `make` it:\n\n```bash\nmkdir target \u0026\u0026 cd target # Required to be `target`. Don't change it to `build` or other names.\ncmake .. \u0026\u0026 make\n```\n\n3. If you want to install the library:\n\n```bash\nsudo make install\n```\n\nCommon options like `--install-prefix` and `--config` are supported naturally by CMake.\n\nThere are also some custom options (via `cmake -D`) you can enable:\n\n- `FE_TRACK_VALGRIND`: See [`\"track-valgrind\"`](#cargo-features) above;\n- `FE_FINER_GRAINED`: See [`\"finer-grained\"`](#cargo-features) above.\n- `FE_PGO_GATHER`: Enable PGO (Profile-Guided Optimization) gathering.\n- `FE_PGO_USE`: Build with optimization from pre-gathered PGO data (which requires appending ` llvm-tools` to the second line of step 1).\n\nAdditionally, environment variables (see [the section above](#environment-variables)) can also be used to control the build.\n\n## Benchmarks\n\nUsing a subset of [`mimalloc-bench`](https://github.com/daanx/mimalloc-bench) for benchmarking. Running on my laptop with 16GB of RAM and an Intel i7-10750H CPU @ 2.60GHz. The process is repeated 10 times.\n\nTime consumed:\n\n![Time consumed #1](./assets/time1.png)\n![Time consumed #2](./assets/time2.png)\n\nMemory consumed:\n\n![Memory consumed #1](./assets/memory1.png)\n![Memory consumed #2](./assets/memory2.png)\n\n## Caveats\n\nThis crate only supports the latest nightly Rust compiler currently and utilizes many unstable features. Use it with care.\n\n### License\n\nLicensed under either of\n\n* Apache License, Version 2.0 ([LICENSE-APACHE](LICENSE-APACHE))\n* MIT license ([LICENSE-MIT](LICENSE-MIT))\n\nat your option.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjs2xxx%2Fferroc","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjs2xxx%2Fferroc","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjs2xxx%2Fferroc/lists"}