squashfs_async/inodes/
directory.rs1use serde::Deserialize;
2
3use super::super::deser::{self, from_reader};
4use super::super::error::InodeTableError;
5
6#[derive(Default, Debug, Clone)]
8pub struct DirectoryTableLocation {
9 pub start: u64,
10 pub offset: u64,
11 pub file_size: u64,
12}
13pub trait DirectoryInode: std::fmt::Debug {
15 fn hard_link_count(&self) -> u32;
16 fn parent_inode_number(&self) -> u32;
17 fn table_location(&self) -> DirectoryTableLocation;
18}
19#[derive(Debug, Default, Deserialize)]
20pub struct BasicDirectory {
21 dir_block_start: u32,
22 hard_link_count: u32,
23 file_size: u16,
24 block_offset: u16,
25 parent_inode_number: u32,
26}
27from_reader!(BasicDirectory, 16);
28impl DirectoryInode for BasicDirectory {
29 fn hard_link_count(&self) -> u32 {
30 self.hard_link_count
31 }
32 fn parent_inode_number(&self) -> u32 {
33 self.parent_inode_number
34 }
35 fn table_location(&self) -> DirectoryTableLocation {
36 DirectoryTableLocation {
37 start: self.dir_block_start as u64,
38 offset: self.block_offset as u64,
39 file_size: self.file_size as u64,
40 }
41 }
42}
43
44#[derive(Debug, Default, Deserialize)]
45struct DirectoryIndex {
46 _index: u32,
47 _start: u32,
48 name_size: u32,
49 #[serde(skip)]
50 name: String,
51}
52impl DirectoryIndex {
53 pub async fn from_reader(mut r: impl crate::AsyncRead) -> Result<Self, InodeTableError> {
54 let mut index: Self = deser::bincode_deser_from(&mut r, 12)
55 .await
56 .map_err(|_| InodeTableError::InvalidEntry)?;
57 index.name = deser::bincode_deser_string_from(r, index.name_size as usize + 1)
58 .await
59 .map_err(|_| InodeTableError::InvalidEntry)?;
60 Ok(index)
61 }
62}
63
64#[derive(Debug, Default, Deserialize)]
65pub struct ExtendedDirectory {
66 hard_link_count: u32,
67 file_size: u32,
68 dir_block_start: u32,
69 parent_inode_number: u32,
70 index_count: u16,
71 block_offset: u16,
72 _xattr_idx: u32,
73 #[serde(skip)]
74 index: Vec<DirectoryIndex>,
75}
76impl DirectoryInode for ExtendedDirectory {
77 fn hard_link_count(&self) -> u32 {
78 self.hard_link_count
79 }
80 fn parent_inode_number(&self) -> u32 {
81 self.parent_inode_number
82 }
83 fn table_location(&self) -> DirectoryTableLocation {
84 DirectoryTableLocation {
85 start: self.dir_block_start as u64,
86 offset: self.block_offset as u64,
87 file_size: self.file_size as u64,
88 }
89 }
90}
91impl ExtendedDirectory {
92 pub async fn from_reader(mut r: impl crate::AsyncRead) -> Result<Self, InodeTableError> {
93 let mut dir: Self = deser::bincode_deser_from(&mut r, 24)
94 .await
95 .map_err(|_| InodeTableError::InvalidEntry)?;
96 for _ in 0..dir.index_count {
97 dir.index.push(DirectoryIndex::from_reader(&mut r).await?);
98 }
99 Ok(dir)
100 }
101}