//file format "sniff" use binrw::{binrw, BinReaderExt}; pub enum Error{ InvalidHeader(binrw::Error), UnexpectedEOF, } /* spec //begin global header //global metadata (32 bytes) b"SNFB" u32 format_version u64 priming_bytes //how many bytes of the file must be read to guarantee all of the expected //format-specific metadata is available to facilitate streaming the remaining contents //used by the database to guarantee that it serves at least the bare minimum u128 resource_uuid //identifies the file from anywhere for any other file //global block layout (variable size) u64 num_blocks for block_id in 0..num_blocks{ u64 first_byte } //end global header //begin blocks //each block is compressed with zstd or gz or something */ #[binrw] #[brw(little)] #[derive(Clone,Copy)] pub(crate) enum FourCC{ #[brw(magic=b"SNFM")] Map, #[brw(magic=b"SNFB")] Bot, #[brw(magic=b"SNFD")] Demo, } #[binrw] #[brw(little)] struct Header{ /// Type of file fourcc:FourCC, /// Type version version:u32, /// Minimum data required to know the location of all streamable resources for this specific file priming:u64, /// uuid for this file resource:u128, #[bw(try_calc(u64::try_from(block_location.len())))] block_count:u64, #[br(count=block_count)] block_location:Vec, } pub(crate) struct File{ header:Header, //reference to the data } impl File{ pub(crate) fn new(mut input:R)->Result{ Ok(Self{ header:input.read_le().map_err(|e|Error::InvalidHeader(e))?, }) } pub(crate) fn read_block(&mut self,block_id:u64)->Result,Error>{ Err(Error::UnexpectedEOF) } pub(crate) fn fourcc(&self)->FourCC{ self.header.fourcc } }