embed_collections/lib.rs
1#![allow(rustdoc::redundant_explicit_links)]
2#![cfg_attr(docsrs, feature(doc_cfg))]
3#![cfg_attr(docsrs, allow(unused_attributes))]
4//!
5//! # embed-collections
6//!
7//! A collection of memory efficient data structures, for embedding environment and server applications that need tight memory management.
8//!
9//! This repo consists some small crates.
10//!
11//! **NOTE: There nothing in the main crate, all modules have moved to sub crates**.
12//!
13//! ## Cache efficient collections
14//!
15//! - [embed-constvec](https://docs.rs/embed-constvec): Fixed capacity inline vec
16//! - [embed-seglist](https://docs.rs/embed-seglist): A cache aware (short-live) list to store elements with adaptive size segments
17//! - [embed-btree](https://docs.rs/embed-btree): A cache aware B+tree for lone-live and large dataset, optimized for numeric types, with special entry API allows peeking adjacent values.
18//!
19//! ## Intrusive collections:
20//!
21//! We support all-types from the [pointers](https://docs.rs/pointers) crate,
22//! with `Pointer` trait for intrusive collections:
23//! - raw pointers (`NonNull<T>`, `*const T`, `*mut T`)
24//! - std `Box` (owned),
25//! - std `Arc`, `Rc` (multiple ownership)
26//! - `Irc`: Highly customizable Intrusive Reference Counter.
27//! - [WaitGroupZeroGuard](https://docs.rs/crossfire/latest/crossfire/waitgroup/struct.WaitGroupZeroGuard.html): see the doc in `crossfire` crate
28//!
29//! Sub crates:
30//! - [embed-dlist](https://docs.rs/embed-dlist): Intrusive Doubly Linked List (Queue / Stack).
31//! - [embed-slist](https://docs.rs/embed-slist): Intrusive Singly Linked List ( Queue / stack).
32//! - [embed-avl](https://docs.rs/embed-avl): Intrusive AVL Tree (Balanced Binary Search Tree), port to rust from ZFS
33//!
34//! **Disclaimer**
35//!
36//! Intrusive code is not recommended unless you are full aware of what you are doing.
37//! Most traits are mark with `unsafe`. While we try to give you freedom, not letting the rules probibit
38//! you build highly customized logic, this library still has regular scheduled Miri test routine.
39//! But the disadvantages includes:
40//!
41//! - Complex to write (This crate seal most boilderplates)
42//!
43//! - Linking heap object to another is bad for cache hit (Use structure like `SegList` is preferable)
44//!
45//! There're three usage scenarios:
46//!
47//! 1. Push smart pointer to the list, so that the list hold 1 ref count when the type is `Arc` /
48//! `Rc`, but you have to use UnsafeCell for internal mutation.
49//!
50//! 2. Push `Box` to the list, the list own the items until they are popped, it's better than std
51//! LinkedList because no additional allocation is needed. It will not move the item
52//! in-and-out of hidden `Box` on every push / pop.
53//!
54//! 3. Push raw pointer (better use NonNull instead of *const T for smaller footprint) to the list,
55//! for temporary usage. You must ensure the list item not dropped be other refcount
56//! (for example, the item is holding by Arc in other structure).
57//!
58//!
59//! ### Difference to `intrusive-collections` crate
60//!
61//! This crate choose to use trait instead of c like `offset_of!`, mainly because:
62//!
63//! - Mangling with offset conversion makes the code hard to read (for people not used to c style coding).
64//!
65//! - You don't have to understand some complex macro style.
66//!
67//! - It's dangerous to use pointer offset conversion when the embedded Node not perfectly aligned,
68//! and using memtion to return the node ref is more safer approach.
69//! For example, the default `repr(Rust)` might reorder the field, or you mistakenly use `repr(packed)`.
70//!
71
72/// Cache line size in bytes
73#[cfg(any(
74 target_arch = "x86_64",
75 target_arch = "aarch64",
76 target_arch = "arm64ec",
77 target_arch = "powerpc64",
78))]
79pub const CACHE_LINE_SIZE: usize = 64;
80#[cfg(not(any(
81 target_arch = "x86_64",
82 target_arch = "aarch64",
83 target_arch = "arm64ec",
84 target_arch = "powerpc64",
85)))]
86pub const CACHE_LINE_SIZE: usize = 32;