Cache free clusters count

This commit is contained in:
Rafał Harabień 2018-05-28 00:03:42 +02:00
parent 945612f042
commit b4be13823c

View File

@ -272,6 +272,11 @@ impl FsInfoSector {
self.next_free_cluster = Some(cluster); self.next_free_cluster = Some(cluster);
self.dirty = true; self.dirty = true;
} }
fn set_free_cluster_count(&mut self, free_cluster_count: u32) {
self.free_cluster_count = Some(free_cluster_count);
self.dirty = true;
}
} }
/// FAT filesystem options. /// FAT filesystem options.
@ -493,12 +498,10 @@ impl <'a> FileSystem<'a> {
/// For FAT32 volumes number of free clusters from FSInfo sector is returned (may be incorrect). /// For FAT32 volumes number of free clusters from FSInfo sector is returned (may be incorrect).
/// For other filesystems number is computed on each call (scans entire FAT so it takes more time). /// For other filesystems number is computed on each call (scans entire FAT so it takes more time).
pub fn stats(&self) -> io::Result<FileSystemStats> { pub fn stats(&self) -> io::Result<FileSystemStats> {
let free_clusters = match self.fs_info.borrow().free_cluster_count { let free_clusters_option = self.fs_info.borrow().free_cluster_count;
let free_clusters = match free_clusters_option {
Some(n) => n, Some(n) => n,
_ => { _ => self.recalc_free_clusters()?,
let mut fat = self.fat_slice();
count_free_clusters(&mut fat, self.fat_type, self.total_clusters)?
}
}; };
Ok(FileSystemStats { Ok(FileSystemStats {
cluster_size: self.cluster_size(), cluster_size: self.cluster_size(),
@ -507,6 +510,14 @@ impl <'a> FileSystem<'a> {
}) })
} }
// Forces free clusters recalculation
fn recalc_free_clusters(&self) -> io::Result<u32> {
let mut fat = self.fat_slice();
let free_cluster_count = count_free_clusters(&mut fat, self.fat_type, self.total_clusters)?;
self.fs_info.borrow_mut().set_free_cluster_count(free_cluster_count);
Ok(free_cluster_count)
}
/// Unmounts filesystem. Updates FSInfo sector if required in options. /// Unmounts filesystem. Updates FSInfo sector if required in options.
pub fn unmount(self) -> io::Result<()> { pub fn unmount(self) -> io::Result<()> {
self.unmount_internal() self.unmount_internal()