//! Map file entry type. use crate::err::*; use super::head; use std::collections::BTreeMap; /// Read an entry from a Map file. pub fn read(map: &head::Map, i: usize) -> ResultS<(u16, Entry<'_>)> { let size = map.head().size_entry(); let b = map.dir(); let sta = size * i; read_data! { endian: BIG, buf: b, size: size, start: sta, data { let offset = u32[0] usize; let dsize = u32[4] usize; } } let (index, app_data) = if !map.head().old_wad() { read_data! { endian: BIG, buf: b, size: size, start: sta, data { let index = u16[8]; let app_data = u8[10; map.head().size_appl()]; } } (index, app_data) } else { (i as u16, &b[0..0]) }; let data = &map.data()[offset..offset + dsize]; Ok((index, Entry{data, app_data})) } /// Reads all entries in a Map file. pub fn read_all(map: &head::Map) -> ResultS> { let mut entries = EntryMap::new(); for i in 0..map.num_ent() { let (index, entry) = read(map, i)?; if entries.contains_key(&index) { bail!("entry index already exists"); } entries.insert(index, entry); } Ok(entries) } /// An entry containing chunked data and application-specific data. #[cfg_attr(feature = "serde_obj", derive(serde::Serialize))] #[derive(Debug, Eq, PartialEq)] pub struct Entry<'a> { /// The data in this `Entry`. pub data: &'a [u8], /// The application specific data for this Entry. pub app_data: &'a [u8], } /// A map of indexed entries. pub type EntryMap<'a> = BTreeMap>; // EOF