# Bitcraft Macro Showcase & Expansion ⚙️
This document explains the functionality of the `bitcraft` engine and provides the **struct equivalent** code that the Rust compiler actually expands during compilation, reflecting the latest performance optimizations.
---
## 1. `bitenum!` (Type-Safe Enumerations)
Generates a zero-cost, memory-safe enumeration that resolves to the narrowest possible CPU primitive. It now includes pre-computed range constants.
### **Usage**
```rust
bitenum! {
pub enum ConnectionState(2) {
DISCONNECTED = 0,
CONNECTING = 1,
CONNECTED = 2,
}
}
```
### **Generated "Struct Equivalent"**
```rust
#[derive(Copy, Clone, PartialEq, Eq, Default)]
#[repr(transparent)]
pub struct ConnectionState(pub u8);
impl ConnectionState {
pub const DISCONNECTED: Self = Self(0);
pub const CONNECTING: Self = Self(1);
pub const CONNECTED: Self = Self(2);
/// The number of bits allocated for this enumeration in memory.
pub const BITS: usize = 2;
/// The maximum value allowed for this enumeration variant.
pub const MASK: u8 = 0b11;
#[inline(always)]
pub const fn is_defined(self) -> bool {
match self.0 {
0 | 1 | 2 => true,
_ => false,
}
}
#[inline(always)]
pub const fn to_bits(self) -> u8 { self.0 }
#[inline(always)]
pub const fn from_bits(val: u8) -> Self {
debug_assert!(val <= Self::MASK);
Self(val)
}
#[inline(always)]
pub const fn try_from_bits(val: u8) -> Result<Self, BitstructError> {
let s = Self(val);
if s.is_defined() { Ok(s) } else { Err(...) }
}
}
```
---
## 2. `bitstruct!` (Word-Aligned Packing)
Packs multiple logical fields into a single standard CPU register (`u8`-`u128`). Now utilizes named constants for offsets and masks.
### **Usage**
```rust
bitstruct! {
pub struct Status(u8) {
pub ready: bool = 1,
pub mode: u8 = 3,
}
}
```
### **Generated "Struct Equivalent"**
```rust
#[derive(Copy, Clone, PartialEq, Eq, Default)]
#[repr(transparent)]
pub struct Status(pub u8);
impl Status {
const READY_OFFSET: usize = 0;
const READY_MASK: u8 = 0x01;
#[inline]
pub const fn ready(self) -> bool {
((self.0 >> Self::READY_OFFSET) & Self::READY_MASK) != 0
}
#[inline]
pub fn set_ready(&mut self, val: bool) {
let val_masked = val as u8;
self.0 = (self.0 & !(Self::READY_MASK << Self::READY_OFFSET))
| (val_masked << Self::READY_OFFSET);
}
const MODE_OFFSET: usize = 1;
const MODE_MASK: u8 = 0x07;
#[inline]
pub const fn mode(self) -> u8 {
((self.0 >> Self::MODE_OFFSET) & Self::MODE_MASK) as u8
}
#[inline]
pub fn set_mode(&mut self, val: u8) {
debug_assert!(val <= Self::MODE_MASK);
let val_masked = val & Self::MODE_MASK;
self.0 = (self.0 & !(Self::MODE_MASK << Self::MODE_OFFSET))
| (val_masked << Self::MODE_OFFSET);
}
}
```
---
## 3. `bytestruct!` (Array-Backed Dense Packing)
Native support for arbitrary-length dense buffers (`[u8; N]`) using **Const-Generic Helper Functions** and alignment-aware fast paths.
### **Usage**
```rust
bytestruct! {
pub struct Node(2) {
pub a: u8 = 4,
pub b: u16 = 12,
}
}
```
### **Generated "Struct Equivalent"**
The macro generates a **"Literal Guard"** pattern inside optimized helper functions:
```rust
#[repr(transparent)]
pub struct Node(pub [u8; 2]);
impl Node {
const B_OFFSET: usize = 4;
const B_MASK: u128 = 0x0FFF;
#[inline]
pub const fn b(self) -> u16 {
// Optimized helper: for this case, it performs a 16-bit load
// since the span is byte-aligned (after internal resolution).
const BYTE_INDEX: usize = Self::B_OFFSET >> 3;
const BIT_OFFSET: usize = Self::B_OFFSET & 7;
const BYTE_COUNT: usize = ((Self::B_OFFSET + 12 + 7) >> 3) - BYTE_INDEX;
// Internal bit-loop optimized via while loop (in read_le_bits):
// while i < BYTE_COUNT { acc |= (arr[BYTE_INDEX + i] as u64) << (i << 3); i += 1; }
let val = ::bitcraft::read_le_bits::<{ Self::B_OFFSET }, 12, _, BYTE_INDEX, BIT_OFFSET, BYTE_COUNT>(&self.0);
val as u16
}
#[inline]
pub fn set_b(&mut self, val: u16) {
debug_assert!((val as u128) <= Self::B_MASK);
const BYTE_INDEX: usize = Self::B_OFFSET >> 3;
const BIT_OFFSET: usize = Self::B_OFFSET & 7;
const BYTE_COUNT: usize = ((Self::B_OFFSET + 12 + 7) >> 3) - BYTE_INDEX;
::bitcraft::write_le_bits::<{ Self::B_OFFSET }, 12, _, BYTE_INDEX, BIT_OFFSET, BYTE_COUNT>(&mut self.0, val as u128);
}
}
```
---
## 4. `byteval!` (Packed ID NewTypes)
Shorthand for "Odd-Width" integers like 24-bit or 40-bit IDs. Utilizes the same optimized helpers as `bytestruct!`.
### **Usage**
```rust
byteval! { pub struct Id24(3); }
```
### **Generated "Struct Equivalent"**
```rust
#[repr(transparent)]
pub struct Id24(pub [u8; 3]);
impl Id24 {
/// Native conversion to the widest capable primitive.
#[inline(always)]
pub const fn to_u32(self) -> u32 {
// Specialized conversion: uses a recursive single-expression OR chain.
// Highly optimized by LLVM into a single 24-bit aligned load where possible.
0 | (self.0[0] as u32) << (0 << 3)
| (self.0[1] as u32) << (1 << 3)
| (self.0[2] as u32) << (2 << 3)
}
#[inline(always)]
pub const fn from_u32(val: u32) -> Self {
// Specialized writeback: uses a single array constructor with shifts.
Self([
(val >> 0) as u8,
(val >> 8) as u8,
(val >> 16) as u8,
])
}
#[inline(always)]
pub const fn to_bits(self) -> u32 { self.to_u32() }
const VALUE_OFFSET: usize = 0;
const VALUE_MASK: u128 = 0x00FFFFFF;
#[inline]
pub const fn value(self) -> u32 {
const BYTE_INDEX: usize = Self::VALUE_OFFSET >> 3;
const BIT_OFFSET: usize = Self::VALUE_OFFSET & 7;
const BYTE_COUNT: usize = ((Self::VALUE_OFFSET + 24 + 7) >> 3) - BYTE_INDEX;
// Field access: utilizes read_le_bits which uses a while loop for accumulation.
let val = ::bitcraft::read_le_bits::<{ Self::VALUE_OFFSET }, 24, _, BYTE_INDEX, BIT_OFFSET, BYTE_COUNT>(&self.0);
val as u32
}
}
```
---
## 🔍 Visibility and Inspection
To see the real, machine-generated expansion for any macro in your project, install the `cargo-expand` tool:
```bash
cargo install cargo-expand
cargo expand --example your_example
```
Our build system provides a filtered expansion specifically for the engine's internals via `make expand-sample`, which generates the clean `sample/expanded_sample.rs` file you see in the repository.