Getting Started

ring-buffer-macro is a Rust procedural macro that generates compile-time ring buffer implementations from a simple tuple struct annotation.

Installation

Add ring-buffer-macro to your project:

cargo add ring-buffer-macro

Or add it directly to your Cargo.toml:

[dependencies]
ring-buffer-macro = "0.2"

Basic Example

Define a tuple struct with the #[ring_buffer(N)] attribute, where N is the buffer capacity:

1use ring_buffer_macro::ring_buffer;
2
3#[ring_buffer(5)]
4struct Buffer(i32);
5
6fn main() {
7 let mut buf = Buffer::new();
8 buf.enqueue(1).unwrap();
9 buf.enqueue(2).unwrap();
10 buf.enqueue(3).unwrap();
11
12 assert_eq!(buf.dequeue(), Some(1));
13 assert_eq!(buf.dequeue(), Some(2));
14 assert_eq!(buf.len(), 1);
15}

What the Macro Generates

The #[ring_buffer(N)] attribute transforms your tuple struct into a full ring buffer implementation with named fields and methods.

input
// You write:
#[ring_buffer(5)]
struct Buffer(i32);
generated
1// The macro generates:
2struct Buffer {
3 data: Vec<i32>,
4 capacity: usize,
5 head: usize,
6 tail: usize,
7 size: usize,
8}
9
10impl Buffer {
11 fn new() -> Self { /* ... */ }
12 fn enqueue(&mut self, item: i32) -> Result<(), i32> { /* ... */ }
13 fn dequeue(&mut self) -> Option<i32> { /* ... */ }
14 fn peek(&self) -> Option<&i32> { /* ... */ }
15 fn peek_mut(&mut self) -> Option<&mut i32> { /* ... */ }
16 fn peek_back(&self) -> Option<&i32> { /* ... */ }
17 fn is_full(&self) -> bool { /* ... */ }
18 fn is_empty(&self) -> bool { /* ... */ }
19 fn len(&self) -> usize { /* ... */ }
20 fn capacity(&self) -> usize { /* ... */ }
21 fn clear(&mut self) { /* ... */ }
22 fn iter(&self) -> impl Iterator<Item = &i32> { /* ... */ }
23 fn drain(&mut self) -> BufferDrain<i32> { /* ... */ }
24}

Configuration Options

The macro supports named parameters for advanced configuration:

OptionValuesDefaultDescription
capacitypositive integerrequiredMaximum number of elements
mode"standard", "spsc", "mpsc""standard"Buffer operation mode
power_of_twotrue, falsefalseUse bitwise AND for index wrap
cache_paddedtrue, falsefalse64-byte align head/tail
blockingtrue, falsefalseAdd blocking operations (SPSC/MPSC)
// Named parameter syntax
#[ring_buffer(capacity = 1024, mode = "spsc", power_of_two = true)]
struct FastBuffer(u64);
The simple syntax #[ring_buffer(5)] is shorthand for #[ring_buffer(capacity = 5)] in standard mode.