summaryrefslogtreecommitdiff
path: root/src/loading
diff options
context:
space:
mode:
authorLaurenz <laurmaedje@gmail.com>2021-06-01 12:46:01 +0200
committerLaurenz <laurmaedje@gmail.com>2021-06-01 12:55:07 +0200
commit7218892c722ca583297c0ebbda350bdf6f16d3ce (patch)
tree27ebbfaf0662c1e0dd01e7c5e9e360ab288cae4d /src/loading
parent9bdb0bdeffa5e4b6da9e3f6d3c1b79c506005fc5 (diff)
Refactor path handling
Diffstat (limited to 'src/loading')
-rw-r--r--src/loading/fs.rs44
-rw-r--r--src/loading/mod.rs14
2 files changed, 30 insertions, 28 deletions
diff --git a/src/loading/fs.rs b/src/loading/fs.rs
index ac3f3706..7fa1c120 100644
--- a/src/loading/fs.rs
+++ b/src/loading/fs.rs
@@ -24,8 +24,7 @@ pub struct FsLoader {
cache: FileCache,
}
-/// Maps from paths to loaded file buffers. When the buffer is `None` the file
-/// does not exist or couldn't be read.
+/// Maps from resolved file hashes to loaded file buffers.
type FileCache = HashMap<FileHash, Buffer>;
impl FsLoader {
@@ -169,38 +168,29 @@ impl Loader for FsLoader {
}
fn load_face(&mut self, idx: usize) -> Option<Buffer> {
- load(&mut self.cache, &self.files[idx])
+ self.load_file(&self.files[idx].clone())
}
fn load_file(&mut self, path: &Path) -> Option<Buffer> {
- load(&mut self.cache, path)
+ let hash = self.resolve(path)?;
+ Some(Rc::clone(match self.cache.entry(hash) {
+ Entry::Occupied(entry) => entry.into_mut(),
+ Entry::Vacant(entry) => {
+ let buffer = std::fs::read(path).ok()?;
+ entry.insert(Rc::new(buffer))
+ }
+ }))
}
fn resolve(&self, path: &Path) -> Option<FileHash> {
- hash(path)
- }
-}
-
-/// Load from the file system using a cache.
-fn load(cache: &mut FileCache, path: &Path) -> Option<Buffer> {
- Some(match cache.entry(hash(path)?) {
- Entry::Occupied(entry) => entry.get().clone(),
- Entry::Vacant(entry) => {
- let buffer = std::fs::read(path).ok()?;
- entry.insert(Rc::new(buffer)).clone()
+ let file = File::open(path).ok()?;
+ let meta = file.metadata().ok()?;
+ if meta.is_file() {
+ let handle = Handle::from_file(file).ok()?;
+ Some(FileHash::from_raw(fxhash::hash64(&handle)))
+ } else {
+ None
}
- })
-}
-
-/// Create a hash that is the same for all paths pointing to the same file.
-fn hash(path: &Path) -> Option<FileHash> {
- let file = File::open(path).ok()?;
- let meta = file.metadata().ok()?;
- if meta.is_file() {
- let handle = Handle::from_file(file).ok()?;
- Some(FileHash(fxhash::hash64(&handle)))
- } else {
- None
}
}
diff --git a/src/loading/mod.rs b/src/loading/mod.rs
index f57b5c73..0e171796 100644
--- a/src/loading/mod.rs
+++ b/src/loading/mod.rs
@@ -36,7 +36,19 @@ pub trait Loader {
///
/// Should be the same for all paths pointing to the same file.
#[derive(Debug, Copy, Clone, Eq, PartialEq, Hash)]
-pub struct FileHash(pub u64);
+pub struct FileHash(u64);
+
+impl FileHash {
+ /// Create an file hash from a raw hash value.
+ pub fn from_raw(v: u64) -> Self {
+ Self(v)
+ }
+
+ /// Convert into the raw underlying hash value.
+ pub fn into_raw(self) -> u64 {
+ self.0
+ }
+}
/// A loader which serves nothing.
pub struct BlankLoader;