From d10c618065813e07854671cf0a85f92f8cb13738 Mon Sep 17 00:00:00 2001 From: Robert Baldyga Date: Thu, 29 Aug 2019 10:22:38 +0200 Subject: [PATCH] Move parts metadata to separate section Fix problem introduced by increasing partition name size to 1024 bytes, which effectively made superblock bigger than one page. Due to this flushing superblock required more than one io, which in case of dirty shutdown between these ios resulted in CRC missmatch and made cache recovery impossible. Moving parts metadata to separate sections makes superblock fitting in one page, effectively solving described problem. Signed-off-by: Robert Baldyga --- src/metadata/metadata_hash.c | 39 ++++++++++++++++++++++++++++-- src/metadata/metadata_hash.h | 2 ++ src/metadata/metadata_superblock.h | 4 --- src/mngt/ocf_mngt_cache.c | 14 +---------- 4 files changed, 40 insertions(+), 19 deletions(-) diff --git a/src/metadata/metadata_hash.c b/src/metadata/metadata_hash.c index d908f30..0fb669c 100644 --- a/src/metadata/metadata_hash.c +++ b/src/metadata/metadata_hash.c @@ -96,6 +96,12 @@ static ocf_cache_line_t ocf_metadata_hash_get_entries( case metadata_segment_reserved: return 32; + case metadata_segment_part_config: + return OCF_IO_CLASS_MAX + 1; + + case metadata_segment_part_runtime: + return OCF_IO_CLASS_MAX + 1; + case metadata_segment_core_config: return OCF_CORE_MAX; @@ -154,6 +160,14 @@ static int64_t ocf_metadata_hash_get_element_size( size = PAGE_SIZE; break; + case metadata_segment_part_config: + size = sizeof(struct ocf_user_part_config); + break; + + case metadata_segment_part_runtime: + size = sizeof(struct ocf_user_part_runtime); + break; + case metadata_segment_hash: size = sizeof(ocf_cache_line_t); break; @@ -318,6 +332,8 @@ static const char * const ocf_metadata_hash_raw_names[] = { [metadata_segment_sb_config] = "Super block config", [metadata_segment_sb_runtime] = "Super block runtime", [metadata_segment_reserved] = "Reserved", + [metadata_segment_part_config] = "Part config", + [metadata_segment_part_runtime] = "Part runtime", [metadata_segment_cleaning] = "Cleaning", [metadata_segment_eviction] = "Eviction", [metadata_segment_collision] = "Collision", @@ -504,6 +520,8 @@ int ocf_metadata_hash_init(struct ocf_cache *cache, (struct ocf_cache_line_settings *)&metadata->settings; struct ocf_core_meta_config *core_meta_config; struct ocf_core_meta_runtime *core_meta_runtime; + struct ocf_user_part_config *part_config; + struct ocf_user_part_runtime *part_runtime; ocf_core_t core; ocf_core_id_t core_id; uint32_t i = 0; @@ -531,8 +549,16 @@ int ocf_metadata_hash_init(struct ocf_cache *cache, return result; } - cache->conf_meta = METADATA_MEM_POOL(ctrl, - metadata_segment_sb_config); + cache->conf_meta = METADATA_MEM_POOL(ctrl, metadata_segment_sb_config); + + /* Set partition metadata */ + part_config = METADATA_MEM_POOL(ctrl, metadata_segment_part_config); + part_runtime = METADATA_MEM_POOL(ctrl, metadata_segment_part_runtime); + + for (i = 0; i < OCF_IO_CLASS_MAX + 1; i++) { + cache->user_parts[i].config = &part_config[i]; + cache->user_parts[i].runtime = &part_runtime[i]; + } /* Set core metadata */ core_meta_config = METADATA_MEM_POOL(ctrl, @@ -1326,6 +1352,8 @@ static void ocf_metadata_hash_load_superblock_finish(ocf_pipeline_t pipeline, struct ocf_pipeline_arg ocf_metadata_hash_load_sb_store_segment_args[] = { OCF_PL_ARG_INT(metadata_segment_sb_config), OCF_PL_ARG_INT(metadata_segment_sb_runtime), + OCF_PL_ARG_INT(metadata_segment_part_config), + OCF_PL_ARG_INT(metadata_segment_part_runtime), OCF_PL_ARG_INT(metadata_segment_core_config), OCF_PL_ARG_TERMINATOR(), }; @@ -1333,6 +1361,8 @@ struct ocf_pipeline_arg ocf_metadata_hash_load_sb_store_segment_args[] = { struct ocf_pipeline_arg ocf_metadata_hash_load_sb_load_segment_args[] = { OCF_PL_ARG_INT(metadata_segment_sb_config), OCF_PL_ARG_INT(metadata_segment_sb_runtime), + OCF_PL_ARG_INT(metadata_segment_part_config), + OCF_PL_ARG_INT(metadata_segment_part_runtime), OCF_PL_ARG_INT(metadata_segment_core_config), OCF_PL_ARG_INT(metadata_segment_core_uuid), OCF_PL_ARG_TERMINATOR(), @@ -1340,6 +1370,8 @@ struct ocf_pipeline_arg ocf_metadata_hash_load_sb_load_segment_args[] = { struct ocf_pipeline_arg ocf_metadata_hash_load_sb_check_crc_args[] = { OCF_PL_ARG_INT(metadata_segment_sb_runtime), + OCF_PL_ARG_INT(metadata_segment_part_config), + OCF_PL_ARG_INT(metadata_segment_part_runtime), OCF_PL_ARG_INT(metadata_segment_core_config), OCF_PL_ARG_INT(metadata_segment_core_uuid), OCF_PL_ARG_TERMINATOR(), @@ -1481,6 +1513,7 @@ static void ocf_metadata_hash_flush_superblock_finish(ocf_pipeline_t pipeline, } struct ocf_pipeline_arg ocf_metadata_hash_flush_sb_calculate_crc_args[] = { + OCF_PL_ARG_INT(metadata_segment_part_config), OCF_PL_ARG_INT(metadata_segment_core_config), OCF_PL_ARG_INT(metadata_segment_core_uuid), OCF_PL_ARG_TERMINATOR(), @@ -1488,6 +1521,7 @@ struct ocf_pipeline_arg ocf_metadata_hash_flush_sb_calculate_crc_args[] = { struct ocf_pipeline_arg ocf_metadata_hash_flush_sb_flush_segment_args[] = { OCF_PL_ARG_INT(metadata_segment_sb_config), + OCF_PL_ARG_INT(metadata_segment_part_config), OCF_PL_ARG_INT(metadata_segment_core_config), OCF_PL_ARG_INT(metadata_segment_core_uuid), OCF_PL_ARG_TERMINATOR(), @@ -1631,6 +1665,7 @@ out: struct ocf_pipeline_arg ocf_metadata_hash_flush_all_args[] = { OCF_PL_ARG_INT(metadata_segment_sb_runtime), + OCF_PL_ARG_INT(metadata_segment_part_runtime), OCF_PL_ARG_INT(metadata_segment_core_runtime), OCF_PL_ARG_INT(metadata_segment_cleaning), OCF_PL_ARG_INT(metadata_segment_eviction), diff --git a/src/metadata/metadata_hash.h b/src/metadata/metadata_hash.h index 82cdf5e..b19f3a9 100644 --- a/src/metadata/metadata_hash.h +++ b/src/metadata/metadata_hash.h @@ -19,6 +19,8 @@ enum ocf_metadata_segment { metadata_segment_sb_config = 0, /*!< Super block conf */ metadata_segment_sb_runtime, /*!< Super block runtime */ metadata_segment_reserved, /*!< Reserved space on disk */ + metadata_segment_part_config, /*!< Part Config Metadata */ + metadata_segment_part_runtime, /*!< Part Runtime Metadata */ metadata_segment_core_config, /*!< Core Config Metadata */ metadata_segment_core_runtime, /*!< Core Runtime Metadata */ metadata_segment_core_uuid, /*!< Core UUID */ diff --git a/src/metadata/metadata_superblock.h b/src/metadata/metadata_superblock.h index c1fd9c6..0baa76f 100644 --- a/src/metadata/metadata_superblock.h +++ b/src/metadata/metadata_superblock.h @@ -48,8 +48,6 @@ struct ocf_superblock_config { /* Current core sequence number */ ocf_core_id_t curr_core_seq_no; - struct ocf_user_part_config user_parts[OCF_IO_CLASS_MAX + 1]; - /* * Checksum for each metadata region. * This field has to be the last one! @@ -63,8 +61,6 @@ struct ocf_superblock_config { struct ocf_superblock_runtime { struct ocf_part freelist_part; - struct ocf_user_part_runtime user_parts[OCF_IO_CLASS_MAX + 1]; - uint32_t cleaning_thread_access; }; diff --git a/src/mngt/ocf_mngt_cache.c b/src/mngt/ocf_mngt_cache.c index 1f4cd51..ecc638d 100644 --- a/src/mngt/ocf_mngt_cache.c +++ b/src/mngt/ocf_mngt_cache.c @@ -958,7 +958,7 @@ static void _ocf_mngt_attach_prepare_metadata(ocf_pipeline_t pipeline, { struct ocf_cache_attach_context *context = priv; ocf_cache_t cache = context->cache; - int ret, i; + int ret; if (context->init_mode == ocf_init_mode_load && context->metadata.status) { @@ -986,11 +986,6 @@ static void _ocf_mngt_attach_prepare_metadata(ocf_pipeline_t pipeline, } - for (i = 0; i < OCF_IO_CLASS_MAX + 1; ++i) { - cache->user_parts[i].runtime = - &cache->device->runtime_meta->user_parts[i]; - } - cache->device->freelist_part = &cache->device->runtime_meta->freelist_part; ret = ocf_concurrency_init(cache); @@ -1158,8 +1153,6 @@ static void _ocf_mngt_attach_handle_error( static void _ocf_mngt_cache_init(ocf_cache_t cache, struct ocf_cache_mngt_init_params *params) { - int i; - /* * Super block elements initialization */ @@ -1168,11 +1161,6 @@ static void _ocf_mngt_cache_init(ocf_cache_t cache, cache->conf_meta->promotion_policy_type = params->metadata.promotion_policy; - for (i = 0; i < OCF_IO_CLASS_MAX + 1; ++i) { - cache->user_parts[i].config = - &cache->conf_meta->user_parts[i]; - } - INIT_LIST_HEAD(&cache->io_queues); /* Init Partitions */