aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Chris Beck <beck.ct@gmail.com> 2019-09-05 14:00:23 -0700
committerGravatar Carl Lerche <me@carllerche.com> 2019-09-05 14:00:23 -0700
commitc17e40115f5bb2a2db71ed90dceae6ec643dc024 (patch)
tree5457d4a726f8e16120c02976fa8b07caf07df0f1
parent73426dfaa3e56884977d7822b79696ac2cc96a42 (diff)
downloadbytes-c17e40115f5bb2a2db71ed90dceae6ec643dc024.tar.gz
bytes-c17e40115f5bb2a2db71ed90dceae6ec643dc024.tar.zst
bytes-c17e40115f5bb2a2db71ed90dceae6ec643dc024.zip
Add no_std support, by adding an `std` feature (#281)
To make the library work as `no_std` we add an `std` feature which is on by default. When it is off, we compile as `no_std` and make parts of the API that require `std::io` conditional on the `std` feature.
-rw-r--r--Cargo.toml4
-rw-r--r--ci/azure-test-stable.yml4
-rw-r--r--src/buf/buf_impl.rs16
-rw-r--r--src/buf/buf_mut.rs18
-rw-r--r--src/buf/chain.rs4
-rw-r--r--src/buf/mod.rs8
-rw-r--r--src/buf/take.rs2
-rw-r--r--src/buf/vec_deque.rs2
-rw-r--r--src/bytes.rs27
-rw-r--r--src/debug.rs2
-rw-r--r--src/either.rs4
-rw-r--r--src/hex.rs2
-rw-r--r--src/lib.rs7
-rw-r--r--src/serde.rs2
14 files changed, 77 insertions, 25 deletions
diff --git a/Cargo.toml b/Cargo.toml
index 9ec601d..746a193 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -19,6 +19,10 @@ edition = "2018"
publish = false
+[features]
+default = ["std"]
+std = []
+
[dependencies]
serde = { version = "1.0", optional = true }
either = { version = "1.5", default-features = false, optional = true }
diff --git a/ci/azure-test-stable.yml b/ci/azure-test-stable.yml
index dd15616..b402696 100644
--- a/ci/azure-test-stable.yml
+++ b/ci/azure-test-stable.yml
@@ -40,3 +40,7 @@ jobs:
- ${{ if parameters.benches }}:
- script: cargo check --benches
displayName: Check benchmarks
+
+ # Run with no default defaults
+ - script: cargo ${{ parameters.cmd }}
+ displayName: cargo ${{ parameters.cmd }} --no-default-features
diff --git a/src/buf/buf_impl.rs b/src/buf/buf_impl.rs
index e126bb4..b9e9141 100644
--- a/src/buf/buf_impl.rs
+++ b/src/buf/buf_impl.rs
@@ -1,6 +1,14 @@
-use super::{Take, Reader, Chain};
+use super::{Take, Chain};
-use std::{cmp, io::IoSlice, ptr, mem};
+#[cfg(feature = "std")]
+use super::Reader;
+
+use core::{cmp, ptr, mem};
+
+#[cfg(feature = "std")]
+use std::io::IoSlice;
+
+use alloc::{boxed::Box};
macro_rules! buf_get_impl {
($this:ident, $typ:tt::$conv:tt) => ({
@@ -148,6 +156,7 @@ pub trait Buf {
/// with `dst` being a zero length slice.
///
/// [`writev`]: http://man7.org/linux/man-pages/man2/readv.2.html
+ #[cfg(feature = "std")]
fn bytes_vectored<'a>(&'a self, dst: &mut [IoSlice<'a>]) -> usize {
if dst.is_empty() {
return 0;
@@ -884,6 +893,7 @@ pub trait Buf {
/// assert_eq!(11, num);
/// assert_eq!(&dst[..11], &b"hello world"[..]);
/// ```
+ #[cfg(feature = "std")]
fn reader(self) -> Reader<Self> where Self: Sized {
super::reader::new(self)
}
@@ -915,6 +925,7 @@ impl<T: Buf + ?Sized> Buf for &mut T {
(**self).bytes()
}
+ #[cfg(feature = "std")]
fn bytes_vectored<'b>(&'b self, dst: &mut [IoSlice<'b>]) -> usize {
(**self).bytes_vectored(dst)
}
@@ -933,6 +944,7 @@ impl<T: Buf + ?Sized> Buf for Box<T> {
(**self).bytes()
}
+ #[cfg(feature = "std")]
fn bytes_vectored<'b>(&'b self, dst: &mut [IoSlice<'b>]) -> usize {
(**self).bytes_vectored(dst)
}
diff --git a/src/buf/buf_mut.rs b/src/buf/buf_mut.rs
index 7cd6be8..1571580 100644
--- a/src/buf/buf_mut.rs
+++ b/src/buf/buf_mut.rs
@@ -1,6 +1,12 @@
-use super::{Writer};
+#[cfg(feature = "std")]
+use super::Writer;
-use std::{mem, cmp, io::IoSliceMut, ptr, usize};
+use core::{mem, cmp, ptr, usize};
+
+#[cfg(feature = "std")]
+use std::io::IoSliceMut;
+
+use alloc::{vec::Vec, boxed::Box};
/// A trait for values that provide sequential write access to bytes.
///
@@ -185,6 +191,7 @@ pub trait BufMut {
/// with `dst` being a zero length slice.
///
/// [`readv`]: http://man7.org/linux/man-pages/man2/readv.2.html
+ #[cfg(feature = "std")]
unsafe fn bytes_vectored_mut<'a>(&'a mut self, dst: &mut [IoSliceMut<'a>]) -> usize {
if dst.is_empty() {
return 0;
@@ -913,6 +920,7 @@ pub trait BufMut {
///
/// assert_eq!(*buf, b"hello world"[..]);
/// ```
+ #[cfg(feature = "std")]
fn writer(self) -> Writer<Self> where Self: Sized {
super::writer::new(self)
}
@@ -927,6 +935,7 @@ impl<T: BufMut + ?Sized> BufMut for &mut T {
(**self).bytes_mut()
}
+ #[cfg(feature = "std")]
unsafe fn bytes_vectored_mut<'b>(&'b mut self, dst: &mut [IoSliceMut<'b>]) -> usize {
(**self).bytes_vectored_mut(dst)
}
@@ -945,6 +954,7 @@ impl<T: BufMut + ?Sized> BufMut for Box<T> {
(**self).bytes_mut()
}
+ #[cfg(feature = "std")]
unsafe fn bytes_vectored_mut<'b>(&'b mut self, dst: &mut [IoSliceMut<'b>]) -> usize {
(**self).bytes_vectored_mut(dst)
}
@@ -968,7 +978,7 @@ impl BufMut for &mut [u8] {
#[inline]
unsafe fn advance_mut(&mut self, cnt: usize) {
// Lifetime dance taken from `impl Write for &mut [u8]`.
- let (_, b) = std::mem::replace(self, &mut []).split_at_mut(cnt);
+ let (_, b) = core::mem::replace(self, &mut []).split_at_mut(cnt);
*self = b;
}
}
@@ -994,7 +1004,7 @@ impl BufMut for Vec<u8> {
#[inline]
unsafe fn bytes_mut(&mut self) -> &mut [u8] {
- use std::slice;
+ use core::slice;
if self.capacity() == self.len() {
self.reserve(64); // Grow the vec
diff --git a/src/buf/chain.rs b/src/buf/chain.rs
index 7d03d36..a66e3e8 100644
--- a/src/buf/chain.rs
+++ b/src/buf/chain.rs
@@ -1,5 +1,7 @@
use crate::{Buf, BufMut};
use crate::buf::IntoIter;
+
+#[cfg(feature = "std")]
use std::io::{IoSlice, IoSliceMut};
/// A `Chain` sequences two buffers.
@@ -178,6 +180,7 @@ impl<T, U> Buf for Chain<T, U>
self.b.advance(cnt);
}
+ #[cfg(feature = "std")]
fn bytes_vectored<'a>(&'a self, dst: &mut [IoSlice<'a>]) -> usize {
let mut n = self.a.bytes_vectored(dst);
n += self.b.bytes_vectored(&mut dst[n..]);
@@ -227,6 +230,7 @@ impl<T, U> BufMut for Chain<T, U>
self.b.advance_mut(cnt);
}
+ #[cfg(feature = "std")]
unsafe fn bytes_vectored_mut<'a>(&'a mut self, dst: &mut [IoSliceMut<'a>]) -> usize {
let mut n = self.a.bytes_vectored_mut(dst);
n += self.b.bytes_vectored_mut(&mut dst[n..]);
diff --git a/src/buf/mod.rs b/src/buf/mod.rs
index cd7373e..15e032d 100644
--- a/src/buf/mod.rs
+++ b/src/buf/mod.rs
@@ -20,15 +20,21 @@ mod buf_impl;
mod buf_mut;
mod chain;
mod iter;
-mod reader;
mod take;
mod vec_deque;
+
+// When std::io::Reader etc. traits are not available, skip these
+#[cfg(feature = "std")]
+mod reader;
+#[cfg(feature = "std")]
mod writer;
pub use self::buf_impl::Buf;
pub use self::buf_mut::BufMut;
pub use self::chain::Chain;
pub use self::iter::IntoIter;
+#[cfg(feature = "std")]
pub use self::reader::Reader;
pub use self::take::Take;
+#[cfg(feature = "std")]
pub use self::writer::Writer;
diff --git a/src/buf/take.rs b/src/buf/take.rs
index d4b1881..03f3141 100644
--- a/src/buf/take.rs
+++ b/src/buf/take.rs
@@ -1,6 +1,6 @@
use crate::Buf;
-use std::cmp;
+use core::cmp;
/// A `Buf` adapter which limits the bytes read from an underlying buffer.
///
diff --git a/src/buf/vec_deque.rs b/src/buf/vec_deque.rs
index 4464426..0b48b0a 100644
--- a/src/buf/vec_deque.rs
+++ b/src/buf/vec_deque.rs
@@ -1,4 +1,4 @@
-use std::collections::VecDeque;
+use alloc::collections::VecDeque;
use super::Buf;
diff --git a/src/bytes.rs b/src/bytes.rs
index 1d5583b..f48609a 100644
--- a/src/bytes.rs
+++ b/src/bytes.rs
@@ -2,12 +2,13 @@ use crate::{Buf, BufMut};
use crate::buf::IntoIter;
use crate::debug;
-use std::{cmp, fmt, mem, hash, slice, ptr, usize};
-use std::borrow::{Borrow, BorrowMut};
-use std::ops::{Deref, DerefMut, RangeBounds};
-use std::sync::atomic::{self, AtomicUsize, AtomicPtr};
-use std::sync::atomic::Ordering::{Relaxed, Acquire, Release, AcqRel};
-use std::iter::{FromIterator, Iterator};
+use core::{cmp, fmt, mem, hash, slice, ptr, usize};
+use core::ops::{Deref, DerefMut, RangeBounds};
+use core::sync::atomic::{self, AtomicUsize, AtomicPtr};
+use core::sync::atomic::Ordering::{Relaxed, Acquire, Release, AcqRel};
+use core::iter::{FromIterator, Iterator};
+
+use alloc::{vec::Vec, string::String, boxed::Box, borrow::{Borrow, BorrowMut}};
/// A reference counted contiguous slice of memory.
///
@@ -316,10 +317,10 @@ struct Inner {
}
// Thread-safe reference-counted container for the shared storage. This mostly
-// the same as `std::sync::Arc` but without the weak counter. The ref counting
+// the same as `core::sync::Arc` but without the weak counter. The ref counting
// fns are based on the ones found in `std`.
//
-// The main reason to use `Shared` instead of `std::sync::Arc` is that it ends
+// The main reason to use `Shared` instead of `core::sync::Arc` is that it ends
// up making the overall code simpler and easier to reason about. This is due to
// some of the logic around setting `Inner::arc` and other ways the `arc` field
// is used. Using `Arc` ended up requiring a number of funky transmutes and
@@ -527,7 +528,7 @@ impl Bytes {
/// Requires that `begin <= end` and `end <= self.len()`, otherwise slicing
/// will panic.
pub fn slice(&self, range: impl RangeBounds<usize>) -> Bytes {
- use std::ops::Bound;
+ use core::ops::Bound;
let len = self.len();
@@ -857,7 +858,7 @@ impl Bytes {
/// assert_eq!(iter.next().map(|b| *b), Some(b'c'));
/// assert_eq!(iter.next(), None);
/// ```
- pub fn iter<'a>(&'a self) -> std::slice::Iter<'a, u8> {
+ pub fn iter<'a>(&'a self) -> core::slice::Iter<'a, u8> {
self.bytes().iter()
}
}
@@ -1031,7 +1032,7 @@ impl IntoIterator for Bytes {
impl<'a> IntoIterator for &'a Bytes {
type Item = &'a u8;
- type IntoIter = std::slice::Iter<'a, u8>;
+ type IntoIter = core::slice::Iter<'a, u8>;
fn into_iter(self) -> Self::IntoIter {
self.as_ref().into_iter()
@@ -1539,7 +1540,7 @@ impl BytesMut {
/// assert_eq!(iter.next().map(|b| *b), Some(b'c'));
/// assert_eq!(iter.next(), None);
/// ```
- pub fn iter<'a>(&'a self) -> std::slice::Iter<'a, u8> {
+ pub fn iter<'a>(&'a self) -> core::slice::Iter<'a, u8> {
self.bytes().iter()
}
}
@@ -1780,7 +1781,7 @@ impl IntoIterator for BytesMut {
impl<'a> IntoIterator for &'a BytesMut {
type Item = &'a u8;
- type IntoIter = std::slice::Iter<'a, u8>;
+ type IntoIter = core::slice::Iter<'a, u8>;
fn into_iter(self) -> Self::IntoIter {
self.as_ref().into_iter()
diff --git a/src/debug.rs b/src/debug.rs
index 32d8868..b1a3cc8 100644
--- a/src/debug.rs
+++ b/src/debug.rs
@@ -1,4 +1,4 @@
-use std::fmt;
+use core::fmt;
/// Alternative implementation of `fmt::Debug` for byte slice.
///
diff --git a/src/either.rs b/src/either.rs
index 954dfff..76bee80 100644
--- a/src/either.rs
+++ b/src/either.rs
@@ -2,6 +2,8 @@ use crate::{Buf, BufMut};
use either::Either;
use either::Either::*;
+
+#[cfg(feature = "std")]
use std::io::{IoSlice, IoSliceMut};
impl<L, R> Buf for Either<L, R>
@@ -23,6 +25,7 @@ where
}
}
+ #[cfg(feature = "std")]
fn bytes_vectored<'a>(&'a self, dst: &mut [IoSlice<'a>]) -> usize {
match *self {
Left(ref b) => b.bytes_vectored(dst),
@@ -64,6 +67,7 @@ where
}
}
+ #[cfg(feature = "std")]
unsafe fn bytes_vectored_mut<'a>(&'a mut self, dst: &mut [IoSliceMut<'a>]) -> usize {
match *self {
Left(ref mut b) => b.bytes_vectored_mut(dst),
diff --git a/src/hex.rs b/src/hex.rs
index d3fdafb..48ae6a4 100644
--- a/src/hex.rs
+++ b/src/hex.rs
@@ -1,5 +1,5 @@
use crate::{Bytes, BytesMut};
-use std::fmt::{Formatter, LowerHex, Result, UpperHex};
+use core::fmt::{Formatter, LowerHex, Result, UpperHex};
struct BytesRef<'a>(&'a [u8]);
diff --git a/src/lib.rs b/src/lib.rs
index 114de41..af4dfee 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -71,6 +71,13 @@
#![deny(warnings, missing_docs, missing_debug_implementations, rust_2018_idioms)]
#![doc(html_root_url = "https://docs.rs/bytes/0.5.0")]
+#![no_std]
+
+extern crate alloc;
+
+#[cfg(feature = "std")]
+extern crate std;
+
pub mod buf;
pub use crate::buf::{
Buf,
diff --git a/src/serde.rs b/src/serde.rs
index 7ade4d9..8f6b902 100644
--- a/src/serde.rs
+++ b/src/serde.rs
@@ -1,4 +1,4 @@
-use std::{cmp, fmt};
+use core::{cmp, fmt};
use serde::{Serialize, Serializer, Deserialize, Deserializer, de};
use super::{Bytes, BytesMut};