From 5e506f4c591075d25792807e95977b775a07c2de Mon Sep 17 00:00:00 2001 From: Yan Song Date: Mon, 4 Sep 2023 09:55:14 +0000 Subject: [PATCH] storage: fix chunk map compatibility The blob cache file of nydusd v2.2 and <=v2.1 are in different formats, which are not compatible. Should use different chunk map files for them, in order to upgrade or downgrade smoothly. For the nydusd <=v2.1, the files in blob cache directory: ``` $blob_id $blob_id.chunk_map ``` For the nydusd =v2.2, the files in blob cache directory: ``` $blob_id.blob.data $blob_id.chunk_map ``` NOTE: nydusd (v2.2) maybe use the chunk map file of nydusd(<=v2.1), it will cause the corrupted blob cache data to be read. For the nydusd of current patch, the files in blob cache directory: ``` $blob_id.blob.data $blob_id.blob.data.chunk_map ``` NOTE: this will discard the old blob cache data and chunk map files. Signed-off-by: Yan Song --- storage/src/cache/filecache/mod.rs | 11 +++++++---- storage/src/cache/fscache/mod.rs | 6 ++++-- storage/src/cache/state/indexed_chunk_map.rs | 10 +--------- utils/src/metrics.rs | 2 ++ 4 files changed, 14 insertions(+), 15 deletions(-) diff --git a/storage/src/cache/filecache/mod.rs b/storage/src/cache/filecache/mod.rs index 31a7f3c9c47..6cfed8b34b1 100644 --- a/storage/src/cache/filecache/mod.rs +++ b/storage/src/cache/filecache/mod.rs @@ -25,6 +25,9 @@ use crate::cache::{BlobCache, BlobCacheMgr}; use crate::device::{BlobFeatures, BlobInfo}; use crate::RAFS_DEFAULT_CHUNK_SIZE; +pub const BLOB_RAW_FILE_SUFFIX: &str = ".blob.raw"; +pub const BLOB_DATA_FILE_SUFFIX: &str = ".blob.data"; + /// An implementation of [BlobCacheMgr](../trait.BlobCacheMgr.html) to improve performance by /// caching uncompressed blob with local storage. #[derive(Clone)] @@ -107,7 +110,7 @@ impl FileCacheMgr { .underlying_files .lock() .unwrap() - .insert(blob_id); + .insert(blob_id + BLOB_DATA_FILE_SUFFIX); Ok(entry) } } @@ -236,9 +239,9 @@ impl FileCacheEntry { && !is_legacy_stargz; // Set cache file to its expected size. let suffix = if mgr.cache_raw_data { - ".blob.raw" + BLOB_RAW_FILE_SUFFIX } else { - ".blob.data" + BLOB_DATA_FILE_SUFFIX }; let blob_data_file_path = blob_file_path.clone() + suffix; let file = OpenOptions::new() @@ -358,7 +361,7 @@ impl FileCacheEntry { Arc::new(BlobStateMap::from(DigestedChunkMap::new())) } else { Arc::new(BlobStateMap::from(IndexedChunkMap::new( - blob_file, + &format!("{}{}", blob_file, BLOB_DATA_FILE_SUFFIX), blob_info.chunk_count(), true, )?)) diff --git a/storage/src/cache/fscache/mod.rs b/storage/src/cache/fscache/mod.rs index 081a3e00465..cf624f4f427 100644 --- a/storage/src/cache/fscache/mod.rs +++ b/storage/src/cache/fscache/mod.rs @@ -22,6 +22,8 @@ use crate::device::{BlobFeatures, BlobInfo, BlobObject}; use crate::factory::BLOB_FACTORY; use crate::RAFS_DEFAULT_CHUNK_SIZE; +use crate::cache::filecache::BLOB_DATA_FILE_SUFFIX; + const FSCACHE_BLOBS_CHECK_NUM: u8 = 1; /// An implementation of [BlobCacheMgr](../trait.BlobCacheMgr.html) to improve performance by @@ -104,7 +106,7 @@ impl FsCacheMgr { .underlying_files .lock() .unwrap() - .insert(blob_id); + .insert(blob_id + BLOB_DATA_FILE_SUFFIX); Ok(entry) } } @@ -256,7 +258,7 @@ impl FileCacheEntry { }; let chunk_map = Arc::new(BlobStateMap::from(IndexedChunkMap::new( - &blob_file_path, + &format!("{}{}", blob_file_path, BLOB_DATA_FILE_SUFFIX), blob_info.chunk_count(), false, )?)); diff --git a/storage/src/cache/state/indexed_chunk_map.rs b/storage/src/cache/state/indexed_chunk_map.rs index 0ee25bb5a1c..ff5808cdac5 100644 --- a/storage/src/cache/state/indexed_chunk_map.rs +++ b/storage/src/cache/state/indexed_chunk_map.rs @@ -12,7 +12,7 @@ use std::io::Result; use crate::cache::state::persist_map::PersistMap; use crate::cache::state::{ChunkIndexGetter, ChunkMap, RangeMap}; -use crate::device::{BlobChunkInfo, BlobInfo}; +use crate::device::BlobChunkInfo; /// The name suffix of blob chunk_map file, named $blob_id.chunk_map. const FILE_SUFFIX: &str = "chunk_map"; @@ -39,14 +39,6 @@ impl IndexedChunkMap { PersistMap::open(&filename, chunk_count, true, persist).map(|map| IndexedChunkMap { map }) } - - /// Create a new instance of `IndexedChunkMap` from an existing chunk map file. - pub fn open(blob_info: &BlobInfo, workdir: &str) -> Result { - let filename = format!("{}/{}.{}", workdir, blob_info.blob_id(), FILE_SUFFIX); - - PersistMap::open(&filename, blob_info.chunk_count(), false, true) - .map(|map| IndexedChunkMap { map }) - } } impl ChunkMap for IndexedChunkMap { diff --git a/utils/src/metrics.rs b/utils/src/metrics.rs index 7c216f0c75c..f5321d98aa3 100644 --- a/utils/src/metrics.rs +++ b/utils/src/metrics.rs @@ -714,6 +714,8 @@ pub struct BlobcacheMetrics { id: String, // Prefer to let external tool get file's state like file size and disk usage. // Because stat(2) file may get blocked. + // It should include the real blob cache file names, so that the external GC + // process can handle it directly. pub underlying_files: Mutex>, pub store_path: String, // Cache hit percentage = (partial_hits + whole_hits) / total