Skip to main content

BStackGuardedSlice

Trait BStackGuardedSlice 

Source
pub trait BStackGuardedSlice<'a, A: BStackAllocator + 'a>
where Self: 'a,
{ // Required methods fn len(&self) -> u64; unsafe fn raw_block(&self) -> BStackSlice<'a, A>; // Provided methods fn as_slice(&self) -> Result<BStackSlice<'a, A>, Error> { ... } fn is_empty(&self) -> bool { ... } fn pre_read(&self, _offset: u64, _len: u64) -> Result<()> { ... } fn post_read<'d>(&self, data: &'d [u8]) -> Result<Cow<'d, [u8]>> { ... } fn pre_write<'d>(&self, data: &'d [u8]) -> Result<Cow<'d, [u8]>> { ... } fn post_write(&self, _offset: u64, _len: u64) -> Result<()> { ... } fn read(&self) -> Result<Vec<u8>> { ... } fn write(&self, data: impl AsRef<[u8]>) -> Result<()> { ... } fn zero(&self) -> Result<()> { ... } }
Expand description

A BStackSlice abstraction with lifecycle hooks for transparent I/O interception.

A is the allocator type, given as a generic parameter so that a single implementing struct can satisfy BStackGuardedSlice<'a, A> for any allocator without being locked to one concrete choice.

§Required method

Implement as_slice to bind the trait to an underlying BStackSlice. All other methods have working defaults.

§Hook methods

Override any combination of the four hook methods to intercept I/O:

HookWhen it fires
pre_readBefore bytes are read from disk. Return Err to deny.
post_readAfter bytes arrive from disk. Transform or pass through.
pre_writeBefore bytes are sent to disk. Transform or pass through.
post_writeAfter a successful write. Audit or update metadata.

All four hooks default to no-ops. post_read and pre_write return Cow::Borrowed, so no allocation occurs in the non-transforming path.

§Lifetime

'a is the allocator lifetime, matching BStackSlice<'a, A>. All implementors must satisfy Self: 'a and A: 'a.

Required Methods§

Source

fn len(&self) -> u64

The length of the data in this guarded view.

This should return the length of the apparent slice returned by as_slice, not the underlying raw block length.

Source

unsafe fn raw_block(&self) -> BStackSlice<'a, A>

The raw I/O block for this guarded view.

Defaults to as_slice. Override when hooks operate on a coarser granularity than the slice — for example, a block cipher that must process aligned 16-byte blocks.

Used by [FullBlockSubview] to issue reads against the full block rather than the narrowed sub-range.

§Safety

In general, calling this method is only safe when pre and post read/write hooks are not active or are called during the call, otherwise the caller may risk data corruption or undefined behavior. Prefer overriding as_slice when possible.

Provided Methods§

Source

fn as_slice(&self) -> Result<BStackSlice<'a, A>, Error>

The apparent slice for this guard view.

All I/O methods appears to operate within this slice, and all hooks receive offsets relative to this slice. The implementation should only return Some if the usage of this view is somehow safe and reflect the actual underlying data. For example, exposing a cyphertext for encrypted data does not help the caller to understand the actual plaintext data, so for a guard that performs decryption, this method should return None since there is no clear mapping between the apparent slice and the underlying data.

The returned slice should have length equal to called len().

Source

fn is_empty(&self) -> bool

Returns true if this guarded view contains no data.

This is a convenience method that defaults to self.len() == 0.

Source

fn pre_read(&self, _offset: u64, _len: u64) -> Result<()>

Called before a read at [offset, offset + len) within the Range.

Calling this method directly is not recommended. Use read instead, which automatically fires the hooks and handles the necessary allocations.

offset is absolute to the crate::BStack, and len is the number of bytes of the raw block to be read (before any post_read transformation). Return Err to deny the operation.

Source

fn post_read<'d>(&self, data: &'d [u8]) -> Result<Cow<'d, [u8]>>

Called with the raw bytes just read from the underlying store.

Calling this method directly is not recommended. Use read instead, which automatically fires the hooks and handles the necessary allocations.

Return Cow::Borrowed to pass through without allocation; return Cow::Owned for decryption, decompression, or other transformations.

Callers that expect a fixed output size (e.g., read_into) will return InvalidData if the returned slice has a different length than data.

Source

fn pre_write<'d>(&self, data: &'d [u8]) -> Result<Cow<'d, [u8]>>

Called with the data about to be written.

Calling this method directly is not recommended. Use write instead, which automatically fires the hooks and handles the necessary allocations.

Return Cow::Borrowed to pass through without allocation; return Cow::Owned for encryption, compression, or other transformations.

Source

fn post_write(&self, _offset: u64, _len: u64) -> Result<()>

Called after a successful write at [offset, offset + len).

Calling this method directly is not recommended. Use write instead, which automatically fires the hooks and handles the necessary allocations.

offset is absolute offset within the crate::BStack, and len is the length of the original data passed to pre_write (not the transformed length returned by pre_write). (before any pre_write transformation).

Source

fn read(&self) -> Result<Vec<u8>>

Read the entire slice into a newly allocated Vec<u8>.

Fires pre_read(0, slice.len()), reads raw bytes, then passes them through post_read. The transformation may change the returned length.

This method at maximum allocates twice the slice length (once for the raw read and once for the transformed output).

Source

fn write(&self, data: impl AsRef<[u8]>) -> Result<()>

Overwrite the beginning of this slice with data.

Passes data through pre_write before writing. Writes min(self.len(), data.len()) bytes, and passes the original length to post_write.

Requires feature set.

Source

fn zero(&self) -> Result<()>

Zero the entire slice.

Constructs a zero buffer, passes it through pre_write (allowing hooks to substitute a different fill pattern), then writes the result.

Requires feature set.

Dyn Compatibility§

This trait is not dyn compatible.

In older versions of Rust, dyn compatibility was called "object safety", so this trait is not object safe.

Implementors§