xref: /DragonOS/kernel/src/filesystem/fat/fs.rs (revision 2286eda6526ed1b46afd79b47dc701034b9e903d)
1 #![allow(dead_code)]
2 use core::{any::Any, fmt::Debug};
3 
4 use alloc::{
5     collections::BTreeMap,
6     string::String,
7     sync::{Arc, Weak},
8     vec::Vec,
9 };
10 
11 use crate::{
12     filesystem::vfs::{
13         core::generate_inode_id,
14         file::{FileMode, FilePrivateData},
15         FileSystem, FileType, IndexNode, InodeId, Metadata, PollStatus,
16     },
17     include::bindings::bindings::{
18         EFAULT, EINVAL, EISDIR, ENOENT, ENOSPC, ENOTDIR, ENOTEMPTY, ENOTSUP, EPERM, EROFS,
19     },
20     io::{device::LBA_SIZE, disk_info::Partition, SeekFrom},
21     kerror,
22     libs::{
23         spinlock::{SpinLock, SpinLockGuard},
24         vec_cursor::VecCursor,
25     },
26     time::TimeSpec,
27 };
28 
29 use super::{
30     bpb::{BiosParameterBlock, FATType},
31     entry::{FATDir, FATDirEntry, FATDirIter, FATEntry},
32     utils::RESERVED_CLUSTERS,
33 };
34 
35 /// FAT32文件系统的最大的文件大小
36 pub const MAX_FILE_SIZE: u64 = 0xffff_ffff;
37 
38 /// @brief 表示当前簇和上一个簇的关系的结构体
39 /// 定义这样一个结构体的原因是,FAT文件系统的文件中,前后两个簇具有关联关系。
40 #[derive(Debug, Clone, Copy, Default)]
41 pub struct Cluster {
42     pub cluster_num: u64,
43     pub parent_cluster: u64,
44 }
45 
46 impl PartialOrd for Cluster {
47     /// @brief 根据当前簇号比较大小
48     fn partial_cmp(&self, other: &Self) -> Option<core::cmp::Ordering> {
49         return self.cluster_num.partial_cmp(&other.cluster_num);
50     }
51 }
52 
53 impl PartialEq for Cluster {
54     /// @brief 根据当前簇号比较是否相等
55     fn eq(&self, other: &Self) -> bool {
56         self.cluster_num == other.cluster_num
57     }
58 }
59 
60 impl Eq for Cluster {}
61 
62 #[derive(Debug)]
63 pub struct FATFileSystem {
64     /// 当前文件系统所在的分区
65     pub partition: Arc<Partition>,
66     /// 当前文件系统的BOPB
67     pub bpb: BiosParameterBlock,
68     /// 当前文件系统的第一个数据扇区(相对分区开始位置)
69     pub first_data_sector: u64,
70     /// 文件系统信息结构体
71     pub fs_info: Arc<LockedFATFsInfo>,
72     /// 文件系统的根inode
73     root_inode: Arc<LockedFATInode>,
74 }
75 
76 /// FAT文件系统的Inode
77 #[derive(Debug)]
78 pub struct LockedFATInode(SpinLock<FATInode>);
79 
80 #[derive(Debug)]
81 pub struct LockedFATFsInfo(SpinLock<FATFsInfo>);
82 
83 impl LockedFATFsInfo {
84     #[inline]
85     pub fn new(fs_info: FATFsInfo) -> Self {
86         return Self(SpinLock::new(fs_info));
87     }
88 }
89 
90 #[derive(Debug)]
91 pub struct FATInode {
92     /// 指向父Inode的弱引用
93     parent: Weak<LockedFATInode>,
94     /// 指向自身的弱引用
95     self_ref: Weak<LockedFATInode>,
96     /// 子Inode的B树. 该数据结构用作缓存区。其中,它的key表示inode的名称。
97     /// 请注意,由于FAT的查询过程对大小写不敏感,因此我们选择让key全部是大写的,方便统一操作。
98     children: BTreeMap<String, Arc<LockedFATInode>>,
99     /// 当前inode的元数据
100     metadata: Metadata,
101     /// 指向inode所在的文件系统对象的指针
102     fs: Weak<FATFileSystem>,
103 
104     /// 根据不同的Inode类型,创建不同的私有字段
105     inode_type: FATDirEntry,
106 }
107 
108 impl FATInode {
109     /// @brief 更新当前inode的元数据
110     pub fn update_metadata(&mut self) {
111         // todo: 更新文件的访问时间等信息
112         match &self.inode_type {
113             FATDirEntry::File(f) | FATDirEntry::VolId(f) => {
114                 self.metadata.size = f.size() as i64;
115             }
116             FATDirEntry::Dir(d) => {
117                 self.metadata.size = d.size(&self.fs.upgrade().unwrap().clone()) as i64;
118             }
119             FATDirEntry::UnInit => {
120                 kerror!("update_metadata: Uninitialized FATDirEntry: {:?}", self);
121                 return;
122             }
123         };
124     }
125 
126     fn find(&mut self, name: &str) -> Result<Arc<LockedFATInode>, i32> {
127         match &self.inode_type {
128             FATDirEntry::Dir(d) => {
129                 // 尝试在缓存区查找
130                 if let Some(entry) = self.children.get(&name.to_uppercase()) {
131                     return Ok(entry.clone());
132                 }
133                 // 在缓存区找不到
134                 // 在磁盘查找
135                 let fat_entry: FATDirEntry =
136                     d.find_entry(name, None, None, self.fs.upgrade().unwrap())?;
137                 // kdebug!("find entry from disk ok, entry={fat_entry:?}");
138                 // 创建新的inode
139                 let entry_inode: Arc<LockedFATInode> = LockedFATInode::new(
140                     self.fs.upgrade().unwrap(),
141                     self.self_ref.clone(),
142                     fat_entry,
143                 );
144                 // 加入缓存区, 由于FAT文件系统的大小写不敏感问题,因此存入缓存区的key应当是全大写的
145                 self.children
146                     .insert(name.to_uppercase(), entry_inode.clone());
147                 return Ok(entry_inode);
148             }
149             FATDirEntry::UnInit => {
150                 panic!(
151                     "Uninitialized FAT Inode, fs = {:?}, inode={self:?}",
152                     self.fs
153                 )
154             }
155             _ => {
156                 return Err(-(ENOTDIR as i32));
157             }
158         }
159     }
160 }
161 
162 impl LockedFATInode {
163     pub fn new(
164         fs: Arc<FATFileSystem>,
165         parent: Weak<LockedFATInode>,
166         inode_type: FATDirEntry,
167     ) -> Arc<LockedFATInode> {
168         let file_type = if let FATDirEntry::Dir(_) = inode_type {
169             FileType::Dir
170         } else {
171             FileType::File
172         };
173 
174         let inode: Arc<LockedFATInode> = Arc::new(LockedFATInode(SpinLock::new(FATInode {
175             parent: parent,
176             self_ref: Weak::default(),
177             children: BTreeMap::new(),
178             fs: Arc::downgrade(&fs),
179             inode_type: inode_type,
180             metadata: Metadata {
181                 dev_id: 0,
182                 inode_id: generate_inode_id(),
183                 size: 0,
184                 blk_size: fs.bpb.bytes_per_sector as usize,
185                 blocks: if let FATType::FAT32(_) = fs.bpb.fat_type {
186                     fs.bpb.total_sectors_32 as usize
187                 } else {
188                     fs.bpb.total_sectors_16 as usize
189                 },
190                 atime: TimeSpec::default(),
191                 mtime: TimeSpec::default(),
192                 ctime: TimeSpec::default(),
193                 file_type: file_type,
194                 mode: 0o777,
195                 nlinks: 1,
196                 uid: 0,
197                 gid: 0,
198                 raw_dev: 0,
199             },
200         })));
201 
202         inode.0.lock().self_ref = Arc::downgrade(&inode);
203 
204         inode.0.lock().update_metadata();
205 
206         return inode;
207     }
208 }
209 
210 /// FsInfo结构体(内存中的一份拷贝,当卸载卷或者sync的时候,把它写入磁盘)
211 #[derive(Debug)]
212 pub struct FATFsInfo {
213     /// Lead Signature - must equal 0x41615252
214     lead_sig: u32,
215     /// Value must equal 0x61417272
216     struc_sig: u32,
217     /// 空闲簇数目
218     free_count: u32,
219     /// 第一个空闲簇的位置(不一定准确,仅供加速查找)
220     next_free: u32,
221     /// 0xAA550000
222     trail_sig: u32,
223     /// Dirty flag to flush to disk
224     dirty: bool,
225     /// FsInfo Structure 在磁盘上的字节偏移量
226     /// Not present for FAT12 and FAT16
227     offset: Option<u64>,
228 }
229 
230 impl FileSystem for FATFileSystem {
231     fn root_inode(&self) -> Arc<dyn crate::filesystem::vfs::IndexNode> {
232         return self.root_inode.clone();
233     }
234 
235     fn info(&self) -> crate::filesystem::vfs::FsInfo {
236         todo!()
237     }
238 
239     /// @brief 本函数用于实现动态转换。
240     /// 具体的文件系统在实现本函数时,最简单的方式就是:直接返回self
241     fn as_any_ref(&self) -> &dyn Any {
242         self
243     }
244 }
245 
246 impl FATFileSystem {
247     /// FAT12允许的最大簇号
248     pub const FAT12_MAX_CLUSTER: u32 = 0xFF5;
249     /// FAT16允许的最大簇号
250     pub const FAT16_MAX_CLUSTER: u32 = 0xFFF5;
251     /// FAT32允许的最大簇号
252     pub const FAT32_MAX_CLUSTER: u32 = 0x0FFFFFF7;
253 
254     pub fn new(partition: Arc<Partition>) -> Result<Arc<FATFileSystem>, i32> {
255         let bpb = BiosParameterBlock::new(partition.clone())?;
256 
257         // 从磁盘上读取FAT32文件系统的FsInfo结构体
258         let fs_info: FATFsInfo = match bpb.fat_type {
259             FATType::FAT32(bpb32) => {
260                 let fs_info_in_disk_bytes_offset = partition.lba_start * LBA_SIZE as u64
261                     + bpb32.fs_info as u64 * bpb.bytes_per_sector as u64;
262                 FATFsInfo::new(
263                     partition.clone(),
264                     fs_info_in_disk_bytes_offset,
265                     bpb.bytes_per_sector as usize,
266                 )?
267             }
268             _ => FATFsInfo::default(),
269         };
270 
271         // 根目录项占用的扇区数(向上取整)
272         let root_dir_sectors: u64 = ((bpb.root_entries_cnt as u64 * 32)
273             + (bpb.bytes_per_sector as u64 - 1))
274             / (bpb.bytes_per_sector as u64);
275 
276         // FAT表大小(单位:扇区)
277         let fat_size = if bpb.fat_size_16 != 0 {
278             bpb.fat_size_16 as u64
279         } else {
280             match bpb.fat_type {
281                 FATType::FAT32(x) => x.fat_size_32 as u64,
282                 _ => {
283                     kerror!("FAT12 and FAT16 volumes should have non-zero BPB_FATSz16");
284                     return Err(-(EINVAL as i32));
285                 }
286             }
287         };
288 
289         let first_data_sector =
290             bpb.rsvd_sec_cnt as u64 + (bpb.num_fats as u64 * fat_size) + root_dir_sectors;
291 
292         // 创建文件系统的根节点
293         let root_inode: Arc<LockedFATInode> = Arc::new(LockedFATInode(SpinLock::new(FATInode {
294             parent: Weak::default(),
295             self_ref: Weak::default(),
296             children: BTreeMap::new(),
297             fs: Weak::default(),
298             inode_type: FATDirEntry::UnInit,
299             metadata: Metadata {
300                 dev_id: 0,
301                 inode_id: generate_inode_id(),
302                 size: 0,
303                 blk_size: bpb.bytes_per_sector as usize,
304                 blocks: if let FATType::FAT32(_) = bpb.fat_type {
305                     bpb.total_sectors_32 as usize
306                 } else {
307                     bpb.total_sectors_16 as usize
308                 },
309                 atime: TimeSpec::default(),
310                 mtime: TimeSpec::default(),
311                 ctime: TimeSpec::default(),
312                 file_type: FileType::Dir,
313                 mode: 0o777,
314                 nlinks: 1,
315                 uid: 0,
316                 gid: 0,
317                 raw_dev: 0,
318             },
319         })));
320 
321         let result: Arc<FATFileSystem> = Arc::new(FATFileSystem {
322             partition: partition,
323             bpb,
324             first_data_sector,
325             fs_info: Arc::new(LockedFATFsInfo::new(fs_info)),
326             root_inode: root_inode,
327         });
328 
329         // 对root inode加锁,并继续完成初始化工作
330         let mut root_guard: SpinLockGuard<FATInode> = result.root_inode.0.lock();
331         root_guard.inode_type = FATDirEntry::Dir(result.root_dir());
332         root_guard.parent = Arc::downgrade(&result.root_inode);
333         root_guard.self_ref = Arc::downgrade(&result.root_inode);
334         root_guard.fs = Arc::downgrade(&result);
335         // 释放锁
336         drop(root_guard);
337 
338         return Ok(result);
339     }
340 
341     /// @brief 计算每个簇有多少个字节
342     #[inline]
343     pub fn bytes_per_cluster(&self) -> u64 {
344         return (self.bpb.bytes_per_sector as u64) * (self.bpb.sector_per_cluster as u64);
345     }
346 
347     /// @brief 读取当前簇在FAT表中存储的信息
348     ///
349     /// @param cluster 当前簇
350     ///
351     /// @return Ok(FATEntry) 当前簇在FAT表中,存储的信息。(详情见FATEntry的注释)
352     /// @return Err(i32) 错误码
353     pub fn get_fat_entry(&self, cluster: Cluster) -> Result<FATEntry, i32> {
354         let current_cluster = cluster.cluster_num;
355 
356         let fat_type: FATType = self.bpb.fat_type;
357         // 获取FAT表的起始扇区(相对分区起始扇区的偏移量)
358         let fat_start_sector = self.fat_start_sector();
359         let bytes_per_sec = self.bpb.bytes_per_sector as u64;
360 
361         // cluster对应的FAT表项在分区内的字节偏移量
362         let fat_bytes_offset =
363             fat_type.get_fat_bytes_offset(cluster, fat_start_sector, bytes_per_sec);
364 
365         // FAT表项所在的LBA地址
366         // let fat_ent_lba = self.get_lba_from_offset(self.bytes_to_sector(fat_bytes_offset));
367         let fat_ent_lba = self.partition.lba_start + fat_bytes_offset / LBA_SIZE as u64;
368 
369         // FAT表项在逻辑块内的字节偏移量
370         let blk_offset = self.get_in_block_offset(fat_bytes_offset);
371 
372         let mut v = Vec::<u8>::new();
373         v.resize(self.bpb.bytes_per_sector as usize, 0);
374         self.partition
375             .disk()
376             .read_at(fat_ent_lba as usize, 1 * self.lba_per_sector(), &mut v)?;
377 
378         let mut cursor = VecCursor::new(v);
379         cursor.seek(SeekFrom::SeekSet(blk_offset as i64))?;
380 
381         let res: FATEntry = match self.bpb.fat_type {
382             FATType::FAT12(_) => {
383                 let mut entry = cursor.read_u16()?;
384                 // 由于FAT12文件系统的FAT表,每个entry占用1.5字节,因此奇数的簇需要取高12位的值。
385                 if (current_cluster & 1) > 0 {
386                     entry >>= 4;
387                 } else {
388                     entry &= 0x0fff;
389                 }
390 
391                 if entry == 0 {
392                     FATEntry::Unused
393                 } else if entry == 0x0ff7 {
394                     FATEntry::Bad
395                 } else if entry >= 0x0ff8 {
396                     FATEntry::EndOfChain
397                 } else {
398                     FATEntry::Next(Cluster {
399                         cluster_num: entry as u64,
400                         parent_cluster: current_cluster,
401                     })
402                 }
403             }
404             FATType::FAT16(_) => {
405                 let entry = cursor.read_u16()?;
406 
407                 if entry == 0 {
408                     FATEntry::Unused
409                 } else if entry == 0xfff7 {
410                     FATEntry::Bad
411                 } else if entry >= 0xfff8 {
412                     FATEntry::EndOfChain
413                 } else {
414                     FATEntry::Next(Cluster {
415                         cluster_num: entry as u64,
416                         parent_cluster: current_cluster,
417                     })
418                 }
419             }
420             FATType::FAT32(_) => {
421                 let entry = cursor.read_u32()? & 0x0fffffff;
422 
423                 match entry {
424                     _n if (current_cluster >= 0x0ffffff7 && current_cluster <= 0x0fffffff) => {
425                         // 当前簇号不是一个能被获得的簇(可能是文件系统出错了)
426                         kerror!("FAT32 get fat entry: current cluster number [{}] is not an allocatable cluster number.", current_cluster);
427                         FATEntry::Bad
428                     }
429                     0 => FATEntry::Unused,
430                     0x0ffffff7 => FATEntry::Bad,
431                     0x0ffffff8..=0x0fffffff => FATEntry::EndOfChain,
432                     _n => FATEntry::Next(Cluster {
433                         cluster_num: entry as u64,
434                         parent_cluster: current_cluster,
435                     }),
436                 }
437             }
438         };
439         return Ok(res);
440     }
441 
442     /// @brief 读取当前簇在FAT表中存储的信息(直接返回读取到的值,而不加处理)
443     ///
444     /// @param cluster 当前簇
445     ///
446     /// @return Ok(u64) 当前簇在FAT表中,存储的信息。
447     /// @return Err(i32) 错误码
448     pub fn get_fat_entry_raw(&self, cluster: Cluster) -> Result<u64, i32> {
449         let current_cluster = cluster.cluster_num;
450 
451         let fat_type: FATType = self.bpb.fat_type;
452         // 获取FAT表的起始扇区(相对分区起始扇区的偏移量)
453         let fat_start_sector = self.fat_start_sector();
454         let bytes_per_sec = self.bpb.bytes_per_sector as u64;
455 
456         // cluster对应的FAT表项在分区内的字节偏移量
457         let fat_bytes_offset =
458             fat_type.get_fat_bytes_offset(cluster, fat_start_sector, bytes_per_sec);
459 
460         // FAT表项所在的LBA地址
461         let fat_ent_lba = self.get_lba_from_offset(self.bytes_to_sector(fat_bytes_offset));
462 
463         // FAT表项在逻辑块内的字节偏移量
464         let blk_offset = self.get_in_block_offset(fat_bytes_offset);
465 
466         let mut v = Vec::<u8>::new();
467         v.resize(self.bpb.bytes_per_sector as usize, 0);
468         self.partition
469             .disk()
470             .read_at(fat_ent_lba, 1 * self.lba_per_sector(), &mut v)?;
471 
472         let mut cursor = VecCursor::new(v);
473         cursor.seek(SeekFrom::SeekSet(blk_offset as i64))?;
474 
475         let res = match self.bpb.fat_type {
476             FATType::FAT12(_) => {
477                 let mut entry = cursor.read_u16()?;
478                 entry = if (current_cluster & 0x0001) > 0 {
479                     entry >> 4
480                 } else {
481                     entry & 0x0fff
482                 };
483                 entry as u64
484             }
485             FATType::FAT16(_) => {
486                 let entry = (cursor.read_u16()?) as u64;
487                 entry
488             }
489             FATType::FAT32(_) => {
490                 let entry = cursor.read_u32()? & 0x0fff_ffff;
491                 entry as u64
492             }
493         };
494 
495         return Ok(res);
496     }
497 
498     /// @brief 获取当前文件系统的root inode,在磁盘上的字节偏移量
499     pub fn root_dir_bytes_offset(&self) -> u64 {
500         match self.bpb.fat_type {
501             FATType::FAT32(s) => {
502                 let first_sec_cluster: u64 = (s.root_cluster as u64 - 2)
503                     * (self.bpb.sector_per_cluster as u64)
504                     + self.first_data_sector;
505                 return (self.get_lba_from_offset(first_sec_cluster) * LBA_SIZE) as u64;
506             }
507             _ => {
508                 let root_sec = (self.bpb.rsvd_sec_cnt as u64)
509                     + (self.bpb.num_fats as u64) * (self.bpb.fat_size_16 as u64);
510                 return (self.get_lba_from_offset(root_sec) * LBA_SIZE) as u64;
511             }
512         }
513     }
514 
515     /// @brief 获取当前文件系统的根目录项区域的结束位置,在磁盘上的字节偏移量。
516     /// 请注意,当前函数只对FAT12/FAT16生效。对于FAT32,返回None
517     pub fn root_dir_end_bytes_offset(&self) -> Option<u64> {
518         match self.bpb.fat_type {
519             FATType::FAT12(_) | FATType::FAT16(_) => {
520                 return Some(
521                     self.root_dir_bytes_offset() + (self.bpb.root_entries_cnt as u64) * 32,
522                 );
523             }
524             _ => {
525                 return None;
526             }
527         }
528     }
529 
530     /// @brief 获取簇在磁盘内的字节偏移量(相对磁盘起始位置。注意,不是分区内偏移量)
531     pub fn cluster_bytes_offset(&self, cluster: Cluster) -> u64 {
532         if cluster.cluster_num >= 2 {
533             // 指定簇的第一个扇区号
534             let first_sec_of_cluster = (cluster.cluster_num - 2)
535                 * (self.bpb.sector_per_cluster as u64)
536                 + self.first_data_sector;
537             return (self.get_lba_from_offset(first_sec_of_cluster) * LBA_SIZE) as u64;
538         } else {
539             return 0;
540         }
541     }
542 
543     /// @brief 获取一个空闲簇
544     ///
545     /// @param prev_cluster 簇链的前一个簇。本函数将会把新获取的簇,连接到它的后面。
546     ///
547     /// @return Ok(Cluster) 新获取的空闲簇
548     /// @return Err(i32) 错误码
549     pub fn allocate_cluster(&self, prev_cluster: Option<Cluster>) -> Result<Cluster, i32> {
550         let end_cluster: Cluster = self.max_cluster_number();
551         let start_cluster: Cluster = match self.bpb.fat_type {
552             FATType::FAT32(_) => {
553                 let next_free: u64 = match self.fs_info.0.lock().next_free() {
554                     Some(x) => x,
555                     None => 0xffffffff,
556                 };
557                 if next_free < end_cluster.cluster_num {
558                     Cluster::new(next_free)
559                 } else {
560                     Cluster::new(RESERVED_CLUSTERS as u64)
561                 }
562             }
563             _ => Cluster::new(RESERVED_CLUSTERS as u64),
564         };
565 
566         // 寻找一个空的簇
567         let free_cluster: Cluster = match self.get_free_cluster(start_cluster, end_cluster) {
568             Ok(c) => c,
569             Err(_) if start_cluster.cluster_num > RESERVED_CLUSTERS as u64 => {
570                 self.get_free_cluster(Cluster::new(RESERVED_CLUSTERS as u64), end_cluster)?
571             }
572             Err(e) => return Err(e),
573         };
574 
575         self.set_entry(free_cluster, FATEntry::EndOfChain)?;
576         // 减少空闲簇计数
577         self.fs_info.0.lock().update_free_count_delta(-1);
578         // 更新搜索空闲簇的参考量
579         self.fs_info
580             .0
581             .lock()
582             .update_next_free((free_cluster.cluster_num + 1) as u32);
583 
584         // 如果这个空闲簇不是簇链的第一个簇,那么把当前簇跟前一个簇连上。
585         if let Some(prev_cluster) = prev_cluster {
586             // kdebug!("set entry, prev ={prev_cluster:?}, next = {free_cluster:?}");
587             self.set_entry(prev_cluster, FATEntry::Next(free_cluster))?;
588         }
589         // 清空新获取的这个簇
590         self.zero_cluster(free_cluster)?;
591         return Ok(free_cluster);
592     }
593 
594     /// @brief 释放簇链上的所有簇
595     ///
596     /// @param start_cluster 簇链的第一个簇
597     pub fn deallocate_cluster_chain(&self, start_cluster: Cluster) -> Result<(), i32> {
598         let clusters: Vec<Cluster> = self.clusters(start_cluster);
599         for c in clusters {
600             self.deallocate_cluster(c)?;
601         }
602         return Ok(());
603     }
604 
605     /// @brief 释放簇
606     ///
607     /// @param 要释放的簇
608     pub fn deallocate_cluster(&self, cluster: Cluster) -> Result<(), i32> {
609         let entry: FATEntry = self.get_fat_entry(cluster)?;
610         // 如果不是坏簇
611         if entry != FATEntry::Bad {
612             self.set_entry(cluster, FATEntry::Unused)?;
613             self.fs_info.0.lock().update_free_count_delta(1);
614             // 安全选项:清空被释放的簇
615             #[cfg(feature = "secure")]
616             self.zero_cluster(cluster)?;
617             return Ok(());
618         } else {
619             // 不能释放坏簇
620             kerror!("Bad clusters cannot be freed.");
621             return Err(-(EFAULT as i32));
622         }
623     }
624 
625     /// @brief 获取文件系统的根目录项
626     pub fn root_dir(&self) -> FATDir {
627         match self.bpb.fat_type {
628             FATType::FAT32(s) => {
629                 return FATDir {
630                     first_cluster: Cluster::new(s.root_cluster as u64),
631                     dir_name: String::from("/"),
632                     root_offset: None,
633                     short_dir_entry: None,
634                     loc: None,
635                 };
636             }
637             _ => FATDir {
638                 first_cluster: Cluster::new(0),
639                 dir_name: String::from("/"),
640                 root_offset: Some(self.root_dir_bytes_offset()),
641                 short_dir_entry: None,
642                 loc: None,
643             },
644         }
645     }
646 
647     /// @brief 获取FAT表的起始扇区(相对分区起始扇区的偏移量)
648     pub fn fat_start_sector(&self) -> u64 {
649         let active_fat = self.active_fat();
650         let fat_size = self.fat_size();
651         return self.bpb.rsvd_sec_cnt as u64 + active_fat * fat_size;
652     }
653 
654     /// @brief 获取当前活动的FAT表
655     pub fn active_fat(&self) -> u64 {
656         if self.mirroring_enabled() {
657             return 0;
658         } else {
659             match self.bpb.fat_type {
660                 FATType::FAT32(bpb32) => {
661                     return (bpb32.ext_flags & 0x0f) as u64;
662                 }
663                 _ => {
664                     return 0;
665                 }
666             }
667         }
668     }
669 
670     /// @brief 获取当前文件系统的每个FAT表的大小
671     pub fn fat_size(&self) -> u64 {
672         if self.bpb.fat_size_16 != 0 {
673             return self.bpb.fat_size_16 as u64;
674         } else {
675             match self.bpb.fat_type {
676                 FATType::FAT32(bpb32) => {
677                     return bpb32.fat_size_32 as u64;
678                 }
679 
680                 _ => {
681                     panic!("FAT12 and FAT16 volumes should have non-zero BPB_FATSz16");
682                 }
683             }
684         }
685     }
686 
687     /// @brief 判断当前文件系统是否启用了FAT表镜像
688     pub fn mirroring_enabled(&self) -> bool {
689         match self.bpb.fat_type {
690             FATType::FAT32(bpb32) => {
691                 return (bpb32.ext_flags & 0x80) == 0;
692             }
693             _ => {
694                 return false;
695             }
696         }
697     }
698 
699     /// @brief 根据分区内的扇区偏移量,获得在磁盘上的LBA地址
700     #[inline]
701     pub fn get_lba_from_offset(&self, in_partition_sec_offset: u64) -> usize {
702         return (self.partition.lba_start
703             + in_partition_sec_offset * (self.bpb.bytes_per_sector as u64 / LBA_SIZE as u64))
704             as usize;
705     }
706 
707     /// @brief 获取每个扇区占用多少个LBA
708     #[inline]
709     pub fn lba_per_sector(&self) -> usize {
710         return self.bpb.bytes_per_sector as usize / LBA_SIZE;
711     }
712 
713     /// @brief 将分区内字节偏移量转换为扇区偏移量
714     #[inline]
715     pub fn bytes_to_sector(&self, in_partition_bytes_offset: u64) -> u64 {
716         return in_partition_bytes_offset / (self.bpb.bytes_per_sector as u64);
717     }
718 
719     /// @brief 根据磁盘上的字节偏移量,获取对应位置在分区内的字节偏移量
720     #[inline]
721     pub fn get_in_partition_bytes_offset(&self, disk_bytes_offset: u64) -> u64 {
722         return disk_bytes_offset - (self.partition.lba_start * LBA_SIZE as u64);
723     }
724 
725     /// @brief 根据字节偏移量计算在逻辑块内的字节偏移量
726     #[inline]
727     pub fn get_in_block_offset(&self, bytes_offset: u64) -> u64 {
728         return bytes_offset % LBA_SIZE as u64;
729     }
730 
731     /// @brief 获取在FAT表中,以start_cluster开头的FAT链的所有簇的信息
732     ///
733     /// @param start_cluster 整个FAT链的起始簇号
734     pub fn clusters(&self, start_cluster: Cluster) -> Vec<Cluster> {
735         return self.cluster_iter(start_cluster).collect();
736     }
737 
738     /// @brief 获取在FAT表中,以start_cluster开头的FAT链的长度(总计经过多少个簇)
739     ///
740     /// @param start_cluster 整个FAT链的起始簇号
741     pub fn num_clusters_chain(&self, start_cluster: Cluster) -> u64 {
742         return self
743             .cluster_iter(start_cluster)
744             .fold(0, |size, _cluster| size + 1);
745     }
746     /// @brief 获取一个簇迭代器对象
747     ///
748     /// @param start_cluster 整个FAT链的起始簇号
749     fn cluster_iter(&self, start_cluster: Cluster) -> ClusterIter {
750         return ClusterIter {
751             current_cluster: Some(start_cluster),
752             fs: self,
753         };
754     }
755 
756     /// @brief 获取从start_cluster开始的簇链中,第n个簇的信息。(请注意,下标从0开始)
757     #[inline]
758     pub fn get_cluster_by_relative(&self, start_cluster: Cluster, n: usize) -> Option<Cluster> {
759         return self.cluster_iter(start_cluster).skip(n).next();
760     }
761 
762     /// @brief 获取整个簇链的最后一个簇
763     #[inline]
764     pub fn get_last_cluster(&self, start_cluster: Cluster) -> Option<Cluster> {
765         return self.cluster_iter(start_cluster).last();
766     }
767 
768     /// @brief 判断FAT文件系统的shut bit是否正常。
769     /// shut bit 表示文件系统是否正常卸载。如果这一位是1,则表示这个卷是“干净的”
770     /// 参考资料:https://thestarman.pcministry.com/DOS/DirtyShutdownFlag.html
771     ///
772     /// @return Ok(true) 正常
773     /// @return Ok(false) 不正常
774     /// @return Err(i32) 在判断时发生错误
775     pub fn is_shut_bit_ok(&mut self) -> Result<bool, i32> {
776         match self.bpb.fat_type {
777             FATType::FAT32(_) => {
778                 // 对于FAT32, error bit位于第一个扇区的第8字节。
779                 let bit = self.get_fat_entry_raw(Cluster::new(1))? & 0x0800_0000;
780                 return Ok(bit > 0);
781             }
782             FATType::FAT16(_) => {
783                 let bit = self.get_fat_entry_raw(Cluster::new(1))? & 0x8000;
784                 return Ok(bit > 0);
785             }
786             _ => return Ok(true),
787         }
788     }
789 
790     /// @brief 判断FAT文件系统的hard error bit是否正常。
791     /// 如果此位为0,则文件系统驱动程序在上次安装卷时遇到磁盘 I/O 错误,这表明
792     /// 卷上的某些扇区可能已损坏。
793     /// 参考资料:https://thestarman.pcministry.com/DOS/DirtyShutdownFlag.html
794     ///
795     /// @return Ok(true) 正常
796     /// @return Ok(false) 不正常
797     /// @return Err(i32) 在判断时发生错误
798     pub fn is_hard_error_bit_ok(&mut self) -> Result<bool, i32> {
799         match self.bpb.fat_type {
800             FATType::FAT32(_) => {
801                 let bit = self.get_fat_entry_raw(Cluster::new(1))? & 0x0400_0000;
802                 return Ok(bit > 0);
803             }
804             FATType::FAT16(_) => {
805                 let bit = self.get_fat_entry_raw(Cluster::new(1))? & 0x4000;
806                 return Ok(bit > 0);
807             }
808             _ => return Ok(true),
809         }
810     }
811 
812     /// @brief 设置文件系统的shut bit为正常状态
813     /// 参考资料:https://thestarman.pcministry.com/DOS/DirtyShutdownFlag.html
814     ///
815     /// @return Ok(()) 设置成功
816     /// @return Err(i32) 在设置过程中,出现错误
817     pub fn set_shut_bit_ok(&mut self) -> Result<(), i32> {
818         match self.bpb.fat_type {
819             FATType::FAT32(_) => {
820                 let raw_entry = self.get_fat_entry_raw(Cluster::new(1))? | 0x0800_0000;
821                 self.set_entry(Cluster::new(1), FATEntry::Next(Cluster::new(raw_entry)))?;
822 
823                 return Ok(());
824             }
825 
826             FATType::FAT16(_) => {
827                 let raw_entry = self.get_fat_entry_raw(Cluster::new(1))? | 0x8000;
828                 self.set_entry(Cluster::new(1), FATEntry::Next(Cluster::new(raw_entry)))?;
829                 return Ok(());
830             }
831             _ => return Ok(()),
832         }
833     }
834 
835     /// @brief 设置文件系统的hard error bit为正常状态
836     /// 参考资料:https://thestarman.pcministry.com/DOS/DirtyShutdownFlag.html
837     ///
838     /// @return Ok(()) 设置成功
839     /// @return Err(i32) 在设置过程中,出现错误
840     pub fn set_hard_error_bit_ok(&mut self) -> Result<(), i32> {
841         match self.bpb.fat_type {
842             FATType::FAT32(_) => {
843                 let raw_entry = self.get_fat_entry_raw(Cluster::new(1))? | 0x0400_0000;
844                 self.set_entry(Cluster::new(1), FATEntry::Next(Cluster::new(raw_entry)))?;
845                 return Ok(());
846             }
847 
848             FATType::FAT16(_) => {
849                 let raw_entry = self.get_fat_entry_raw(Cluster::new(1))? | 0x4000;
850                 self.set_entry(Cluster::new(1), FATEntry::Next(Cluster::new(raw_entry)))?;
851                 return Ok(());
852             }
853             _ => return Ok(()),
854         }
855     }
856 
857     /// @brief 执行文件系统卸载前的一些准备工作:设置好对应的标志位,并把缓存中的数据刷入磁盘
858     pub fn umount(&mut self) -> Result<(), i32> {
859         self.fs_info.0.lock().flush(&self.partition)?;
860 
861         self.set_shut_bit_ok()?;
862 
863         self.set_hard_error_bit_ok()?;
864 
865         self.partition.disk().sync()?;
866 
867         return Ok(());
868     }
869 
870     /// @brief 获取文件系统的最大簇号
871     pub fn max_cluster_number(&self) -> Cluster {
872         match self.bpb.fat_type {
873             FATType::FAT32(s) => {
874                 // FAT32
875 
876                 // 数据扇区数量(总扇区数-保留扇区-FAT占用的扇区)
877                 let data_sec: u64 = self.bpb.total_sectors_32 as u64
878                     - (self.bpb.rsvd_sec_cnt as u64
879                         + self.bpb.num_fats as u64 * s.fat_size_32 as u64);
880 
881                 // 数据区的簇数量
882                 let total_clusters: u64 = data_sec / self.bpb.sector_per_cluster as u64;
883 
884                 // 返回最大的簇号
885                 return Cluster::new(total_clusters + RESERVED_CLUSTERS as u64 - 1);
886             }
887 
888             _ => {
889                 // FAT12 / FAT16
890                 let root_dir_sectors: u64 = (((self.bpb.root_entries_cnt as u64) * 32)
891                     + self.bpb.bytes_per_sector as u64
892                     - 1)
893                     / self.bpb.bytes_per_sector as u64;
894                 // 数据区扇区数
895                 let data_sec: u64 = self.bpb.total_sectors_16 as u64
896                     - (self.bpb.rsvd_sec_cnt as u64
897                         + (self.bpb.num_fats as u64 * self.bpb.fat_size_16 as u64)
898                         + root_dir_sectors);
899                 let total_clusters = data_sec / self.bpb.sector_per_cluster as u64;
900                 return Cluster::new(total_clusters + RESERVED_CLUSTERS as u64 - 1);
901             }
902         }
903     }
904 
905     /// @brief 在文件系统中寻找一个簇号在给定的范围(左闭右开区间)内的空闲簇
906     ///
907     /// @param start_cluster 起始簇号
908     /// @param end_cluster 终止簇号(不包含)
909     ///
910     /// @return Ok(Cluster) 寻找到的空闲簇
911     /// @return Err(i32) 错误码。如果磁盘无剩余空间,或者簇号达到给定的最大值,则返回-ENOSPC.
912     pub fn get_free_cluster(
913         &self,
914         start_cluster: Cluster,
915         end_cluster: Cluster,
916     ) -> Result<Cluster, i32> {
917         let max_cluster: Cluster = self.max_cluster_number();
918         let mut cluster: u64 = start_cluster.cluster_num;
919 
920         let fat_type: FATType = self.bpb.fat_type;
921         let fat_start_sector: u64 = self.fat_start_sector();
922         let bytes_per_sec: u64 = self.bpb.bytes_per_sector as u64;
923 
924         match fat_type {
925             FATType::FAT12(_) => {
926                 let part_bytes_offset: u64 =
927                     fat_type.get_fat_bytes_offset(start_cluster, fat_start_sector, bytes_per_sec);
928                 let in_block_offset = self.get_in_block_offset(part_bytes_offset);
929 
930                 let lba = self.get_lba_from_offset(self.bytes_to_sector(part_bytes_offset));
931 
932                 // 由于FAT12的FAT表不大于6K,因此直接读取6K
933                 let num_lba = (6 * 1024) / LBA_SIZE;
934                 let mut v: Vec<u8> = Vec::new();
935                 v.resize(num_lba * LBA_SIZE, 0);
936                 self.partition.disk().read_at(lba, num_lba, &mut v)?;
937 
938                 let mut cursor: VecCursor = VecCursor::new(v);
939                 cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
940 
941                 let mut packed_val: u16 = cursor.read_u16()?;
942                 loop {
943                     let val = if (cluster & 0x1) > 0 {
944                         packed_val >> 4
945                     } else {
946                         packed_val & 0x0fff
947                     };
948                     if val == 0 {
949                         return Ok(Cluster::new(cluster as u64));
950                     }
951 
952                     cluster += 1;
953 
954                     // 磁盘无剩余空间,或者簇号达到给定的最大值
955                     if cluster == end_cluster.cluster_num || cluster == max_cluster.cluster_num {
956                         return Err(-(ENOSPC as i32));
957                     }
958 
959                     packed_val = match cluster & 1 {
960                         0 => cursor.read_u16()?,
961                         _ => {
962                             let next_byte = cursor.read_u8()? as u16;
963                             (packed_val >> 8) | (next_byte << 8)
964                         }
965                     };
966                 }
967             }
968             FATType::FAT16(_) => {
969                 // todo: 优化这里,减少读取磁盘的次数。
970                 while cluster < end_cluster.cluster_num && cluster < max_cluster.cluster_num {
971                     let part_bytes_offset: u64 = fat_type.get_fat_bytes_offset(
972                         Cluster::new(cluster),
973                         fat_start_sector,
974                         bytes_per_sec,
975                     );
976                     let in_block_offset = self.get_in_block_offset(part_bytes_offset);
977 
978                     let lba = self.get_lba_from_offset(self.bytes_to_sector(part_bytes_offset));
979 
980                     let mut v: Vec<u8> = Vec::new();
981                     v.resize(self.lba_per_sector() * LBA_SIZE, 0);
982                     self.partition
983                         .disk()
984                         .read_at(lba, self.lba_per_sector(), &mut v)?;
985 
986                     let mut cursor: VecCursor = VecCursor::new(v);
987                     cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
988 
989                     let val = cursor.read_u16()?;
990                     // 找到空闲簇
991                     if val == 0 {
992                         return Ok(Cluster::new(val as u64));
993                     }
994                     cluster += 1;
995                 }
996 
997                 // 磁盘无剩余空间,或者簇号达到给定的最大值
998                 return Err(-(ENOSPC as i32));
999             }
1000             FATType::FAT32(_) => {
1001                 // todo: 优化这里,减少读取磁盘的次数。
1002                 while cluster < end_cluster.cluster_num && cluster < max_cluster.cluster_num {
1003                     let part_bytes_offset: u64 = fat_type.get_fat_bytes_offset(
1004                         Cluster::new(cluster),
1005                         fat_start_sector,
1006                         bytes_per_sec,
1007                     );
1008                     let in_block_offset = self.get_in_block_offset(part_bytes_offset);
1009 
1010                     let lba = self.get_lba_from_offset(self.bytes_to_sector(part_bytes_offset));
1011 
1012                     let mut v: Vec<u8> = Vec::new();
1013                     v.resize(self.lba_per_sector() * LBA_SIZE, 0);
1014                     self.partition
1015                         .disk()
1016                         .read_at(lba, self.lba_per_sector(), &mut v)?;
1017 
1018                     let mut cursor: VecCursor = VecCursor::new(v);
1019                     cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1020 
1021                     let val = cursor.read_u32()? & 0x0fffffff;
1022 
1023                     if val == 0 {
1024                         return Ok(Cluster::new(cluster));
1025                     }
1026                     cluster += 1;
1027                 }
1028 
1029                 // 磁盘无剩余空间,或者簇号达到给定的最大值
1030                 return Err(-(ENOSPC as i32));
1031             }
1032         }
1033     }
1034 
1035     /// @brief 在FAT表中,设置指定的簇的信息。
1036     ///
1037     /// @param cluster 目标簇
1038     /// @param fat_entry 这个簇在FAT表中,存储的信息(下一个簇的簇号)
1039     pub fn set_entry(&self, cluster: Cluster, fat_entry: FATEntry) -> Result<(), i32> {
1040         // fat表项在分区上的字节偏移量
1041         let fat_part_bytes_offset: u64 = self.bpb.fat_type.get_fat_bytes_offset(
1042             cluster,
1043             self.fat_start_sector(),
1044             self.bpb.bytes_per_sector as u64,
1045         );
1046 
1047         match self.bpb.fat_type {
1048             FATType::FAT12(_) => {
1049                 // 计算要写入的值
1050                 let raw_val: u16 = match fat_entry {
1051                     FATEntry::Unused => 0,
1052                     FATEntry::Bad => 0xff7,
1053                     FATEntry::EndOfChain => 0xfff,
1054                     FATEntry::Next(c) => c.cluster_num as u16,
1055                 };
1056 
1057                 let in_block_offset = self.get_in_block_offset(fat_part_bytes_offset);
1058 
1059                 let lba = self.get_lba_from_offset(self.bytes_to_sector(fat_part_bytes_offset));
1060 
1061                 let mut v: Vec<u8> = Vec::new();
1062                 v.resize(LBA_SIZE, 0);
1063                 self.partition.disk().read_at(lba, 1, &mut v)?;
1064 
1065                 let mut cursor: VecCursor = VecCursor::new(v);
1066                 cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1067 
1068                 let old_val: u16 = cursor.read_u16()?;
1069                 let new_val: u16 = if (cluster.cluster_num & 0x1) > 0 {
1070                     (old_val & 0x000f) | (raw_val << 4)
1071                 } else {
1072                     (old_val & 0xf000) | raw_val
1073                 };
1074 
1075                 // 写回数据到磁盘上
1076                 cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1077                 cursor.write_u16(new_val)?;
1078                 self.partition.disk().write_at(lba, 1, cursor.as_slice())?;
1079                 return Ok(());
1080             }
1081             FATType::FAT16(_) => {
1082                 // 计算要写入的值
1083                 let raw_val: u16 = match fat_entry {
1084                     FATEntry::Unused => 0,
1085                     FATEntry::Bad => 0xfff7,
1086                     FATEntry::EndOfChain => 0xfdff,
1087                     FATEntry::Next(c) => c.cluster_num as u16,
1088                 };
1089 
1090                 let in_block_offset = self.get_in_block_offset(fat_part_bytes_offset);
1091 
1092                 let lba = self.get_lba_from_offset(self.bytes_to_sector(fat_part_bytes_offset));
1093 
1094                 let mut v: Vec<u8> = Vec::new();
1095                 v.resize(LBA_SIZE, 0);
1096                 self.partition.disk().read_at(lba, 1, &mut v)?;
1097 
1098                 let mut cursor: VecCursor = VecCursor::new(v);
1099                 cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1100 
1101                 cursor.write_u16(raw_val)?;
1102                 self.partition.disk().write_at(lba, 1, cursor.as_slice())?;
1103 
1104                 return Ok(());
1105             }
1106             FATType::FAT32(_) => {
1107                 let fat_size: u64 = self.fat_size();
1108                 let bound: u64 = if self.mirroring_enabled() {
1109                     1
1110                 } else {
1111                     self.bpb.num_fats as u64
1112                 };
1113                 // kdebug!("set entry, bound={bound}, fat_size={fat_size}");
1114                 for i in 0..bound {
1115                     // 当前操作的FAT表在磁盘上的字节偏移量
1116                     let f_offset: u64 = fat_part_bytes_offset + i * fat_size;
1117                     let in_block_offset: u64 = self.get_in_block_offset(f_offset);
1118                     let lba = self.get_lba_from_offset(self.bytes_to_sector(f_offset));
1119 
1120                     // kdebug!("set entry, lba={lba}, in_block_offset={in_block_offset}");
1121                     let mut v: Vec<u8> = Vec::new();
1122                     v.resize(LBA_SIZE, 0);
1123                     self.partition.disk().read_at(lba, 1, &mut v)?;
1124 
1125                     let mut cursor: VecCursor = VecCursor::new(v);
1126                     cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1127 
1128                     // FAT32的高4位保留
1129                     let old_bits = cursor.read_u32()? & 0xf0000000;
1130 
1131                     if fat_entry == FATEntry::Unused
1132                         && cluster.cluster_num >= 0x0ffffff7
1133                         && cluster.cluster_num <= 0x0fffffff
1134                     {
1135                         kerror!(
1136                             "FAT32: Reserved Cluster {:?} cannot be marked as free",
1137                             cluster
1138                         );
1139                         return Err(-(EPERM as i32));
1140                     }
1141 
1142                     // 计算要写入的值
1143                     let mut raw_val: u32 = match fat_entry {
1144                         FATEntry::Unused => 0,
1145                         FATEntry::Bad => 0x0FFFFFF7,
1146                         FATEntry::EndOfChain => 0x0FFFFFFF,
1147                         FATEntry::Next(c) => c.cluster_num as u32,
1148                     };
1149 
1150                     // 恢复保留位
1151                     raw_val |= old_bits;
1152 
1153                     // kdebug!("sent entry, raw_val={raw_val}");
1154 
1155                     cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1156                     cursor.write_u32(raw_val)?;
1157 
1158                     self.partition.disk().write_at(lba, 1, cursor.as_slice())?;
1159                 }
1160 
1161                 return Ok(());
1162             }
1163         }
1164     }
1165 
1166     /// @brief 清空指定的簇
1167     ///
1168     /// @param cluster 要被清空的簇
1169     pub fn zero_cluster(&self, cluster: Cluster) -> Result<(), i32> {
1170         // 准备数据,用于写入
1171         let zeros: Vec<u8> = vec![0u8; self.bytes_per_cluster() as usize];
1172         let offset: usize = self.cluster_bytes_offset(cluster) as usize;
1173         self.partition
1174             .disk()
1175             .device()
1176             .write_at(offset, zeros.len(), zeros.as_slice())?;
1177         return Ok(());
1178     }
1179 }
1180 
1181 impl Drop for FATFileSystem {
1182     fn drop(&mut self) {
1183         let r = self.umount();
1184         if r.is_err() {
1185             kerror!(
1186                 "Umount FAT filesystem failed: errno={}, FS detail:{self:?}",
1187                 r.unwrap_err()
1188             );
1189         }
1190     }
1191 }
1192 
1193 impl FATFsInfo {
1194     const LEAD_SIG: u32 = 0x41615252;
1195     const STRUC_SIG: u32 = 0x61417272;
1196     const TRAIL_SIG: u32 = 0xAA550000;
1197     const FS_INFO_SIZE: u64 = 512;
1198 
1199     /// @brief 从磁盘上读取FAT文件系统的FSInfo结构体
1200     ///
1201     /// @param partition 磁盘分区
1202     /// @param in_disk_fs_info_offset FSInfo扇区在磁盘内的字节偏移量(单位:字节)
1203     /// @param bytes_per_sec 每扇区字节数
1204     pub fn new(
1205         partition: Arc<Partition>,
1206         in_disk_fs_info_offset: u64,
1207         bytes_per_sec: usize,
1208     ) -> Result<Self, i32> {
1209         let mut v = Vec::<u8>::new();
1210         v.resize(bytes_per_sec, 0);
1211 
1212         // 计算fs_info扇区在磁盘上的字节偏移量,从磁盘读取数据
1213         partition
1214             .disk()
1215             .read_at(in_disk_fs_info_offset as usize / LBA_SIZE, 1, &mut v)?;
1216         let mut cursor = VecCursor::new(v);
1217 
1218         let mut fsinfo = FATFsInfo::default();
1219 
1220         fsinfo.lead_sig = cursor.read_u32()?;
1221         cursor.seek(SeekFrom::SeekCurrent(480))?;
1222         fsinfo.struc_sig = cursor.read_u32()?;
1223         fsinfo.free_count = cursor.read_u32()?;
1224         fsinfo.next_free = cursor.read_u32()?;
1225 
1226         cursor.seek(SeekFrom::SeekCurrent(12))?;
1227 
1228         fsinfo.trail_sig = cursor.read_u32()?;
1229         fsinfo.dirty = false;
1230         fsinfo.offset = Some(in_disk_fs_info_offset);
1231 
1232         if fsinfo.is_valid() {
1233             return Ok(fsinfo);
1234         } else {
1235             kerror!("Error occurred while parsing FATFsInfo.");
1236             return Err(-(EINVAL as i32));
1237         }
1238     }
1239 
1240     /// @brief 判断是否为正确的FsInfo结构体
1241     fn is_valid(&self) -> bool {
1242         self.lead_sig == Self::LEAD_SIG
1243             && self.struc_sig == Self::STRUC_SIG
1244             && self.trail_sig == Self::TRAIL_SIG
1245     }
1246 
1247     /// @brief 根据fsinfo的信息,计算当前总的空闲簇数量
1248     ///
1249     /// @param 当前文件系统的最大簇号
1250     pub fn count_free_cluster(&self, max_cluster: Cluster) -> Option<u64> {
1251         let count_clusters = max_cluster.cluster_num - RESERVED_CLUSTERS as u64 + 1;
1252         // 信息不合理,当前的FsInfo中存储的free count大于计算出来的值
1253         if self.free_count as u64 > count_clusters {
1254             return None;
1255         } else {
1256             match self.free_count {
1257                 // free count字段不可用
1258                 0xffffffff => return None,
1259                 // 返回FsInfo中存储的数据
1260                 n => return Some(n as u64),
1261             }
1262         }
1263     }
1264 
1265     /// @brief 更新FsInfo中的“空闲簇统计信息“为new_count
1266     ///
1267     /// 请注意,除非手动调用`flush()`,否则本函数不会将数据刷入磁盘
1268     pub fn update_free_count_abs(&mut self, new_count: u32) {
1269         self.free_count = new_count;
1270     }
1271 
1272     /// @brief 更新FsInfo中的“空闲簇统计信息“,把它加上delta.
1273     ///
1274     /// 请注意,除非手动调用`flush()`,否则本函数不会将数据刷入磁盘
1275     pub fn update_free_count_delta(&mut self, delta: i32) {
1276         self.free_count = (self.free_count as i32 + delta) as u32;
1277     }
1278 
1279     /// @brief 更新FsInfo中的“第一个空闲簇统计信息“为next_free.
1280     ///
1281     /// 请注意,除非手动调用`flush()`,否则本函数不会将数据刷入磁盘
1282     pub fn update_next_free(&mut self, next_free: u32) {
1283         // 这个值是参考量,不一定要准确,仅供加速查找
1284         self.next_free = next_free;
1285     }
1286 
1287     /// @brief 获取fs info 记载的第一个空闲簇。(不一定准确,仅供参考)
1288     pub fn next_free(&self) -> Option<u64> {
1289         match self.next_free {
1290             0xffffffff => return None,
1291             0 | 1 => return None,
1292             n => return Some(n as u64),
1293         };
1294     }
1295 
1296     /// @brief 把fs info刷入磁盘
1297     ///
1298     /// @param partition fs info所在的分区
1299     pub fn flush(&self, partition: &Arc<Partition>) -> Result<(), i32> {
1300         if let Some(off) = self.offset {
1301             let in_block_offset = off % LBA_SIZE as u64;
1302 
1303             let lba = off as usize / LBA_SIZE;
1304 
1305             let mut v: Vec<u8> = Vec::new();
1306             v.resize(LBA_SIZE, 0);
1307             partition.disk().read_at(lba, 1, &mut v)?;
1308 
1309             let mut cursor: VecCursor = VecCursor::new(v);
1310             cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1311 
1312             cursor.write_u32(self.lead_sig)?;
1313             cursor.seek(SeekFrom::SeekCurrent(480))?;
1314             cursor.write_u32(self.struc_sig)?;
1315             cursor.write_u32(self.free_count)?;
1316             cursor.write_u32(self.next_free)?;
1317             cursor.seek(SeekFrom::SeekCurrent(12))?;
1318             cursor.write_u32(self.trail_sig)?;
1319 
1320             partition.disk().write_at(lba, 1, cursor.as_slice())?;
1321         }
1322         return Ok(());
1323     }
1324 
1325     /// @brief 读取磁盘上的Fs Info扇区,将里面的内容更新到结构体中
1326     ///
1327     /// @param partition fs info所在的分区
1328     pub fn update(&mut self, partition: Arc<Partition>) -> Result<(), i32> {
1329         if let Some(off) = self.offset {
1330             let in_block_offset = off % LBA_SIZE as u64;
1331 
1332             let lba = off as usize / LBA_SIZE;
1333 
1334             let mut v: Vec<u8> = Vec::new();
1335             v.resize(LBA_SIZE, 0);
1336             partition.disk().read_at(lba, 1, &mut v)?;
1337             let mut cursor: VecCursor = VecCursor::new(v);
1338             cursor.seek(SeekFrom::SeekSet(in_block_offset as i64))?;
1339             self.lead_sig = cursor.read_u32()?;
1340 
1341             cursor.seek(SeekFrom::SeekCurrent(480))?;
1342             self.struc_sig = cursor.read_u32()?;
1343             self.free_count = cursor.read_u32()?;
1344             self.next_free = cursor.read_u32()?;
1345             cursor.seek(SeekFrom::SeekCurrent(12))?;
1346             self.trail_sig = cursor.read_u32()?;
1347         }
1348         return Ok(());
1349     }
1350 }
1351 
1352 impl IndexNode for LockedFATInode {
1353     fn read_at(
1354         &self,
1355         offset: usize,
1356         len: usize,
1357         buf: &mut [u8],
1358         _data: &mut FilePrivateData,
1359     ) -> Result<usize, i32> {
1360         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1361         match &guard.inode_type {
1362             FATDirEntry::File(f) | FATDirEntry::VolId(f) => {
1363                 let r = f.read(
1364                     &guard.fs.upgrade().unwrap(),
1365                     &mut buf[0..len],
1366                     offset as u64,
1367                 );
1368                 guard.update_metadata();
1369                 return r;
1370             }
1371             FATDirEntry::Dir(_) => {
1372                 return Err(-(EISDIR as i32));
1373             }
1374             FATDirEntry::UnInit => {
1375                 kerror!("FATFS: param: Inode_type uninitialized.");
1376                 return Err(-(EROFS as i32));
1377             }
1378         }
1379     }
1380 
1381     fn write_at(
1382         &self,
1383         offset: usize,
1384         len: usize,
1385         buf: &[u8],
1386         _data: &mut FilePrivateData,
1387     ) -> Result<usize, i32> {
1388         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1389         let fs: &Arc<FATFileSystem> = &guard.fs.upgrade().unwrap();
1390 
1391         match &mut guard.inode_type {
1392             FATDirEntry::File(f) | FATDirEntry::VolId(f) => {
1393                 let r = f.write(fs, &buf[0..len], offset as u64);
1394                 guard.update_metadata();
1395                 return r;
1396             }
1397             FATDirEntry::Dir(_) => {
1398                 return Err(-(EISDIR as i32));
1399             }
1400             FATDirEntry::UnInit => {
1401                 kerror!("FATFS: param: Inode_type uninitialized.");
1402                 return Err(-(EROFS as i32));
1403             }
1404         }
1405     }
1406 
1407     fn poll(&self) -> Result<PollStatus, i32> {
1408         // 加锁
1409         let inode: SpinLockGuard<FATInode> = self.0.lock();
1410 
1411         // 检查当前inode是否为一个文件夹,如果是的话,就返回错误
1412         if inode.metadata.file_type == FileType::Dir {
1413             return Err(-(EISDIR as i32));
1414         }
1415 
1416         return Ok(PollStatus {
1417             flags: PollStatus::READ_MASK | PollStatus::WRITE_MASK,
1418         });
1419     }
1420 
1421     fn create(
1422         &self,
1423         name: &str,
1424         file_type: FileType,
1425         _mode: u32,
1426     ) -> Result<Arc<dyn IndexNode>, i32> {
1427         // 由于FAT32不支持文件权限的功能,因此忽略mode参数
1428 
1429         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1430         let fs: &Arc<FATFileSystem> = &guard.fs.upgrade().unwrap();
1431 
1432         match &mut guard.inode_type {
1433             FATDirEntry::File(_) | FATDirEntry::VolId(_) => {
1434                 return Err(-(ENOTDIR as i32));
1435             }
1436             FATDirEntry::Dir(d) => match file_type {
1437                 FileType::File => {
1438                     d.create_file(name, fs)?;
1439                     return Ok(guard.find(name)?);
1440                 }
1441                 FileType::Dir => {
1442                     d.create_dir(name, fs)?;
1443                     return Ok(guard.find(name)?);
1444                 }
1445 
1446                 FileType::SymLink => return Err(-(ENOTSUP as i32)),
1447                 _ => return Err(-(EINVAL as i32)),
1448             },
1449             FATDirEntry::UnInit => {
1450                 kerror!("FATFS: param: Inode_type uninitialized.");
1451                 return Err(-(EROFS as i32));
1452             }
1453         }
1454     }
1455 
1456     fn fs(&self) -> Arc<dyn FileSystem> {
1457         return self.0.lock().fs.upgrade().unwrap();
1458     }
1459 
1460     fn as_any_ref(&self) -> &dyn core::any::Any {
1461         return self;
1462     }
1463 
1464     fn metadata(&self) -> Result<Metadata, i32> {
1465         return Ok(self.0.lock().metadata.clone());
1466     }
1467 
1468     fn list(&self) -> Result<Vec<String>, i32> {
1469         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1470         let fatent: &FATDirEntry = &guard.inode_type;
1471         match fatent {
1472             FATDirEntry::File(_) | FATDirEntry::VolId(_) => {
1473                 return Err(-(ENOTDIR as i32));
1474             }
1475             FATDirEntry::Dir(dir) => {
1476                 // 获取当前目录下的所有目录项
1477                 let mut ret: Vec<String> = Vec::new();
1478                 let dir_iter: FATDirIter = dir.to_iter(guard.fs.upgrade().unwrap());
1479                 for ent in dir_iter {
1480                     ret.push(ent.name());
1481 
1482                     // ====== 生成inode缓存,存入B树
1483                     let name: String = ent.name();
1484                     // kdebug!("name={name}");
1485 
1486                     if guard.children.contains_key(&name.to_uppercase()) == false
1487                         && name != "."
1488                         && name != ".."
1489                     {
1490                         // 创建新的inode
1491                         let entry_inode: Arc<LockedFATInode> = LockedFATInode::new(
1492                             guard.fs.upgrade().unwrap(),
1493                             guard.self_ref.clone(),
1494                             ent,
1495                         );
1496                         // 加入缓存区, 由于FAT文件系统的大小写不敏感问题,因此存入缓存区的key应当是全大写的
1497                         guard
1498                             .children
1499                             .insert(name.to_uppercase(), entry_inode.clone());
1500                     }
1501                 }
1502                 return Ok(ret);
1503             }
1504             FATDirEntry::UnInit => {
1505                 kerror!("FATFS: param: Inode_type uninitialized.");
1506                 return Err(-(EROFS as i32));
1507             }
1508         }
1509     }
1510 
1511     fn find(&self, name: &str) -> Result<Arc<dyn IndexNode>, i32> {
1512         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1513         let target = guard.find(name)?;
1514         return Ok(target);
1515     }
1516 
1517     fn open(&self, _data: &mut FilePrivateData, _mode: &FileMode) -> Result<(), i32> {
1518         return Ok(());
1519     }
1520 
1521     fn close(&self, _data: &mut FilePrivateData) -> Result<(), i32> {
1522         return Ok(());
1523     }
1524 
1525     fn unlink(&self, name: &str) -> Result<(), i32> {
1526         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1527         let target: Arc<LockedFATInode> = guard.find(name)?;
1528         // 对目标inode上锁,以防更改
1529         let target_guard: SpinLockGuard<FATInode> = target.0.lock();
1530         // 先从缓存删除
1531         guard.children.remove(&name.to_uppercase());
1532 
1533         let dir = match &guard.inode_type {
1534             FATDirEntry::File(_) | FATDirEntry::VolId(_) => {
1535                 return Err(-(ENOTDIR as i32));
1536             }
1537             FATDirEntry::Dir(d) => d,
1538             FATDirEntry::UnInit => {
1539                 kerror!("FATFS: param: Inode_type uninitialized.");
1540                 return Err(-(EROFS as i32));
1541             }
1542         };
1543         // 检查文件是否存在
1544         dir.check_existence(name, Some(false), guard.fs.upgrade().unwrap())?;
1545 
1546         // 再从磁盘删除
1547         let r = dir.remove(guard.fs.upgrade().unwrap().clone(), name, true);
1548         drop(target_guard);
1549         return r;
1550     }
1551 
1552     fn rmdir(&self, name: &str) -> Result<(), i32> {
1553         let mut guard: SpinLockGuard<FATInode> = self.0.lock();
1554         let target: Arc<LockedFATInode> = guard.find(name)?;
1555         // 对目标inode上锁,以防更改
1556         let target_guard: SpinLockGuard<FATInode> = target.0.lock();
1557         // 先从缓存删除
1558         guard.children.remove(&name.to_uppercase());
1559 
1560         let dir = match &guard.inode_type {
1561             FATDirEntry::File(_) | FATDirEntry::VolId(_) => {
1562                 return Err(-(ENOTDIR as i32));
1563             }
1564             FATDirEntry::Dir(d) => d,
1565             FATDirEntry::UnInit => {
1566                 kerror!("FATFS: param: Inode_type uninitialized.");
1567                 return Err(-(EROFS as i32));
1568             }
1569         };
1570         // 检查文件夹是否存在
1571         dir.check_existence(name, Some(true), guard.fs.upgrade().unwrap())?;
1572 
1573         // 再从磁盘删除
1574         let r: Result<(), i32> = dir.remove(guard.fs.upgrade().unwrap().clone(), name, true);
1575         if r.is_ok() {
1576             return r;
1577         } else {
1578             let r = r.unwrap_err();
1579             if r == -(ENOTEMPTY as i32) {
1580                 // 如果要删除的是目录,且不为空,则删除动作未发生,重新加入缓存
1581                 guard.children.insert(name.to_uppercase(), target.clone());
1582                 drop(target_guard);
1583             }
1584             return Err(r);
1585         }
1586     }
1587 
1588     fn get_entry_name(&self, ino: InodeId) -> Result<String, i32> {
1589         let guard: SpinLockGuard<FATInode> = self.0.lock();
1590         if guard.metadata.file_type != FileType::Dir {
1591             return Err(-(ENOTDIR as i32));
1592         }
1593         match ino {
1594             0 => {
1595                 return Ok(String::from("."));
1596             }
1597             1 => {
1598                 return Ok(String::from(".."));
1599             }
1600             ino => {
1601                 // 暴力遍历所有的children,判断inode id是否相同
1602                 // TODO: 优化这里,这个地方性能很差!
1603                 let mut key: Vec<String> = guard
1604                     .children
1605                     .keys()
1606                     .filter(|k| guard.children.get(*k).unwrap().metadata().unwrap().inode_id == ino)
1607                     .cloned()
1608                     .collect();
1609 
1610                 match key.len() {
1611                     0=>{return Err(-(ENOENT as i32));}
1612                     1=>{return Ok(key.remove(0));}
1613                     _ => panic!("FatFS get_entry_name: key.len()={key_len}>1, current inode_id={inode_id}, to find={to_find}", key_len=key.len(), inode_id = guard.metadata.inode_id, to_find=ino)
1614                 }
1615             }
1616         }
1617     }
1618 }
1619 
1620 impl Default for FATFsInfo {
1621     fn default() -> Self {
1622         return FATFsInfo {
1623             lead_sig: FATFsInfo::LEAD_SIG,
1624             struc_sig: FATFsInfo::STRUC_SIG,
1625             free_count: 0xFFFFFFFF,
1626             next_free: RESERVED_CLUSTERS,
1627             trail_sig: FATFsInfo::TRAIL_SIG,
1628             dirty: false,
1629             offset: None,
1630         };
1631     }
1632 }
1633 
1634 impl Cluster {
1635     pub fn new(cluster: u64) -> Self {
1636         return Cluster {
1637             cluster_num: cluster,
1638             parent_cluster: 0,
1639         };
1640     }
1641 }
1642 
1643 /// @brief 用于迭代FAT表的内容的簇迭代器对象
1644 #[derive(Debug)]
1645 struct ClusterIter<'a> {
1646     /// 迭代器的next要返回的簇
1647     current_cluster: Option<Cluster>,
1648     /// 属于的文件系统
1649     fs: &'a FATFileSystem,
1650 }
1651 
1652 impl<'a> Iterator for ClusterIter<'a> {
1653     type Item = Cluster;
1654 
1655     fn next(&mut self) -> Option<Self::Item> {
1656         // 当前要返回的簇
1657         let ret: Option<Cluster> = self.current_cluster;
1658 
1659         // 获得下一个要返回簇
1660         let new: Option<Cluster> = match self.current_cluster {
1661             Some(c) => {
1662                 let entry: Option<FATEntry> = self.fs.get_fat_entry(c).ok();
1663                 match entry {
1664                     Some(FATEntry::Next(c)) => Some(c),
1665                     _ => None,
1666                 }
1667             }
1668             _ => None,
1669         };
1670 
1671         self.current_cluster = new;
1672         return ret;
1673     }
1674 }
1675