hao/io/
peimage.rs

1use crate::error::{HaoError, Result};
2use crate::io::DataReader;
3
4use pewter::pe::optional_header::OptionalHeader;
5use pewter::pe::sections::cor20::ImageCor20Header;
6use pewter::pe::sections::{SectionRow};
7use pewter::PEFile;
8
9pub struct PEImage<'a> {
10    pub pe: PEFile<'a>,
11}
12
13impl<'a> PEImage<'a> {
14    pub fn load_bytes(data: &'a [u8]) -> Result<Self> {
15        let pe = PEFile::parse(data).map_err(|_| HaoError::BadPeFormat)?;
16
17        Ok(Self { pe })
18    }
19
20    pub fn optional_header(&self) -> Result<&OptionalHeader> {
21        self.pe.optional_header.as_ref().ok_or(HaoError::BadPeFormat)
22    }
23
24    pub fn rva_to_section(&self, rva: u32) -> Option<&SectionRow> {
25        self.pe.sections.find_rva(rva as usize)
26    }
27
28    pub fn rva_to_file_offset_(&self, _rva: u32) -> Result<usize> {
29        todo!()
30    }
31
32    pub fn create_reader(&self, rva: u32, size: Option<usize>) -> Result<DataReader<'a>> {
33        let data = self
34            .pe
35            .sections
36            .find_rva_data(rva as usize)
37            .ok_or_else(|| HaoError::BadRva(rva))?;
38
39        let data = if let Some(size) = size {
40            &data[..size]
41        } else {
42            data
43        };
44
45        Ok(DataReader::new(data))
46    }
47
48    pub fn read_clr_rt_header(&self) -> Result<ImageCor20Header> {
49        let clr = self
50            .pe
51            .read_clr_runtime_header()
52            .map_err(|_| HaoError::BadImageFormat("Failed to read image cor20 header"))?;
53
54        let header = clr.ok_or(HaoError::NotDotNetBinary)?;
55
56        Ok(header)
57    }
58}