17ff28519SKozlowski Mateusz /* SPDX-License-Identifier: BSD-3-Clause 217cf101bSMateusz Kozlowski * Copyright 2023 Solidigm All Rights Reserved 3a6dbe372Spaul luse * Copyright (C) 2022 Intel Corporation. 47ff28519SKozlowski Mateusz * All rights reserved. 57ff28519SKozlowski Mateusz */ 67ff28519SKozlowski Mateusz 7f34b13ecSNathan Claudel #include "spdk/assert.h" 8f34b13ecSNathan Claudel 97ff28519SKozlowski Mateusz #include "ftl_layout_upgrade.h" 107ff28519SKozlowski Mateusz #include "ftl_layout.h" 117ff28519SKozlowski Mateusz #include "ftl_sb_current.h" 12c8ab874dSKozlowski Mateusz #include "ftl_sb_prev.h" 137ff28519SKozlowski Mateusz #include "ftl_core.h" 147ff28519SKozlowski Mateusz #include "ftl_band.h" 15a5c04e6dSMateusz Kozlowski #include "utils/ftl_layout_tracker_bdev.h" 16a5c04e6dSMateusz Kozlowski 17a5c04e6dSMateusz Kozlowski int 18a5c04e6dSMateusz Kozlowski ftl_region_major_upgrade_enabled(struct spdk_ftl_dev *dev, struct ftl_layout_region *region) 19a5c04e6dSMateusz Kozlowski { 20a5c04e6dSMateusz Kozlowski if (ftl_region_upgrade_enabled(dev, region)) { 21a5c04e6dSMateusz Kozlowski return -1; 22a5c04e6dSMateusz Kozlowski } 23a5c04e6dSMateusz Kozlowski 24a5c04e6dSMateusz Kozlowski if (dev->sb->upgrade_ready) { 25a5c04e6dSMateusz Kozlowski return 0; 26a5c04e6dSMateusz Kozlowski } else { 27a5c04e6dSMateusz Kozlowski FTL_ERRLOG(dev, "FTL major upgrade ERROR, required upgrade shutdown in the previous version\n"); 28a5c04e6dSMateusz Kozlowski return -1; 29a5c04e6dSMateusz Kozlowski } 30a5c04e6dSMateusz Kozlowski } 317ff28519SKozlowski Mateusz 327ff28519SKozlowski Mateusz int 337ff28519SKozlowski Mateusz ftl_region_upgrade_disabled(struct spdk_ftl_dev *dev, struct ftl_layout_region *region) 347ff28519SKozlowski Mateusz { 357ff28519SKozlowski Mateusz return -1; 367ff28519SKozlowski Mateusz } 377ff28519SKozlowski Mateusz 387ff28519SKozlowski Mateusz int 397ff28519SKozlowski Mateusz ftl_region_upgrade_enabled(struct spdk_ftl_dev *dev, struct ftl_layout_region *region) 407ff28519SKozlowski Mateusz { 417ff28519SKozlowski Mateusz if (!(dev->sb->clean == 1 && dev->sb_shm->shm_clean == 0)) { 427ff28519SKozlowski Mateusz FTL_ERRLOG(dev, "FTL region upgrade: SB dirty\n"); 437ff28519SKozlowski Mateusz return -1; 447ff28519SKozlowski Mateusz } 457ff28519SKozlowski Mateusz return 0; 467ff28519SKozlowski Mateusz } 477ff28519SKozlowski Mateusz 487ff28519SKozlowski Mateusz #ifndef UTEST 497ff28519SKozlowski Mateusz extern struct ftl_region_upgrade_desc sb_upgrade_desc[]; 507ff28519SKozlowski Mateusz extern struct ftl_region_upgrade_desc p2l_upgrade_desc[]; 517ff28519SKozlowski Mateusz extern struct ftl_region_upgrade_desc nvc_upgrade_desc[]; 527ff28519SKozlowski Mateusz extern struct ftl_region_upgrade_desc band_upgrade_desc[]; 532d613454SMateusz Kozlowski extern struct ftl_region_upgrade_desc trim_log_upgrade_desc[]; 547ff28519SKozlowski Mateusz 557ff28519SKozlowski Mateusz static struct ftl_layout_upgrade_desc_list layout_upgrade_desc[] = { 56c8ab874dSKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_SB] = { 578fc78fd8SMateusz Kozlowski .latest_ver = FTL_SB_VERSION_CURRENT, 58c8ab874dSKozlowski Mateusz .count = FTL_SB_VERSION_CURRENT, 59c8ab874dSKozlowski Mateusz .desc = sb_upgrade_desc, 60c8ab874dSKozlowski Mateusz }, 61c8ab874dSKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_SB_BASE] = { 628fc78fd8SMateusz Kozlowski .latest_ver = FTL_SB_VERSION_CURRENT, 63c8ab874dSKozlowski Mateusz .count = FTL_SB_VERSION_CURRENT, 64c8ab874dSKozlowski Mateusz .desc = sb_upgrade_desc, 65c8ab874dSKozlowski Mateusz }, 667ff28519SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_L2P] = {}, 678c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_BAND_MD] = { 688fc78fd8SMateusz Kozlowski .latest_ver = FTL_BAND_VERSION_CURRENT, 698c41c403SKozlowski Mateusz .count = FTL_BAND_VERSION_CURRENT, 708c41c403SKozlowski Mateusz .desc = band_upgrade_desc, 718c41c403SKozlowski Mateusz }, 728c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_BAND_MD_MIRROR] = { 738fc78fd8SMateusz Kozlowski .latest_ver = FTL_BAND_VERSION_CURRENT, 748c41c403SKozlowski Mateusz .count = FTL_BAND_VERSION_CURRENT, 758c41c403SKozlowski Mateusz .desc = band_upgrade_desc, 768c41c403SKozlowski Mateusz }, 777ff28519SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_VALID_MAP] = {}, 788c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_NVC_MD] = { 798fc78fd8SMateusz Kozlowski .latest_ver = FTL_NVC_VERSION_CURRENT, 808c41c403SKozlowski Mateusz .count = FTL_NVC_VERSION_CURRENT, 818c41c403SKozlowski Mateusz .desc = nvc_upgrade_desc, 828c41c403SKozlowski Mateusz }, 838c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_NVC_MD_MIRROR] = { 848fc78fd8SMateusz Kozlowski .latest_ver = FTL_NVC_VERSION_CURRENT, 858c41c403SKozlowski Mateusz .count = FTL_NVC_VERSION_CURRENT, 868c41c403SKozlowski Mateusz .desc = nvc_upgrade_desc, 878c41c403SKozlowski Mateusz }, 887ff28519SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_DATA_NVC] = {}, 897ff28519SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_DATA_BASE] = {}, 908c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_P2L_CKPT_GC] = { 918fc78fd8SMateusz Kozlowski .latest_ver = FTL_P2L_VERSION_CURRENT, 928c41c403SKozlowski Mateusz .count = FTL_P2L_VERSION_CURRENT, 938c41c403SKozlowski Mateusz .desc = p2l_upgrade_desc, 948c41c403SKozlowski Mateusz }, 958c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_P2L_CKPT_GC_NEXT] = { 968fc78fd8SMateusz Kozlowski .latest_ver = FTL_P2L_VERSION_CURRENT, 978c41c403SKozlowski Mateusz .count = FTL_P2L_VERSION_CURRENT, 988c41c403SKozlowski Mateusz .desc = p2l_upgrade_desc, 998c41c403SKozlowski Mateusz }, 1008c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_P2L_CKPT_COMP] = { 1018fc78fd8SMateusz Kozlowski .latest_ver = FTL_P2L_VERSION_CURRENT, 1028c41c403SKozlowski Mateusz .count = FTL_P2L_VERSION_CURRENT, 1038c41c403SKozlowski Mateusz .desc = p2l_upgrade_desc, 1048c41c403SKozlowski Mateusz }, 1058c41c403SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_P2L_CKPT_COMP_NEXT] = { 1068fc78fd8SMateusz Kozlowski .latest_ver = FTL_P2L_VERSION_CURRENT, 1078c41c403SKozlowski Mateusz .count = FTL_P2L_VERSION_CURRENT, 1088c41c403SKozlowski Mateusz .desc = p2l_upgrade_desc, 1098c41c403SKozlowski Mateusz }, 1107ff28519SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_TRIM_MD] = {}, 1117ff28519SKozlowski Mateusz [FTL_LAYOUT_REGION_TYPE_TRIM_MD_MIRROR] = {}, 1122d613454SMateusz Kozlowski [FTL_LAYOUT_REGION_TYPE_TRIM_LOG] = { 1132d613454SMateusz Kozlowski .latest_ver = FTL_TRIM_LOG_VERSION_CURRENT, 1142d613454SMateusz Kozlowski .count = FTL_TRIM_LOG_VERSION_CURRENT, 1152d613454SMateusz Kozlowski .desc = trim_log_upgrade_desc, 1162d613454SMateusz Kozlowski }, 1172d613454SMateusz Kozlowski [FTL_LAYOUT_REGION_TYPE_TRIM_LOG_MIRROR] = { 1182d613454SMateusz Kozlowski .latest_ver = FTL_TRIM_LOG_VERSION_CURRENT, 1192d613454SMateusz Kozlowski .count = FTL_TRIM_LOG_VERSION_CURRENT, 1202d613454SMateusz Kozlowski .desc = trim_log_upgrade_desc, 1212d613454SMateusz Kozlowski }, 122*6d6179ffSMateusz Kozlowski [FTL_LAYOUT_REGION_TYPE_P2L_LOG_IO_MIN] = {}, 123*6d6179ffSMateusz Kozlowski [FTL_LAYOUT_REGION_TYPE_P2L_LOG_IO_MAX] = {}, 1247ff28519SKozlowski Mateusz }; 1257ff28519SKozlowski Mateusz 1267ff28519SKozlowski Mateusz SPDK_STATIC_ASSERT(sizeof(layout_upgrade_desc) / sizeof(*layout_upgrade_desc) == 1277ff28519SKozlowski Mateusz FTL_LAYOUT_REGION_TYPE_MAX, 1287ff28519SKozlowski Mateusz "Missing layout upgrade descriptors"); 1297ff28519SKozlowski Mateusz #endif 1307ff28519SKozlowski Mateusz 1315555d51cSLukasz Lasek uint64_t 1325555d51cSLukasz Lasek ftl_layout_upgrade_get_latest_version(enum ftl_layout_region_type reg_type) 1335555d51cSLukasz Lasek { 1345555d51cSLukasz Lasek assert(reg_type < FTL_LAYOUT_REGION_TYPE_MAX); 1355555d51cSLukasz Lasek return layout_upgrade_desc[reg_type].latest_ver; 1365555d51cSLukasz Lasek } 1375555d51cSLukasz Lasek 1387ff28519SKozlowski Mateusz static int 1397ff28519SKozlowski Mateusz region_verify(struct spdk_ftl_dev *dev, struct ftl_layout_upgrade_ctx *ctx) 1407ff28519SKozlowski Mateusz { 1417ff28519SKozlowski Mateusz uint64_t ver; 1427ff28519SKozlowski Mateusz 1437ff28519SKozlowski Mateusz assert(ctx->reg); 1448fc78fd8SMateusz Kozlowski ver = ctx->reg->current.version; 1458fc78fd8SMateusz Kozlowski if (ver > ctx->upgrade->latest_ver) { 1467ff28519SKozlowski Mateusz FTL_ERRLOG(dev, "Unknown region version\n"); 1477ff28519SKozlowski Mateusz return -1; 1487ff28519SKozlowski Mateusz } 1497ff28519SKozlowski Mateusz 1508fc78fd8SMateusz Kozlowski while (ver < ctx->upgrade->latest_ver) { 1517ff28519SKozlowski Mateusz int rc = ctx->upgrade->desc[ver].verify(dev, ctx->reg); 1527ff28519SKozlowski Mateusz if (rc) { 1537ff28519SKozlowski Mateusz return rc; 1547ff28519SKozlowski Mateusz } 1558fc78fd8SMateusz Kozlowski ftl_bug(ver > ctx->upgrade->desc[ver].new_version); 1568fc78fd8SMateusz Kozlowski ftl_bug(ctx->upgrade->desc[ver].new_version > ctx->upgrade->latest_ver); 1577ff28519SKozlowski Mateusz ver = ctx->upgrade->desc[ver].new_version; 1587ff28519SKozlowski Mateusz } 1597ff28519SKozlowski Mateusz return 0; 1607ff28519SKozlowski Mateusz } 1617ff28519SKozlowski Mateusz 1627ff28519SKozlowski Mateusz int 1637ff28519SKozlowski Mateusz ftl_region_upgrade(struct spdk_ftl_dev *dev, struct ftl_layout_upgrade_ctx *ctx) 1647ff28519SKozlowski Mateusz { 1657ff28519SKozlowski Mateusz int rc = 0; 1667ff28519SKozlowski Mateusz uint64_t ver; 1677ff28519SKozlowski Mateusz 1687ff28519SKozlowski Mateusz assert(ctx->reg); 1698fc78fd8SMateusz Kozlowski assert(ctx->reg->current.version <= ctx->upgrade->latest_ver); 1708fc78fd8SMateusz Kozlowski ver = ctx->reg->current.version; 1718fc78fd8SMateusz Kozlowski if (ver < ctx->upgrade->latest_ver) { 1727ff28519SKozlowski Mateusz ctx->next_reg_ver = ctx->upgrade->desc[ver].new_version; 1737ff28519SKozlowski Mateusz rc = ctx->upgrade->desc[ver].upgrade(dev, ctx); 1747ff28519SKozlowski Mateusz } 1757ff28519SKozlowski Mateusz return rc; 1767ff28519SKozlowski Mateusz } 1777ff28519SKozlowski Mateusz 1787ff28519SKozlowski Mateusz void 1797ff28519SKozlowski Mateusz ftl_region_upgrade_completed(struct spdk_ftl_dev *dev, struct ftl_layout_upgrade_ctx *ctx, 1808fc78fd8SMateusz Kozlowski uint64_t entry_size, uint64_t num_entries, int status) 1817ff28519SKozlowski Mateusz { 1828fc78fd8SMateusz Kozlowski int rc; 1837ff28519SKozlowski Mateusz 1848fc78fd8SMateusz Kozlowski assert(ctx->reg); 1858fc78fd8SMateusz Kozlowski assert(ctx->reg->current.version < ctx->next_reg_ver); 1868fc78fd8SMateusz Kozlowski assert(ctx->next_reg_ver <= ctx->upgrade->latest_ver); 1878fc78fd8SMateusz Kozlowski 1887ff28519SKozlowski Mateusz if (!status) { 1898fc78fd8SMateusz Kozlowski if (ctx->reg->type != FTL_LAYOUT_REGION_TYPE_SB) { 1908fc78fd8SMateusz Kozlowski /* Superblock region is always default-created in the latest version - see ftl_layout_setup_superblock() */ 1918fc78fd8SMateusz Kozlowski rc = ftl_superblock_md_layout_upgrade_region(dev, ctx->reg, ctx->next_reg_ver); 1928fc78fd8SMateusz Kozlowski if (entry_size && num_entries) { 1938fc78fd8SMateusz Kozlowski dev->layout.region[ctx->reg->type].entry_size = entry_size; 1948fc78fd8SMateusz Kozlowski dev->layout.region[ctx->reg->type].num_entries = num_entries; 1958fc78fd8SMateusz Kozlowski } 1968fc78fd8SMateusz Kozlowski 1977ff28519SKozlowski Mateusz ftl_bug(rc != 0); 1987ff28519SKozlowski Mateusz } 1997ff28519SKozlowski Mateusz 2008fc78fd8SMateusz Kozlowski ctx->reg->current.version = ctx->next_reg_ver; 2017ff28519SKozlowski Mateusz } 2027ff28519SKozlowski Mateusz 2037ff28519SKozlowski Mateusz if (ctx->cb) { 2047ff28519SKozlowski Mateusz ctx->cb(dev, ctx->cb_ctx, status); 2057ff28519SKozlowski Mateusz } 2067ff28519SKozlowski Mateusz } 2077ff28519SKozlowski Mateusz 2087ff28519SKozlowski Mateusz int 2097ff28519SKozlowski Mateusz ftl_layout_verify(struct spdk_ftl_dev *dev) 2107ff28519SKozlowski Mateusz { 2117ff28519SKozlowski Mateusz struct ftl_layout *layout = &dev->layout; 2127ff28519SKozlowski Mateusz struct ftl_layout_upgrade_ctx ctx = {0}; 2138fc78fd8SMateusz Kozlowski enum ftl_layout_region_type reg_type; 2147ff28519SKozlowski Mateusz 2158fc78fd8SMateusz Kozlowski /** 2168fc78fd8SMateusz Kozlowski * Upon SB upgrade some MD regions may be missing in the MD layout blob - e.g. v3 to v5, FTL_LAYOUT_REGION_TYPE_DATA_BASE. 2178fc78fd8SMateusz Kozlowski * The regions couldn't have be added in the SB upgrade path, as the FTL layout wasn't initialized at that point. 2188fc78fd8SMateusz Kozlowski * Now that the FTL layout is initialized, add the missing regions and store the MD layout blob again. 2198fc78fd8SMateusz Kozlowski */ 2207ff28519SKozlowski Mateusz 2217ff28519SKozlowski Mateusz if (ftl_validate_regions(dev, layout)) { 2227ff28519SKozlowski Mateusz return -1; 2237ff28519SKozlowski Mateusz } 2247ff28519SKozlowski Mateusz 2258fc78fd8SMateusz Kozlowski for (reg_type = 0; reg_type < FTL_LAYOUT_REGION_TYPE_MAX; reg_type++) { 2268fc78fd8SMateusz Kozlowski ctx.reg = ftl_layout_region_get(dev, reg_type); 2278fc78fd8SMateusz Kozlowski ctx.upgrade = &layout_upgrade_desc[reg_type]; 2288fc78fd8SMateusz Kozlowski if (!ctx.reg) { 2298fc78fd8SMateusz Kozlowski continue; 2308fc78fd8SMateusz Kozlowski } 2317ff28519SKozlowski Mateusz 2327ff28519SKozlowski Mateusz if (region_verify(dev, &ctx)) { 2337ff28519SKozlowski Mateusz return -1; 2347ff28519SKozlowski Mateusz } 2357ff28519SKozlowski Mateusz } 2367ff28519SKozlowski Mateusz 2378fc78fd8SMateusz Kozlowski return 0; 2387ff28519SKozlowski Mateusz } 2397ff28519SKozlowski Mateusz 2407ff28519SKozlowski Mateusz int 2417ff28519SKozlowski Mateusz ftl_upgrade_layout_dump(struct spdk_ftl_dev *dev) 2427ff28519SKozlowski Mateusz { 2437ff28519SKozlowski Mateusz if (ftl_validate_regions(dev, &dev->layout)) { 2447ff28519SKozlowski Mateusz return -1; 2457ff28519SKozlowski Mateusz } 2467ff28519SKozlowski Mateusz 2477ff28519SKozlowski Mateusz ftl_layout_dump(dev); 2487ff28519SKozlowski Mateusz ftl_superblock_md_layout_dump(dev); 2497ff28519SKozlowski Mateusz return 0; 2507ff28519SKozlowski Mateusz } 2517ff28519SKozlowski Mateusz 2527ff28519SKozlowski Mateusz int 2537ff28519SKozlowski Mateusz ftl_superblock_upgrade(struct spdk_ftl_dev *dev) 2547ff28519SKozlowski Mateusz { 2557ff28519SKozlowski Mateusz struct ftl_layout_upgrade_ctx ctx = {0}; 25630ef80cdSMateusz Kozlowski struct ftl_layout_region *reg = ftl_layout_region_get(dev, FTL_LAYOUT_REGION_TYPE_SB); 2577ff28519SKozlowski Mateusz int rc; 2587ff28519SKozlowski Mateusz 2597ff28519SKozlowski Mateusz ctx.reg = reg; 2607ff28519SKozlowski Mateusz ctx.upgrade = &layout_upgrade_desc[FTL_LAYOUT_REGION_TYPE_SB]; 2618fc78fd8SMateusz Kozlowski reg->current.version = dev->sb->header.version; 2627ff28519SKozlowski Mateusz 2637ff28519SKozlowski Mateusz rc = region_verify(dev, &ctx); 2647ff28519SKozlowski Mateusz if (rc) { 2657ff28519SKozlowski Mateusz return rc; 2667ff28519SKozlowski Mateusz } 2677ff28519SKozlowski Mateusz 2688fc78fd8SMateusz Kozlowski while (reg->current.version < ctx.upgrade->latest_ver) { 2697ff28519SKozlowski Mateusz rc = ftl_region_upgrade(dev, &ctx); 2707ff28519SKozlowski Mateusz if (rc) { 2717ff28519SKozlowski Mateusz return rc; 2727ff28519SKozlowski Mateusz } 2737ff28519SKozlowski Mateusz /* SB upgrades are all synchronous */ 2748fc78fd8SMateusz Kozlowski ftl_region_upgrade_completed(dev, &ctx, 0, 0, rc); 2757ff28519SKozlowski Mateusz } 2767ff28519SKozlowski Mateusz 2778fc78fd8SMateusz Kozlowski /* The mirror shares the same DMA buf, so it is automatically updated upon SB store */ 2788fc78fd8SMateusz Kozlowski dev->layout.region[FTL_LAYOUT_REGION_TYPE_SB_BASE].current.version = reg->current.version; 2797ff28519SKozlowski Mateusz return 0; 2807ff28519SKozlowski Mateusz } 2817ff28519SKozlowski Mateusz 2827ff28519SKozlowski Mateusz static int 2837ff28519SKozlowski Mateusz layout_upgrade_select_next_region(struct spdk_ftl_dev *dev, struct ftl_layout_upgrade_ctx *ctx) 2847ff28519SKozlowski Mateusz { 2857ff28519SKozlowski Mateusz struct ftl_layout_region *reg; 2868fc78fd8SMateusz Kozlowski uint64_t reg_ver, reg_latest_ver; 2877ff28519SKozlowski Mateusz uint32_t reg_type = ctx->reg->type; 2887ff28519SKozlowski Mateusz 2897ff28519SKozlowski Mateusz while (reg_type != FTL_LAYOUT_REGION_TYPE_MAX) { 2907ff28519SKozlowski Mateusz assert(ctx->reg); 2917ff28519SKozlowski Mateusz assert(ctx->upgrade); 2927ff28519SKozlowski Mateusz reg = ctx->reg; 2938fc78fd8SMateusz Kozlowski reg_latest_ver = ctx->upgrade->latest_ver; 2948fc78fd8SMateusz Kozlowski reg_ver = reg->current.version; 2957ff28519SKozlowski Mateusz 2968fc78fd8SMateusz Kozlowski if (reg_ver == reg_latest_ver || reg->type == FTL_LAYOUT_REGION_TYPE_INVALID) { 2977ff28519SKozlowski Mateusz /* select the next region to upgrade */ 2987ff28519SKozlowski Mateusz reg_type++; 2997ff28519SKozlowski Mateusz if (reg_type == FTL_LAYOUT_REGION_TYPE_MAX) { 3007ff28519SKozlowski Mateusz break; 3017ff28519SKozlowski Mateusz } 3027ff28519SKozlowski Mateusz ctx->reg++; 3037ff28519SKozlowski Mateusz ctx->upgrade++; 3048fc78fd8SMateusz Kozlowski } else if (reg_ver < reg_latest_ver) { 3058fc78fd8SMateusz Kozlowski /* qualify region version to upgrade */ 3068fc78fd8SMateusz Kozlowski return FTL_LAYOUT_UPGRADE_CONTINUE; 3077ff28519SKozlowski Mateusz } else { 3087ff28519SKozlowski Mateusz /* unknown version */ 3098fc78fd8SMateusz Kozlowski assert(reg_ver <= reg_latest_ver); 3107ff28519SKozlowski Mateusz FTL_ERRLOG(dev, "Region %d upgrade fault: version %"PRIu64"/%"PRIu64"\n", reg_type, reg_ver, 3118fc78fd8SMateusz Kozlowski reg_latest_ver); 3127ff28519SKozlowski Mateusz return FTL_LAYOUT_UPGRADE_FAULT; 3137ff28519SKozlowski Mateusz } 3147ff28519SKozlowski Mateusz } 3157ff28519SKozlowski Mateusz 3167ff28519SKozlowski Mateusz return FTL_LAYOUT_UPGRADE_DONE; 3177ff28519SKozlowski Mateusz } 3187ff28519SKozlowski Mateusz 3197ff28519SKozlowski Mateusz int 3207ff28519SKozlowski Mateusz ftl_layout_upgrade_init_ctx(struct spdk_ftl_dev *dev, struct ftl_layout_upgrade_ctx *ctx) 3217ff28519SKozlowski Mateusz { 3227ff28519SKozlowski Mateusz if (!ctx->reg) { 32330ef80cdSMateusz Kozlowski ctx->reg = ftl_layout_region_get(dev, 0); 3247ff28519SKozlowski Mateusz ctx->upgrade = &layout_upgrade_desc[0]; 325f34b13ecSNathan Claudel SPDK_STATIC_ASSERT(FTL_LAYOUT_REGION_TYPE_SB == 0, "Invalid SB region type"); 3267ff28519SKozlowski Mateusz } 3277ff28519SKozlowski Mateusz 3287ff28519SKozlowski Mateusz return layout_upgrade_select_next_region(dev, ctx); 3297ff28519SKozlowski Mateusz } 3308fc78fd8SMateusz Kozlowski 3318fc78fd8SMateusz Kozlowski uint64_t 3328fc78fd8SMateusz Kozlowski ftl_layout_upgrade_region_get_latest_version(enum ftl_layout_region_type reg_type) 3338fc78fd8SMateusz Kozlowski { 3348fc78fd8SMateusz Kozlowski assert(reg_type < FTL_LAYOUT_REGION_TYPE_MAX); 3358fc78fd8SMateusz Kozlowski return layout_upgrade_desc[reg_type].latest_ver; 3368fc78fd8SMateusz Kozlowski } 337a5c04e6dSMateusz Kozlowski 3385555d51cSLukasz Lasek int 3395555d51cSLukasz Lasek ftl_layout_upgrade_drop_region(struct spdk_ftl_dev *dev, 3405555d51cSLukasz Lasek struct ftl_layout_tracker_bdev *layout_tracker, 341a5c04e6dSMateusz Kozlowski enum ftl_layout_region_type reg_type, uint32_t reg_ver) 342a5c04e6dSMateusz Kozlowski { 343a5c04e6dSMateusz Kozlowski const struct ftl_layout_tracker_bdev_region_props *reg_search_ctx = NULL; 344a5c04e6dSMateusz Kozlowski int rc = ftl_layout_tracker_bdev_rm_region(layout_tracker, reg_type, reg_ver); 345a5c04e6dSMateusz Kozlowski 346a5c04e6dSMateusz Kozlowski ftl_layout_tracker_bdev_find_next_region(layout_tracker, reg_type, ®_search_ctx); 347a5c04e6dSMateusz Kozlowski if (reg_search_ctx) { 348a5c04e6dSMateusz Kozlowski FTL_ERRLOG(dev, 349a5c04e6dSMateusz Kozlowski "Error when dropping region type %"PRId32", ver %"PRIu32": rc:%"PRId32" but found reg ver %"PRIu32"\n", 350a5c04e6dSMateusz Kozlowski reg_type, reg_ver, rc, reg_search_ctx->ver); 351a5c04e6dSMateusz Kozlowski return -1; 352a5c04e6dSMateusz Kozlowski } 353a5c04e6dSMateusz Kozlowski dev->layout.region[reg_type].type = FTL_LAYOUT_REGION_TYPE_INVALID; 354a5c04e6dSMateusz Kozlowski return 0; 355a5c04e6dSMateusz Kozlowski } 356