[][src]Struct gimli::read::EndianReader

pub struct EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
{ /* fields omitted */ }

An easy way to define a custom Reader implementation with a reference to a generic buffer of bytes and an associated endianity.

Note that the whole original buffer is kept alive in memory even if there is only one reader that references only a handful of bytes from that original buffer. That is, EndianReader will not do any copying, moving, or compacting in order to free up unused regions of the original buffer. If you require this kind of behavior, it is up to you to implement Reader directly by-hand.

Example

Say you have an mmaped file that you want to serve as a gimli::Reader. You can wrap that mmaped file up in a MmapFile type and use EndianReader<Rc<MmapFile>> or EndianReader<Arc<MmapFile>> as readers as long as MmapFile dereferences to the underlying [u8] data.

use std::io;
use std::ops::Deref;
use std::path::Path;
use std::slice;
use std::sync::Arc;

/// A type that represents an `mmap`ed file.
#[derive(Debug)]
pub struct MmapFile {
    ptr: *const u8,
    len: usize,
}

impl MmapFile {
    pub fn new(path: &Path) -> io::Result<MmapFile> {
        // Call `mmap` and check for errors and all that...
    }
}

impl Drop for MmapFile {
    fn drop(&mut self) {
        // Call `munmap` to clean up after ourselves...
    }
}

// And `MmapFile` can deref to a slice of the `mmap`ed region of memory.
impl Deref for MmapFile {
    type Target = [u8];
    fn deref(&self) -> &[u8] {
        unsafe {
            slice::from_raw_parts(self.ptr, self.len)
        }
    }
}

/// A type that represents a shared `mmap`ed file.
#[derive(Debug, Clone)]
pub struct ArcMmapFile(Arc<MmapFile>);

// And `ArcMmapFile` can deref to a slice of the `mmap`ed region of memory.
impl Deref for ArcMmapFile {
    type Target = [u8];
    fn deref(&self) -> &[u8] {
        &self.0
    }
}

// These are both valid for any `Rc` or `Arc`.
unsafe impl gimli::StableDeref for ArcMmapFile {}
unsafe impl gimli::CloneStableDeref for ArcMmapFile {}

/// A `gimli::Reader` that is backed by an `mmap`ed file!
pub type MmapFileReader<Endian> = gimli::EndianReader<Endian, ArcMmapFile>;

Implementations

impl<Endian, T> EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

pub fn new(bytes: T, endian: Endian) -> EndianReader<Endian, T>[src]

Construct a new EndianReader with the given bytes.

pub fn bytes(&self) -> &[u8][src]

Return a reference to the raw bytes underlying this reader.

impl<Endian, T> EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

Range Methods

Unfortunately, std::ops::Index must return a reference, so we can't implement Index<Range<usize>> to return a new EndianReader the way we would like to. Instead, we abandon fancy indexing operators and have these plain old methods.

pub fn range(&self, idx: Range<usize>) -> EndianReader<Endian, T>[src]

Take the given start..end range of the underlying buffer and return a new EndianReader.

use gimli::{EndianReader, LittleEndian};
use std::sync::Arc;

let buf = Arc::<[u8]>::from(&[0x01, 0x02, 0x03, 0x04][..]);
let reader = EndianReader::new(buf.clone(), LittleEndian);
assert_eq!(reader.range(1..3),
           EndianReader::new(&buf[1..3], LittleEndian));

Panics

Panics if the range is out of bounds.

pub fn range_from(&self, idx: RangeFrom<usize>) -> EndianReader<Endian, T>[src]

Take the given start.. range of the underlying buffer and return a new EndianReader.

use gimli::{EndianReader, LittleEndian};
use std::sync::Arc;

let buf = Arc::<[u8]>::from(&[0x01, 0x02, 0x03, 0x04][..]);
let reader = EndianReader::new(buf.clone(), LittleEndian);
assert_eq!(reader.range_from(2..),
           EndianReader::new(&buf[2..], LittleEndian));

Panics

Panics if the range is out of bounds.

pub fn range_to(&self, idx: RangeTo<usize>) -> EndianReader<Endian, T>[src]

Take the given ..end range of the underlying buffer and return a new EndianReader.

use gimli::{EndianReader, LittleEndian};
use std::sync::Arc;

let buf = Arc::<[u8]>::from(&[0x01, 0x02, 0x03, 0x04][..]);
let reader = EndianReader::new(buf.clone(), LittleEndian);
assert_eq!(reader.range_to(..3),
           EndianReader::new(&buf[..3], LittleEndian));

Panics

Panics if the range is out of bounds.

Trait Implementations

impl<Endian: Clone, T: Clone> Clone for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

impl<Endian: Copy, T: Copy> Copy for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

impl<Endian: Debug, T: Debug> Debug for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

impl<Endian, T> Deref for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

type Target = [u8]

The resulting type after dereferencing.

impl<Endian, T> Eq for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

impl<Endian: Hash, T: Hash> Hash for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

impl<Endian, T> Index<RangeFrom<usize>> for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

type Output = [u8]

The returned type after indexing.

impl<Endian, T> Index<usize> for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

type Output = u8

The returned type after indexing.

impl<Endian, T1, T2> PartialEq<EndianReader<Endian, T2>> for EndianReader<Endian, T1> where
    Endian: Endianity,
    T1: CloneStableDeref<Target = [u8]> + Debug,
    T2: CloneStableDeref<Target = [u8]> + Debug
[src]

impl<Endian, T> Reader for EndianReader<Endian, T> where
    Endian: Endianity,
    T: CloneStableDeref<Target = [u8]> + Debug
[src]

type Endian = Endian

The endianity of bytes that are read.

type Offset = usize

The type used for offsets and lengths.

Auto Trait Implementations

impl<Endian, T> RefUnwindSafe for EndianReader<Endian, T> where
    Endian: RefUnwindSafe,
    T: RefUnwindSafe

impl<Endian, T> Send for EndianReader<Endian, T> where
    Endian: Send,
    T: Send

impl<Endian, T> Sync for EndianReader<Endian, T> where
    Endian: Sync,
    T: Sync

impl<Endian, T> Unpin for EndianReader<Endian, T> where
    Endian: Unpin,
    T: Unpin

impl<Endian, T> UnwindSafe for EndianReader<Endian, T> where
    Endian: UnwindSafe,
    T: UnwindSafe

Blanket Implementations

impl<T> Any for T where
    T: 'static + ?Sized
[src]

impl<T> Borrow<T> for T where
    T: ?Sized
[src]

impl<T> BorrowMut<T> for T where
    T: ?Sized
[src]

impl<Q, K> Equivalent<K> for Q where
    K: Borrow<Q> + ?Sized,
    Q: Eq + ?Sized
[src]

impl<T> From<T> for T[src]

impl<T, U> Into<U> for T where
    U: From<T>, 
[src]

impl<T> ToOwned for T where
    T: Clone
[src]

type Owned = T

The resulting type after obtaining ownership.

impl<T, U> TryFrom<U> for T where
    U: Into<T>, 
[src]

type Error = Infallible

The type returned in the event of a conversion error.

impl<T, U> TryInto<U> for T where
    U: TryFrom<T>, 
[src]

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.