mirror of
https://github.com/serai-dex/serai.git
synced 2025-12-08 20:29:23 +00:00
Expose std_shims::io on core
The `io::Write` trait is somewhat worthless, being implemented for nothing, yet `Read` remains fully functional. This also allows using its polyfills _without_ requiring `alloc`. Opportunity taken to make `schnorr-signatures` not require `alloc`. This will require a version bump before being published due to newly requiring the `alloc` feature be specified to maintain pre-existing behavior. Enables resolving https://github.com/monero-oxide/monero-oxide/issues/48.
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
#[cfg(all(feature = "alloc", not(feature = "std")))]
|
||||
pub use extern_alloc::collections::*;
|
||||
#[cfg(all(feature = "alloc", not(feature = "std")))]
|
||||
pub use hashbrown::{HashSet, HashMap};
|
||||
|
||||
#[cfg(feature = "std")]
|
||||
pub use std::collections::*;
|
||||
|
||||
#[cfg(not(feature = "std"))]
|
||||
pub use alloc::collections::*;
|
||||
#[cfg(not(feature = "std"))]
|
||||
pub use hashbrown::{HashSet, HashMap};
|
||||
|
||||
@@ -1,42 +1,74 @@
|
||||
#[cfg(feature = "std")]
|
||||
pub use std::io::*;
|
||||
|
||||
#[cfg(not(feature = "std"))]
|
||||
mod shims {
|
||||
use core::fmt::{Debug, Formatter};
|
||||
use alloc::{boxed::Box, vec::Vec};
|
||||
use core::fmt::{self, Debug, Display, Formatter};
|
||||
#[cfg(feature = "alloc")]
|
||||
use extern_alloc::{boxed::Box, vec::Vec};
|
||||
use crate::error::Error as CoreError;
|
||||
|
||||
/// The kind of error.
|
||||
#[derive(Clone, Copy, PartialEq, Eq, Debug)]
|
||||
pub enum ErrorKind {
|
||||
UnexpectedEof,
|
||||
Other,
|
||||
}
|
||||
|
||||
/// An error.
|
||||
#[derive(Debug)]
|
||||
pub struct Error {
|
||||
kind: ErrorKind,
|
||||
error: Box<dyn Send + Sync>,
|
||||
#[cfg(feature = "alloc")]
|
||||
error: Box<dyn Send + Sync + CoreError>,
|
||||
}
|
||||
|
||||
impl Debug for Error {
|
||||
fn fmt(&self, fmt: &mut Formatter<'_>) -> core::result::Result<(), core::fmt::Error> {
|
||||
fmt.debug_struct("Error").field("kind", &self.kind).finish_non_exhaustive()
|
||||
impl Display for Error {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
|
||||
<Self as Debug>::fmt(self, f)
|
||||
}
|
||||
}
|
||||
impl CoreError for Error {}
|
||||
|
||||
#[cfg(not(feature = "alloc"))]
|
||||
pub trait IntoBoxSendSyncError {}
|
||||
#[cfg(not(feature = "alloc"))]
|
||||
impl<I> IntoBoxSendSyncError for I {}
|
||||
#[cfg(feature = "alloc")]
|
||||
pub trait IntoBoxSendSyncError: Into<Box<dyn Send + Sync + CoreError>> {}
|
||||
#[cfg(feature = "alloc")]
|
||||
impl<I: Into<Box<dyn Send + Sync + CoreError>>> IntoBoxSendSyncError for I {}
|
||||
|
||||
impl Error {
|
||||
pub fn new<E: 'static + Send + Sync>(kind: ErrorKind, error: E) -> Error {
|
||||
Error { kind, error: Box::new(error) }
|
||||
/// Create a new error.
|
||||
///
|
||||
/// The error object itself is silently dropped when `alloc` is not enabled.
|
||||
#[allow(unused)]
|
||||
pub fn new<E: 'static + IntoBoxSendSyncError>(kind: ErrorKind, error: E) -> Error {
|
||||
#[cfg(not(feature = "alloc"))]
|
||||
let res = Error { kind };
|
||||
#[cfg(feature = "alloc")]
|
||||
let res = Error { kind, error: error.into() };
|
||||
res
|
||||
}
|
||||
|
||||
pub fn other<E: 'static + Send + Sync>(error: E) -> Error {
|
||||
Error { kind: ErrorKind::Other, error: Box::new(error) }
|
||||
/// Create a new error with `io::ErrorKind::Other` as its kind.
|
||||
///
|
||||
/// The error object itself is silently dropped when `alloc` is not enabled.
|
||||
#[allow(unused)]
|
||||
pub fn other<E: 'static + IntoBoxSendSyncError>(error: E) -> Error {
|
||||
#[cfg(not(feature = "alloc"))]
|
||||
let res = Error { kind: ErrorKind::Other };
|
||||
#[cfg(feature = "alloc")]
|
||||
let res = Error { kind: ErrorKind::Other, error: error.into() };
|
||||
res
|
||||
}
|
||||
|
||||
/// The kind of error.
|
||||
pub fn kind(&self) -> ErrorKind {
|
||||
self.kind
|
||||
}
|
||||
|
||||
pub fn into_inner(self) -> Option<Box<dyn Send + Sync>> {
|
||||
/// Retrieve the inner error.
|
||||
#[cfg(feature = "alloc")]
|
||||
pub fn into_inner(self) -> Option<Box<dyn Send + Sync + CoreError>> {
|
||||
Some(self.error)
|
||||
}
|
||||
}
|
||||
@@ -94,6 +126,7 @@ mod shims {
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(feature = "alloc")]
|
||||
impl Write for Vec<u8> {
|
||||
fn write(&mut self, buf: &[u8]) -> Result<usize> {
|
||||
self.extend(buf);
|
||||
@@ -101,6 +134,8 @@ mod shims {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "std"))]
|
||||
pub use shims::*;
|
||||
|
||||
#[cfg(feature = "std")]
|
||||
pub use std::io::{ErrorKind, Error, Result, Read, BufRead, Write};
|
||||
|
||||
@@ -2,25 +2,44 @@
|
||||
#![doc = include_str!("../README.md")]
|
||||
#![cfg_attr(not(feature = "std"), no_std)]
|
||||
|
||||
pub extern crate alloc;
|
||||
#[cfg(not(feature = "alloc"))]
|
||||
pub use core::*;
|
||||
#[cfg(not(feature = "alloc"))]
|
||||
pub use core::{alloc, borrow, ffi, fmt, slice, str, task};
|
||||
|
||||
#[cfg(not(feature = "std"))]
|
||||
#[rustversion::before(1.81)]
|
||||
pub mod error {
|
||||
use core::fmt::Debug::Display;
|
||||
pub trait Error: Debug + Display {}
|
||||
}
|
||||
#[cfg(not(feature = "std"))]
|
||||
#[rustversion::since(1.81)]
|
||||
pub use core::error;
|
||||
|
||||
#[cfg(all(feature = "alloc", not(feature = "std")))]
|
||||
pub extern crate alloc as extern_alloc;
|
||||
#[cfg(all(feature = "alloc", not(feature = "std")))]
|
||||
pub use extern_alloc::{alloc, borrow, boxed, ffi, fmt, rc, slice, str, string, task, vec, format};
|
||||
#[cfg(feature = "std")]
|
||||
pub use std::{alloc, borrow, boxed, error, ffi, fmt, rc, slice, str, string, task, vec, format};
|
||||
|
||||
pub mod sync;
|
||||
pub mod collections;
|
||||
pub mod io;
|
||||
|
||||
pub use alloc::vec;
|
||||
pub use alloc::str;
|
||||
pub use alloc::string;
|
||||
pub mod sync;
|
||||
|
||||
pub mod prelude {
|
||||
pub use alloc::{
|
||||
// Shim the `std` prelude
|
||||
#[cfg(all(feature = "alloc", not(feature = "std")))]
|
||||
pub use extern_alloc::{
|
||||
format, vec,
|
||||
boxed::Box,
|
||||
borrow::ToOwned,
|
||||
boxed::Box,
|
||||
vec::Vec,
|
||||
string::{String, ToString},
|
||||
};
|
||||
|
||||
// Shim `div_ceil`
|
||||
#[rustversion::before(1.73)]
|
||||
#[doc(hidden)]
|
||||
pub trait StdShimsDivCeil {
|
||||
@@ -61,6 +80,7 @@ pub mod prelude {
|
||||
}
|
||||
}
|
||||
|
||||
// Shim `io::Error::other`
|
||||
#[cfg(feature = "std")]
|
||||
#[rustversion::before(1.74)]
|
||||
#[doc(hidden)]
|
||||
|
||||
@@ -1,19 +1,26 @@
|
||||
pub use core::sync::*;
|
||||
pub use alloc::sync::*;
|
||||
pub use core::sync::atomic;
|
||||
#[cfg(all(feature = "alloc", not(feature = "std")))]
|
||||
pub use extern_alloc::sync::{Arc, Weak};
|
||||
|
||||
mod mutex_shim {
|
||||
#[cfg(feature = "std")]
|
||||
pub use std::sync::*;
|
||||
#[cfg(not(feature = "std"))]
|
||||
pub use spin::*;
|
||||
pub use spin::{Mutex, MutexGuard};
|
||||
#[cfg(feature = "std")]
|
||||
pub use std::sync::{Mutex, MutexGuard};
|
||||
|
||||
/// A shimmed `Mutex` with an API mutual to `spin` and `std`.
|
||||
#[derive(Default, Debug)]
|
||||
pub struct ShimMutex<T>(Mutex<T>);
|
||||
impl<T> ShimMutex<T> {
|
||||
/// Construct a new `Mutex`.
|
||||
pub const fn new(value: T) -> Self {
|
||||
Self(Mutex::new(value))
|
||||
}
|
||||
|
||||
/// Acquire a lock on the contents of the `Mutex`.
|
||||
///
|
||||
/// On no-`std` environments, this may spin until the lock is acquired. On `std` environments,
|
||||
/// this may panic if the `Mutex` was poisoned.
|
||||
pub fn lock(&self) -> MutexGuard<'_, T> {
|
||||
#[cfg(feature = "std")]
|
||||
let res = self.0.lock().unwrap();
|
||||
@@ -25,10 +32,8 @@ mod mutex_shim {
|
||||
}
|
||||
pub use mutex_shim::{ShimMutex as Mutex, MutexGuard};
|
||||
|
||||
#[cfg(not(feature = "std"))]
|
||||
pub use spin::Lazy as LazyLock;
|
||||
#[rustversion::before(1.80)]
|
||||
#[cfg(feature = "std")]
|
||||
#[cfg(not(feature = "std"))]
|
||||
pub use spin::Lazy as LazyLock;
|
||||
#[rustversion::since(1.80)]
|
||||
#[cfg(feature = "std")]
|
||||
|
||||
Reference in New Issue
Block a user