1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright (c) Intel Corporation. 3 * All rights reserved. 4 */ 5 #include "spdk/ftl.h" 6 7 #include "ftl_conf.h" 8 #include "ftl_core.h" 9 10 static const struct spdk_ftl_conf g_default_conf = { 11 /* 2 free bands - compaction is blocked, gc only */ 12 .limits[SPDK_FTL_LIMIT_CRIT] = 2, 13 /* 3 free bands */ 14 .limits[SPDK_FTL_LIMIT_HIGH] = 3, 15 /* 4 free bands */ 16 .limits[SPDK_FTL_LIMIT_LOW] = 4, 17 /* 5 free bands - gc starts running */ 18 .limits[SPDK_FTL_LIMIT_START] = 5, 19 /* 20% spare blocks */ 20 .overprovisioning = 20, 21 /* 2GiB of DRAM for l2p cache */ 22 .l2p_dram_limit = 2048, 23 /* IO pool size per user thread (this should be adjusted to thread IO qdepth) */ 24 .user_io_pool_size = 2048, 25 .nv_cache = { 26 .chunk_compaction_threshold = 80, 27 }, 28 .fast_shutdown = true, 29 }; 30 31 void 32 spdk_ftl_get_default_conf(struct spdk_ftl_conf *conf) 33 { 34 *conf = g_default_conf; 35 } 36 37 void 38 spdk_ftl_dev_get_conf(const struct spdk_ftl_dev *dev, struct spdk_ftl_conf *conf) 39 { 40 *conf = dev->conf; 41 } 42 43 int 44 spdk_ftl_conf_copy(struct spdk_ftl_conf *dst, const struct spdk_ftl_conf *src) 45 { 46 char *name = NULL; 47 char *core_mask = NULL; 48 char *base_bdev = NULL; 49 char *cache_bdev = NULL; 50 51 if (src->name) { 52 name = strdup(src->name); 53 if (!name) { 54 goto error; 55 } 56 } 57 if (src->core_mask) { 58 core_mask = strdup(src->core_mask); 59 if (!core_mask) { 60 goto error; 61 } 62 } 63 if (src->base_bdev) { 64 base_bdev = strdup(src->base_bdev); 65 if (!base_bdev) { 66 goto error; 67 } 68 } 69 if (src->cache_bdev) { 70 cache_bdev = strdup(src->cache_bdev); 71 if (!cache_bdev) { 72 goto error; 73 } 74 } 75 76 *dst = *src; 77 dst->name = name; 78 dst->core_mask = core_mask; 79 dst->base_bdev = base_bdev; 80 dst->cache_bdev = cache_bdev; 81 return 0; 82 error: 83 free(name); 84 free(core_mask); 85 free(base_bdev); 86 free(cache_bdev); 87 return -ENOMEM; 88 } 89 90 void 91 spdk_ftl_conf_deinit(struct spdk_ftl_conf *conf) 92 { 93 free(conf->name); 94 free(conf->core_mask); 95 free(conf->base_bdev); 96 free(conf->cache_bdev); 97 } 98 99 int 100 ftl_conf_init_dev(struct spdk_ftl_dev *dev, const struct spdk_ftl_conf *conf) 101 { 102 int rc; 103 104 if (!conf->name) { 105 FTL_ERRLOG(dev, "No FTL name in configuration\n"); 106 return -EINVAL; 107 } 108 if (!conf->base_bdev) { 109 FTL_ERRLOG(dev, "No base device in configuration\n"); 110 return -EINVAL; 111 } 112 if (!conf->cache_bdev) { 113 FTL_ERRLOG(dev, "No NV cache device in configuration\n"); 114 return -EINVAL; 115 } 116 117 rc = spdk_ftl_conf_copy(&dev->conf, conf); 118 if (rc) { 119 return rc; 120 } 121 122 dev->limit = SPDK_FTL_LIMIT_MAX; 123 return 0; 124 } 125 126 bool 127 ftl_conf_is_valid(const struct spdk_ftl_conf *conf) 128 { 129 if (conf->overprovisioning >= 100) { 130 return false; 131 } 132 if (conf->overprovisioning == 0) { 133 return false; 134 } 135 136 if (conf->nv_cache.chunk_compaction_threshold == 0 || 137 conf->nv_cache.chunk_compaction_threshold > 100) { 138 return false; 139 } 140 141 return true; 142 } 143