Skip to content

Commit 70dc263

Browse files
zyfjeffbergwolf
authored andcommitted
implement stable unique inode for passthroughfs
In the current passthroughfs implementation, temporary inodes are allocated and then stored in memory, But a FORGET request causes the inode to be removed from memory, new anodes are reassigned, resulting in the instability of the inodes of a file. this PR implements a stable inode, Limited by the current implementation limitations of VFS, Host inode + mnt + dev needs to be controlled in 56bit, and it is not supported beyond the range. Signed-off-by: zyfjeff <[email protected]>
1 parent 2d286b2 commit 70dc263

File tree

3 files changed

+422
-17
lines changed

3 files changed

+422
-17
lines changed

src/passthrough/inode_store.rs

Lines changed: 14 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,15 @@ impl InodeStore {
2323
self.data.insert(data.inode, data);
2424
}
2525

26-
pub fn remove(&mut self, inode: &Inode) -> Option<Arc<InodeData>> {
26+
pub fn remove(&mut self, inode: &Inode, remove_data_only: bool) -> Option<Arc<InodeData>> {
2727
let data = self.data.remove(inode);
28+
if remove_data_only {
29+
// Don't remove by_ids and by_handle, we need use it to store inode
30+
// record the mapping of inodes using these two structures to ensure
31+
// that the same files always use the same inode
32+
return data;
33+
}
34+
2835
if let Some(data) = data.as_ref() {
2936
if let FileOrHandle::Handle(handle) = &data.file_or_handle {
3037
self.by_handle.remove(handle);
@@ -45,16 +52,13 @@ impl InodeStore {
4552
}
4653

4754
pub fn get_by_ids(&self, ids: &InodeAltKey) -> Option<&Arc<InodeData>> {
48-
// safe to unwrap, inode must be in data map if found by ids, otherwise unwrap on
49-
// corruption.
50-
self.inode_by_ids(ids).map(|inode| self.get(inode).unwrap())
55+
let inode = self.inode_by_ids(ids)?;
56+
self.get(inode)
5157
}
5258

5359
pub fn get_by_handle(&self, handle: &FileHandle) -> Option<&Arc<InodeData>> {
54-
// safe to unwrap, inode must be in data map if found by ids, otherwise unwrap on
55-
// corruption.
56-
self.inode_by_handle(handle)
57-
.map(|inode| self.get(inode).unwrap())
60+
let inode = self.inode_by_handle(handle)?;
61+
self.get(inode)
5862
}
5963

6064
pub fn inode_by_ids(&self, ids: &InodeAltKey) -> Option<&Inode> {
@@ -176,10 +180,10 @@ mod test {
176180
assert_eq!(m.get_by_ids(&ids2).unwrap(), &data2);
177181

178182
// remove non-present key
179-
assert!(m.remove(&1).is_none());
183+
assert!(m.remove(&1, false).is_none());
180184

181185
// remove present key, return its value
182-
assert_eq!(m.remove(&inode1).unwrap(), data1.clone());
186+
assert_eq!(m.remove(&inode1, false).unwrap(), data1.clone());
183187
assert!(m.get(&inode1).is_none());
184188
assert!(m.get_by_ids(&ids1).is_none());
185189
assert_eq!(m.get(&inode2).unwrap(), &data2);

0 commit comments

Comments
 (0)