Skip to content

Consider switching Bytes to a "trait object", supporting custom memory management strategies. #294

@carllerche

Description

@carllerche

Currently, Bytes uses its own internal implementation for memory management. It supports a few strategies:

  • Vec<u8>
  • Arc<Vec<u8>>
  • &'static [u8]
  • an inlined strategy.

However, using a fixed strategy prohibits alternate strategies that would be more appropriate to the use case in question. One example is initializing a Bytes instance backed by a file using mmap.

Proposal

The Bytes struct would be updated to:

struct Bytes {
    raw: RawBytes,
}

struct RawBytes {
    ptr: *const u8,
    len: usize,
    data: NonNull<()>,
    vtable: &'static Vtable,
}

struct Vtable {
    clone: unsafe fn(ptr: *const u8, len: usize, data: NonNull<()>) -> Bytes;
    drop: unsafe fn(data: NonNull<()>);
}

An additional Bytes::from_raw constructor would be added. The rest of the Bytes API can be implemented using the above APIs.

Provided strategies

By default, the bytes crate should provide some strategies for using Bytes. A default of Arc<Vec<u8>> seems sufficient. Feature flags can be used to opt-out of the default implementation.

BytesMut

The BytesMut structure is no longer a core part of the bytes API. It is unclear if it should stay in the bytes crate as an option or move out to a separate crate.

Inline representation

This proposal would remove the ability to initialize a Bytes instance using the "inline" representation. It is unclear how big of an impact this would have. It is also unclear if use cases that take advantage of "inline" representation would be able to use an alternate strategy enabled with this change.

Refs #269

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions