//! Trait implementations for `ByteStr`. use crate::bstr::ByteStr; use crate::cmp::Ordering; use crate::slice::SliceIndex; use crate::{hash, ops, range}; #[unstable(feature = "bstr", issue = "134915")] impl Ord for ByteStr { #[inline] fn cmp(&self, other: &ByteStr) -> Ordering { Ord::cmp(&self.0, &other.0) } } #[unstable(feature = "bstr", issue = "134915")] impl PartialOrd for ByteStr { #[inline] fn partial_cmp(&self, other: &ByteStr) -> Option { PartialOrd::partial_cmp(&self.0, &other.0) } } #[unstable(feature = "bstr", issue = "134915")] impl PartialEq for ByteStr { #[inline] fn eq(&self, other: &ByteStr) -> bool { &self.0 == &other.0 } } #[unstable(feature = "bstr", issue = "134915")] impl Eq for ByteStr {} #[unstable(feature = "bstr", issue = "134915")] impl hash::Hash for ByteStr { #[inline] fn hash(&self, state: &mut H) { self.0.hash(state); } } #[doc(hidden)] #[macro_export] #[unstable(feature = "bstr_internals", issue = "none")] macro_rules! impl_partial_eq { ($lhs:ty, $rhs:ty) => { #[allow(unused_lifetimes)] impl<'a> PartialEq<$rhs> for $lhs { #[inline] fn eq(&self, other: &$rhs) -> bool { let other: &[u8] = other.as_ref(); PartialEq::eq(self.as_bytes(), other) } } #[allow(unused_lifetimes)] impl<'a> PartialEq<$lhs> for $rhs { #[inline] fn eq(&self, other: &$lhs) -> bool { let this: &[u8] = self.as_ref(); PartialEq::eq(this, other.as_bytes()) } } }; } #[doc(hidden)] #[unstable(feature = "bstr_internals", issue = "none")] pub use impl_partial_eq; #[doc(hidden)] #[macro_export] #[unstable(feature = "bstr_internals", issue = "none")] macro_rules! impl_partial_eq_ord { ($lhs:ty, $rhs:ty) => { $crate::bstr::impl_partial_eq!($lhs, $rhs); #[allow(unused_lifetimes)] #[unstable(feature = "bstr", issue = "134915")] impl<'a> PartialOrd<$rhs> for $lhs { #[inline] fn partial_cmp(&self, other: &$rhs) -> Option { let other: &[u8] = other.as_ref(); PartialOrd::partial_cmp(self.as_bytes(), other) } } #[allow(unused_lifetimes)] #[unstable(feature = "bstr", issue = "134915")] impl<'a> PartialOrd<$lhs> for $rhs { #[inline] fn partial_cmp(&self, other: &$lhs) -> Option { let this: &[u8] = self.as_ref(); PartialOrd::partial_cmp(this, other.as_bytes()) } } }; } #[doc(hidden)] #[unstable(feature = "bstr_internals", issue = "none")] pub use impl_partial_eq_ord; #[doc(hidden)] #[macro_export] #[unstable(feature = "bstr_internals", issue = "none")] macro_rules! impl_partial_eq_n { ($lhs:ty, $rhs:ty) => { #[allow(unused_lifetimes)] #[unstable(feature = "bstr", issue = "134915")] impl PartialEq<$rhs> for $lhs { #[inline] fn eq(&self, other: &$rhs) -> bool { let other: &[u8] = other.as_ref(); PartialEq::eq(self.as_bytes(), other) } } #[allow(unused_lifetimes)] #[unstable(feature = "bstr", issue = "134915")] impl PartialEq<$lhs> for $rhs { #[inline] fn eq(&self, other: &$lhs) -> bool { let this: &[u8] = self.as_ref(); PartialEq::eq(this, other.as_bytes()) } } }; } #[doc(hidden)] #[unstable(feature = "bstr_internals", issue = "none")] pub use impl_partial_eq_n; // PartialOrd with `[u8]` omitted to avoid inference failures impl_partial_eq!(ByteStr, [u8]); // PartialOrd with `&[u8]` omitted to avoid inference failures impl_partial_eq!(ByteStr, &[u8]); // PartialOrd with `str` omitted to avoid inference failures impl_partial_eq!(ByteStr, str); // PartialOrd with `&str` omitted to avoid inference failures impl_partial_eq!(ByteStr, &str); // PartialOrd with `[u8; N]` omitted to avoid inference failures impl_partial_eq_n!(ByteStr, [u8; N]); // PartialOrd with `[u8; N]` omitted to avoid inference failures impl_partial_eq_n!(ByteStr, &[u8; N]); #[unstable(feature = "bstr", issue = "134915")] impl ops::Index for ByteStr where I: SliceIndex, { type Output = I::Output; #[inline] fn index(&self, index: I) -> &I::Output { index.index(self) } } #[unstable(feature = "bstr", issue = "134915")] impl ops::IndexMut for ByteStr where I: SliceIndex, { #[inline] fn index_mut(&mut self, index: I) -> &mut I::Output { index.index_mut(self) } } #[unstable(feature = "bstr", issue = "134915")] unsafe impl SliceIndex for ops::RangeFull { type Output = ByteStr; #[inline] fn get(self, slice: &ByteStr) -> Option<&Self::Output> { Some(slice) } #[inline] fn get_mut(self, slice: &mut ByteStr) -> Option<&mut Self::Output> { Some(slice) } #[inline] unsafe fn get_unchecked(self, slice: *const ByteStr) -> *const Self::Output { slice } #[inline] unsafe fn get_unchecked_mut(self, slice: *mut ByteStr) -> *mut Self::Output { slice } #[inline] fn index(self, slice: &ByteStr) -> &Self::Output { slice } #[inline] fn index_mut(self, slice: &mut ByteStr) -> &mut Self::Output { slice } } #[unstable(feature = "bstr", issue = "134915")] unsafe impl SliceIndex for usize { type Output = u8; #[inline] fn get(self, slice: &ByteStr) -> Option<&Self::Output> { self.get(slice.as_bytes()) } #[inline] fn get_mut(self, slice: &mut ByteStr) -> Option<&mut Self::Output> { self.get_mut(slice.as_bytes_mut()) } #[inline] unsafe fn get_unchecked(self, slice: *const ByteStr) -> *const Self::Output { // SAFETY: the caller has to uphold the safety contract for `get_unchecked`. unsafe { self.get_unchecked(slice as *const [u8]) } } #[inline] unsafe fn get_unchecked_mut(self, slice: *mut ByteStr) -> *mut Self::Output { // SAFETY: the caller has to uphold the safety contract for `get_unchecked_mut`. unsafe { self.get_unchecked_mut(slice as *mut [u8]) } } #[inline] fn index(self, slice: &ByteStr) -> &Self::Output { self.index(slice.as_bytes()) } #[inline] fn index_mut(self, slice: &mut ByteStr) -> &mut Self::Output { self.index_mut(slice.as_bytes_mut()) } } macro_rules! impl_slice_index { ($index:ty) => { #[unstable(feature = "bstr", issue = "134915")] unsafe impl SliceIndex for $index { type Output = ByteStr; #[inline] fn get(self, slice: &ByteStr) -> Option<&Self::Output> { self.get(slice.as_bytes()).map(ByteStr::from_bytes) } #[inline] fn get_mut(self, slice: &mut ByteStr) -> Option<&mut Self::Output> { self.get_mut(slice.as_bytes_mut()).map(ByteStr::from_bytes_mut) } #[inline] unsafe fn get_unchecked(self, slice: *const ByteStr) -> *const Self::Output { // SAFETY: the caller has to uphold the safety contract for `get_unchecked`. unsafe { self.get_unchecked(slice as *const [u8]) as *const ByteStr } } #[inline] unsafe fn get_unchecked_mut(self, slice: *mut ByteStr) -> *mut Self::Output { // SAFETY: the caller has to uphold the safety contract for `get_unchecked_mut`. unsafe { self.get_unchecked_mut(slice as *mut [u8]) as *mut ByteStr } } #[inline] fn index(self, slice: &ByteStr) -> &Self::Output { ByteStr::from_bytes(self.index(slice.as_bytes())) } #[inline] fn index_mut(self, slice: &mut ByteStr) -> &mut Self::Output { ByteStr::from_bytes_mut(self.index_mut(slice.as_bytes_mut())) } } }; } impl_slice_index!(ops::IndexRange); impl_slice_index!(ops::Range); impl_slice_index!(range::Range); impl_slice_index!(ops::RangeTo); impl_slice_index!(ops::RangeFrom); impl_slice_index!(range::RangeFrom); impl_slice_index!(ops::RangeInclusive); impl_slice_index!(range::RangeInclusive); impl_slice_index!(ops::RangeToInclusive); impl_slice_index!((ops::Bound, ops::Bound));