1 /*- 2 * BSD LICENSE 3 * 4 * Copyright (c) Intel Corporation. 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions 9 * are met: 10 * 11 * * Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * * Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in 15 * the documentation and/or other materials provided with the 16 * distribution. 17 * * Neither the name of Intel Corporation nor the names of its 18 * contributors may be used to endorse or promote products derived 19 * from this software without specific prior written permission. 20 * 21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 24 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 25 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 26 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 27 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 31 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 32 */ 33 34 #ifndef SPDK_FTL_H 35 #define SPDK_FTL_H 36 37 #include "spdk/stdinc.h" 38 #include "spdk/nvme.h" 39 #include "spdk/nvme_ocssd.h" 40 #include "spdk/uuid.h" 41 #include "spdk/thread.h" 42 43 struct spdk_ftl_dev; 44 45 /* Limit thresholds */ 46 enum { 47 SPDK_FTL_LIMIT_CRIT, 48 SPDK_FTL_LIMIT_HIGH, 49 SPDK_FTL_LIMIT_LOW, 50 SPDK_FTL_LIMIT_START, 51 SPDK_FTL_LIMIT_MAX 52 }; 53 54 struct spdk_ftl_limit { 55 /* Threshold from which the limiting starts */ 56 size_t thld; 57 58 /* Limit percentage */ 59 size_t limit; 60 }; 61 62 struct spdk_ftl_conf { 63 /* Number of reserved addresses not exposed to the user */ 64 size_t lba_rsvd; 65 66 /* Write buffer size */ 67 size_t rwb_size; 68 69 /* Threshold for opening new band */ 70 size_t band_thld; 71 72 /* Maximum IO depth per band relocate */ 73 size_t max_reloc_qdepth; 74 75 /* Maximum active band relocates */ 76 size_t max_active_relocs; 77 78 /* IO pool size per user thread */ 79 size_t user_io_pool_size; 80 81 struct { 82 /* Lowest percentage of invalid lbks for a band to be defragged */ 83 size_t invalid_thld; 84 85 /* User writes limits */ 86 struct spdk_ftl_limit limits[SPDK_FTL_LIMIT_MAX]; 87 } defrag; 88 }; 89 90 /* Range of parallel units (inclusive) */ 91 struct spdk_ftl_punit_range { 92 unsigned int begin; 93 unsigned int end; 94 }; 95 96 enum spdk_ftl_mode { 97 /* Create new device */ 98 SPDK_FTL_MODE_CREATE = (1 << 0), 99 }; 100 101 struct spdk_ftl_dev_init_opts { 102 /* NVMe controller */ 103 struct spdk_nvme_ctrlr *ctrlr; 104 /* Controller's transport ID */ 105 struct spdk_nvme_transport_id trid; 106 107 /* Thread responsible for core tasks execution */ 108 struct spdk_thread *core_thread; 109 /* Thread responsible for read requests */ 110 struct spdk_thread *read_thread; 111 112 /* Device's config */ 113 struct spdk_ftl_conf *conf; 114 /* Device's name */ 115 const char *name; 116 /* Parallel unit range */ 117 struct spdk_ftl_punit_range range; 118 /* Mode flags */ 119 unsigned int mode; 120 /* Device UUID (valid when restoring device from disk) */ 121 struct spdk_uuid uuid; 122 }; 123 124 struct spdk_ftl_attrs { 125 /* Device's UUID */ 126 struct spdk_uuid uuid; 127 /* Parallel unit range */ 128 struct spdk_ftl_punit_range range; 129 /* Number of logical blocks */ 130 uint64_t lbk_cnt; 131 /* Logical block size */ 132 size_t lbk_size; 133 }; 134 135 struct ftl_module_init_opts { 136 /* Thread on which to poll for ANM events */ 137 struct spdk_thread *anm_thread; 138 }; 139 140 typedef void (*spdk_ftl_fn)(void *, int); 141 typedef void (*spdk_ftl_init_fn)(struct spdk_ftl_dev *, void *, int); 142 143 /** 144 * Initialize the FTL module. 145 * 146 * \param opts module configuration 147 * \param cb callback function to call when the module is initialized 148 * \param cb_arg callback's argument 149 * 150 * \return 0 if successfully started initialization, negative values if 151 * resources could not be allocated. 152 */ 153 int spdk_ftl_module_init(const struct ftl_module_init_opts *opts, spdk_ftl_fn cb, void *cb_arg); 154 155 /** 156 * Deinitialize the FTL module. All FTL devices have to be unregistered prior to 157 * calling this function. 158 * 159 * \param cb callback function to call when the deinitialization is completed 160 * \param cb_arg callback's argument 161 * 162 * \return 0 if successfully scheduled deinitialization, negative errno 163 * otherwise. 164 */ 165 int spdk_ftl_module_fini(spdk_ftl_fn cb, void *cb_arg); 166 167 /** 168 * Initialize the FTL on given NVMe device and parallel unit range. 169 * 170 * Covers the following: 171 * - initialize and register NVMe ctrlr, 172 * - retrieve geometry and check if the device has proper configuration, 173 * - allocate buffers and resources, 174 * - initialize internal structures, 175 * - initialize internal thread(s), 176 * - restore or create L2P table. 177 * 178 * \param opts configuration for new device 179 * \param cb callback function to call when the device is created 180 * \param cb_arg callback's argument 181 * 182 * \return 0 if initialization was started successfully, negative errno otherwise. 183 */ 184 int spdk_ftl_dev_init(const struct spdk_ftl_dev_init_opts *opts, spdk_ftl_init_fn cb, void *cb_arg); 185 186 /** 187 * Deinitialize and free given device. 188 * 189 * \param dev device 190 * \param cb callback function to call when the device is freed 191 * \param cb_arg callback's argument 192 * 193 * \return 0 if successfully scheduled free, negative errno otherwise. 194 */ 195 int spdk_ftl_dev_free(struct spdk_ftl_dev *dev, spdk_ftl_fn cb, void *cb_arg); 196 197 /** 198 * Initialize FTL configuration structure with default values. 199 * 200 * \param conf FTL configuration to initialize 201 */ 202 void spdk_ftl_conf_init_defaults(struct spdk_ftl_conf *conf); 203 204 /** 205 * Retrieve device’s attributes. 206 * 207 * \param dev device 208 * \param attr Attribute structure to fill 209 */ 210 void spdk_ftl_dev_get_attrs(const struct spdk_ftl_dev *dev, struct spdk_ftl_attrs *attr); 211 212 /** 213 * Submits a read to the specified device. 214 * 215 * \param dev Device 216 * \param ch I/O channel 217 * \param lba Starting LBA to read the data 218 * \param lba_cnt Number of sectors to read 219 * \param iov Single IO vector or pointer to IO vector table 220 * \param iov_cnt Number of IO vectors 221 * \param cb_fn Callback function to invoke when the I/O is completed 222 * \param cb_arg Argument to pass to the callback function 223 * 224 * \return 0 if successfully submitted, negative errno otherwise. 225 */ 226 int spdk_ftl_read(struct spdk_ftl_dev *dev, struct spdk_io_channel *ch, uint64_t lba, 227 size_t lba_cnt, 228 struct iovec *iov, size_t iov_cnt, spdk_ftl_fn cb_fn, void *cb_arg); 229 230 /** 231 * Submits a write to the specified device. 232 * 233 * \param dev Device 234 * \param ch I/O channel 235 * \param lba Starting LBA to write the data 236 * \param lba_cnt Number of sectors to write 237 * \param iov Single IO vector or pointer to IO vector table 238 * \param iov_cnt Number of IO vectors 239 * \param cb_fn Callback function to invoke when the I/O is completed 240 * \param cb_arg Argument to pass to the callback function 241 * 242 * \return 0 if successfully submitted, negative errno otherwise. 243 */ 244 int spdk_ftl_write(struct spdk_ftl_dev *dev, struct spdk_io_channel *ch, uint64_t lba, 245 size_t lba_cnt, 246 struct iovec *iov, size_t iov_cnt, spdk_ftl_fn cb_fn, void *cb_arg); 247 248 /** 249 * Submits a flush request to the specified device. 250 * 251 * \param dev device 252 * \param cb_fn Callback function to invoke when all prior IOs have been completed 253 * \param cb_arg Argument to pass to the callback function 254 * 255 * \return 0 if successfully submitted, negative errno otherwise. 256 */ 257 int spdk_ftl_flush(struct spdk_ftl_dev *dev, spdk_ftl_fn cb_fn, void *cb_arg); 258 259 #endif /* SPDK_FTL_H */ 260