diff options
Diffstat (limited to 'vendor/gimli/src/read/endian_slice.rs')
-rw-r--r-- | vendor/gimli/src/read/endian_slice.rs | 360 |
1 files changed, 0 insertions, 360 deletions
diff --git a/vendor/gimli/src/read/endian_slice.rs b/vendor/gimli/src/read/endian_slice.rs deleted file mode 100644 index 0db28da..0000000 --- a/vendor/gimli/src/read/endian_slice.rs +++ /dev/null @@ -1,360 +0,0 @@ -//! Working with byte slices that have an associated endianity. - -#[cfg(feature = "read")] -use alloc::borrow::Cow; -#[cfg(feature = "read")] -use alloc::string::String; -use core::fmt; -use core::ops::{Deref, Range, RangeFrom, RangeTo}; -use core::str; - -use crate::endianity::Endianity; -use crate::read::{Error, Reader, ReaderOffsetId, Result}; - -/// A `&[u8]` slice with endianity metadata. -/// -/// This implements the `Reader` trait, which is used for all reading of DWARF sections. -#[derive(Default, Clone, Copy, PartialEq, Eq, Hash)] -pub struct EndianSlice<'input, Endian> -where - Endian: Endianity, -{ - slice: &'input [u8], - endian: Endian, -} - -impl<'input, Endian> EndianSlice<'input, Endian> -where - Endian: Endianity, -{ - /// Construct a new `EndianSlice` with the given slice and endianity. - #[inline] - pub fn new(slice: &'input [u8], endian: Endian) -> EndianSlice<'input, Endian> { - EndianSlice { slice, endian } - } - - /// Return a reference to the raw slice. - #[inline] - #[doc(hidden)] - #[deprecated(note = "Method renamed to EndianSlice::slice; use that instead.")] - pub fn buf(&self) -> &'input [u8] { - self.slice - } - - /// Return a reference to the raw slice. - #[inline] - pub fn slice(&self) -> &'input [u8] { - self.slice - } - - /// Split the slice in two at the given index, resulting in the tuple where - /// the first item has range [0, idx), and the second has range [idx, - /// len). Panics if the index is out of bounds. - #[inline] - pub fn split_at( - &self, - idx: usize, - ) -> (EndianSlice<'input, Endian>, EndianSlice<'input, Endian>) { - (self.range_to(..idx), self.range_from(idx..)) - } - - /// Find the first occurrence of a byte in the slice, and return its index. - #[inline] - pub fn find(&self, byte: u8) -> Option<usize> { - self.slice.iter().position(|ch| *ch == byte) - } - - /// Return the offset of the start of the slice relative to the start - /// of the given slice. - #[inline] - pub fn offset_from(&self, base: EndianSlice<'input, Endian>) -> usize { - let base_ptr = base.slice.as_ptr() as *const u8 as usize; - let ptr = self.slice.as_ptr() as *const u8 as usize; - debug_assert!(base_ptr <= ptr); - debug_assert!(ptr + self.slice.len() <= base_ptr + base.slice.len()); - ptr - base_ptr - } - - /// Converts the slice to a string using `str::from_utf8`. - /// - /// Returns an error if the slice contains invalid characters. - #[inline] - pub fn to_string(&self) -> Result<&'input str> { - str::from_utf8(self.slice).map_err(|_| Error::BadUtf8) - } - - /// Converts the slice to a string, including invalid characters, - /// using `String::from_utf8_lossy`. - #[cfg(feature = "read")] - #[inline] - pub fn to_string_lossy(&self) -> Cow<'input, str> { - String::from_utf8_lossy(self.slice) - } - - #[inline] - fn read_slice(&mut self, len: usize) -> Result<&'input [u8]> { - if self.slice.len() < len { - Err(Error::UnexpectedEof(self.offset_id())) - } else { - let val = &self.slice[..len]; - self.slice = &self.slice[len..]; - Ok(val) - } - } -} - -/// # Range Methods -/// -/// Unfortunately, `std::ops::Index` *must* return a reference, so we can't -/// implement `Index<Range<usize>>` to return a new `EndianSlice` the way we would -/// like to. Instead, we abandon fancy indexing operators and have these plain -/// old methods. -impl<'input, Endian> EndianSlice<'input, Endian> -where - Endian: Endianity, -{ - /// Take the given `start..end` range of the underlying slice and return a - /// new `EndianSlice`. - /// - /// ``` - /// use gimli::{EndianSlice, LittleEndian}; - /// - /// let slice = &[0x01, 0x02, 0x03, 0x04]; - /// let endian_slice = EndianSlice::new(slice, LittleEndian); - /// assert_eq!(endian_slice.range(1..3), - /// EndianSlice::new(&slice[1..3], LittleEndian)); - /// ``` - pub fn range(&self, idx: Range<usize>) -> EndianSlice<'input, Endian> { - EndianSlice { - slice: &self.slice[idx], - endian: self.endian, - } - } - - /// Take the given `start..` range of the underlying slice and return a new - /// `EndianSlice`. - /// - /// ``` - /// use gimli::{EndianSlice, LittleEndian}; - /// - /// let slice = &[0x01, 0x02, 0x03, 0x04]; - /// let endian_slice = EndianSlice::new(slice, LittleEndian); - /// assert_eq!(endian_slice.range_from(2..), - /// EndianSlice::new(&slice[2..], LittleEndian)); - /// ``` - pub fn range_from(&self, idx: RangeFrom<usize>) -> EndianSlice<'input, Endian> { - EndianSlice { - slice: &self.slice[idx], - endian: self.endian, - } - } - - /// Take the given `..end` range of the underlying slice and return a new - /// `EndianSlice`. - /// - /// ``` - /// use gimli::{EndianSlice, LittleEndian}; - /// - /// let slice = &[0x01, 0x02, 0x03, 0x04]; - /// let endian_slice = EndianSlice::new(slice, LittleEndian); - /// assert_eq!(endian_slice.range_to(..3), - /// EndianSlice::new(&slice[..3], LittleEndian)); - /// ``` - pub fn range_to(&self, idx: RangeTo<usize>) -> EndianSlice<'input, Endian> { - EndianSlice { - slice: &self.slice[idx], - endian: self.endian, - } - } -} - -impl<'input, Endian> Deref for EndianSlice<'input, Endian> -where - Endian: Endianity, -{ - type Target = [u8]; - fn deref(&self) -> &Self::Target { - self.slice - } -} - -impl<'input, Endian: Endianity> fmt::Debug for EndianSlice<'input, Endian> { - fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> core::result::Result<(), fmt::Error> { - fmt.debug_tuple("EndianSlice") - .field(&self.endian) - .field(&DebugBytes(self.slice)) - .finish() - } -} - -struct DebugBytes<'input>(&'input [u8]); - -impl<'input> core::fmt::Debug for DebugBytes<'input> { - fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> core::result::Result<(), fmt::Error> { - let mut list = fmt.debug_list(); - list.entries(self.0.iter().take(8).copied().map(DebugByte)); - if self.0.len() > 8 { - list.entry(&DebugLen(self.0.len())); - } - list.finish() - } -} - -struct DebugByte(u8); - -impl fmt::Debug for DebugByte { - fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { - write!(fmt, "0x{:02x}", self.0) - } -} - -struct DebugLen(usize); - -impl fmt::Debug for DebugLen { - fn fmt(&self, fmt: &mut fmt::Formatter<'_>) -> fmt::Result { - write!(fmt, "...; {}", self.0) - } -} - -impl<'input, Endian> Reader for EndianSlice<'input, Endian> -where - Endian: Endianity, -{ - type Endian = Endian; - type Offset = usize; - - #[inline] - fn endian(&self) -> Endian { - self.endian - } - - #[inline] - fn len(&self) -> usize { - self.slice.len() - } - - #[inline] - fn is_empty(&self) -> bool { - self.slice.is_empty() - } - - #[inline] - fn empty(&mut self) { - self.slice = &[]; - } - - #[inline] - fn truncate(&mut self, len: usize) -> Result<()> { - if self.slice.len() < len { - Err(Error::UnexpectedEof(self.offset_id())) - } else { - self.slice = &self.slice[..len]; - Ok(()) - } - } - - #[inline] - fn offset_from(&self, base: &Self) -> usize { - self.offset_from(*base) - } - - #[inline] - fn offset_id(&self) -> ReaderOffsetId { - ReaderOffsetId(self.slice.as_ptr() as u64) - } - - #[inline] - fn lookup_offset_id(&self, id: ReaderOffsetId) -> Option<Self::Offset> { - let id = id.0; - let self_id = self.slice.as_ptr() as u64; - let self_len = self.slice.len() as u64; - if id >= self_id && id <= self_id + self_len { - Some((id - self_id) as usize) - } else { - None - } - } - - #[inline] - fn find(&self, byte: u8) -> Result<usize> { - self.find(byte) - .ok_or_else(|| Error::UnexpectedEof(self.offset_id())) - } - - #[inline] - fn skip(&mut self, len: usize) -> Result<()> { - if self.slice.len() < len { - Err(Error::UnexpectedEof(self.offset_id())) - } else { - self.slice = &self.slice[len..]; - Ok(()) - } - } - - #[inline] - fn split(&mut self, len: usize) -> Result<Self> { - let slice = self.read_slice(len)?; - Ok(EndianSlice::new(slice, self.endian)) - } - - #[cfg(not(feature = "read"))] - fn cannot_implement() -> super::reader::seal_if_no_alloc::Sealed { - super::reader::seal_if_no_alloc::Sealed - } - - #[cfg(feature = "read")] - #[inline] - fn to_slice(&self) -> Result<Cow<[u8]>> { - Ok(self.slice.into()) - } - - #[cfg(feature = "read")] - #[inline] - fn to_string(&self) -> Result<Cow<str>> { - match str::from_utf8(self.slice) { - Ok(s) => Ok(s.into()), - _ => Err(Error::BadUtf8), - } - } - - #[cfg(feature = "read")] - #[inline] - fn to_string_lossy(&self) -> Result<Cow<str>> { - Ok(String::from_utf8_lossy(self.slice)) - } - - #[inline] - fn read_slice(&mut self, buf: &mut [u8]) -> Result<()> { - let slice = self.read_slice(buf.len())?; - buf.copy_from_slice(slice); - Ok(()) - } -} - -#[cfg(test)] -mod tests { - use super::*; - use crate::endianity::NativeEndian; - - #[test] - fn test_endian_slice_split_at() { - let endian = NativeEndian; - let slice = &[1, 2, 3, 4, 5, 6, 7, 8, 9, 0]; - let eb = EndianSlice::new(slice, endian); - assert_eq!( - eb.split_at(3), - ( - EndianSlice::new(&slice[..3], endian), - EndianSlice::new(&slice[3..], endian) - ) - ); - } - - #[test] - #[should_panic] - fn test_endian_slice_split_at_out_of_bounds() { - let slice = &[1, 2, 3, 4, 5, 6, 7, 8, 9, 0]; - let eb = EndianSlice::new(slice, NativeEndian); - eb.split_at(30); - } -} |