Crates.io | onsen |
lib.rs | onsen |
version | 0.14.0 |
source | src |
created_at | 2022-07-28 13:51:47.828668 |
updated_at | 2022-09-13 19:02:25.318047 |
description | Memory pool |
homepage | |
repository | https://github.com/cehteh/onsen.git |
max_upload_size | |
id | 634422 |
size | 134,894 |
Onsen provides hot Pools for objects. In most cases allocation from such a Pool is faster and offers better locality than the standard allocator. For small to medium sized objects the performance improvement is around 20% or better. For large objects the gains become smaller as caching effects even out. These improvements cover operating on objects because of locality, not just faster allocation speeds.
Onsen pools allocate blocks with exponentially growing sizes. Allocations are served from these blocks. Freed entries are kept in a double linked cyclic freelist. This freelist is kept in weakly ordered and the entry point always point close to where the last action happend to keep the caches hot.
Onsen comes with its own Box
and Rc
/Weak
implementations that wrap the underlying
RcPool
in a safe way. A Sc
reference counted box without weak reference support is
available as well and provides an advantage for small objects where the weak count would add
some weight.
For each of these a variant that uses static global pools is avaialble as well.
Allocating from a pool returns Slot
handles. These are lightweight abstractions to memory
addresses, they do not keep a relation to the pool they are allocated from. The rationale for
this design is to make them usable in a VM that uses NaN tagging.
Slots are guarded by typestate policies which prevent some wrong use at compile time.
Because of this slots need to be handled with care and certain contracts need to be
enforced. The library provides some help to ensure correctness. Few things can not be asserted
and are guarded by unsafe functions. Higher level API's (Such as Box
, Rc
and Sc
above) can
easily enforce these in a safe way.
pool.leak()
which drops a pool while leaking its memory blocks. This can be
used when one will never try to free memory obtained from that Pool.Slot
.
This is the main reason that makes the Slot
freeing functions unsafe. There is no way
for a pool to know if references are still in use. One should provide or use a safe
abstraction around references to enforce this.
Onsen provides a singlethreaded Pool
, a singlethreaded reference counted RcPool
and a
multithreaded TPool
. Additional features are gated with feature flags.
TPool
(instead std::sync::Mutex
). This makes
sense when parking lot is already in use. There is no significant performance benefit from
this in onsen.STPool
available, a singlethreaded pool that uses a ThreadCell
which
is much faster than mutex protected pools. This pools can be moved cooperatively between
threads with acquire/release semantics.TBox
, TRc
, TSc
that use a global pool per type. The
advantage is that the box does not need to store a reference to its pool which saves a bit
memory and improves locality for small objects.STPool
for the tbox API, this enables tbox and stpool as well.st_tbox is the default. This enables the most complete API with best performance.
Onsen pools are optimized for cache locality and with that to some extend for singlethreaded use. It is best to have one pool per type per thread.
The TPool
adds a mutex to be used in multithreaded cases but its performance is
significantly less than the singlethreaded pools but in many cases still better than the
std allocator. One will still benefit from locality though.
The STPool
is singlethreaded but can be cooperatively passed between threads, its
performance is on par with the other singlethreaded pools. This is especially important
when one uses TBox
, TRc
or TSc
.
Onsen uses criterion for benchmarking, since onsen is made for singlethreaded application its best to be tested when locked on a single CPU core and lock the core to some frequency well below the max to give more consistent results. At higher priority so it wont be disturbed as much from other programs. On Linux you may do something like:
sudo renice -15 $$
sudo cpupower -c 1 frequenc-set -f 2.8GHz
taskset 2 cargo bench
Will produce target/criterion/report/index.html
.