1 /* 2 * Copyright (c) 2022 Intel Corporation 3 * SPDX-License-Identifier: Apache-2.0 4 * 5 * Derived from FreeBSD original driver made by Jim Harris 6 * with contributions from Alexander Motin and Wojciech Macek 7 */ 8 9 #ifndef ZEPHYR_DRIVERS_DISK_NVME_NVME_NAMESPACE_H_ 10 #define ZEPHYR_DRIVERS_DISK_NVME_NVME_NAMESPACE_H_ 11 12 #include <zephyr/drivers/disk.h> 13 14 struct nvme_namespace_data { 15 /** namespace size */ 16 uint64_t nsze; 17 18 /** namespace capacity */ 19 uint64_t ncap; 20 21 /** namespace utilization */ 22 uint64_t nuse; 23 24 /** namespace features */ 25 uint8_t nsfeat; 26 27 /** number of lba formats */ 28 uint8_t nlbaf; 29 30 /** formatted lba size */ 31 uint8_t flbas; 32 33 /** metadata capabilities */ 34 uint8_t mc; 35 36 /** end-to-end data protection capabilities */ 37 uint8_t dpc; 38 39 /** end-to-end data protection type settings */ 40 uint8_t dps; 41 42 /** Namespace Multi-path I/O and Namespace Sharing Capabilities */ 43 uint8_t nmic; 44 45 /** Reservation Capabilities */ 46 uint8_t rescap; 47 48 /** Format Progress Indicator */ 49 uint8_t fpi; 50 51 /** Deallocate Logical Block Features */ 52 uint8_t dlfeat; 53 54 /** Namespace Atomic Write Unit Normal */ 55 uint16_t nawun; 56 57 /** Namespace Atomic Write Unit Power Fail */ 58 uint16_t nawupf; 59 60 /** Namespace Atomic Compare & Write Unit */ 61 uint16_t nacwu; 62 63 /** Namespace Atomic Boundary Size Normal */ 64 uint16_t nabsn; 65 66 /** Namespace Atomic Boundary Offset */ 67 uint16_t nabo; 68 69 /** Namespace Atomic Boundary Size Power Fail */ 70 uint16_t nabspf; 71 72 /** Namespace Optimal IO Boundary */ 73 uint16_t noiob; 74 75 /** NVM Capacity */ 76 uint8_t nvmcap[16]; 77 78 /** Namespace Preferred Write Granularity */ 79 uint16_t npwg; 80 81 /** Namespace Preferred Write Alignment */ 82 uint16_t npwa; 83 84 /** Namespace Preferred Deallocate Granularity */ 85 uint16_t npdg; 86 87 /** Namespace Preferred Deallocate Alignment */ 88 uint16_t npda; 89 90 /** Namespace Optimal Write Size */ 91 uint16_t nows; 92 93 /* bytes 74-91: Reserved */ 94 uint8_t reserved5[18]; 95 96 /** ANA Group Identifier */ 97 uint32_t anagrpid; 98 99 /* bytes 96-98: Reserved */ 100 uint8_t reserved6[3]; 101 102 /** Namespace Attributes */ 103 uint8_t nsattr; 104 105 /** NVM Set Identifier */ 106 uint16_t nvmsetid; 107 108 /** Endurance Group Identifier */ 109 uint16_t endgid; 110 111 /** Namespace Globally Unique Identifier */ 112 uint8_t nguid[16]; 113 114 /** IEEE Extended Unique Identifier */ 115 uint8_t eui64[8]; 116 117 /** lba format support */ 118 uint32_t lbaf[16]; 119 120 uint8_t reserved7[192]; 121 122 uint8_t vendor_specific[3712]; 123 } __packed __aligned(4); 124 125 static inline nvme_namespace_data_swapbytes(struct nvme_namespace_data * s)126void nvme_namespace_data_swapbytes(struct nvme_namespace_data *s) 127 { 128 #if _BYTE_ORDER != _LITTLE_ENDIAN 129 int i; 130 131 s->nsze = sys_le64_to_cpu(s->nsze); 132 s->ncap = sys_le64_to_cpu(s->ncap); 133 s->nuse = sys_le64_to_cpu(s->nuse); 134 s->nawun = sys_le16_to_cpu(s->nawun); 135 s->nawupf = sys_le16_to_cpu(s->nawupf); 136 s->nacwu = sys_le16_to_cpu(s->nacwu); 137 s->nabsn = sys_le16_to_cpu(s->nabsn); 138 s->nabo = sys_le16_to_cpu(s->nabo); 139 s->nabspf = sys_le16_to_cpu(s->nabspf); 140 s->noiob = sys_le16_to_cpu(s->noiob); 141 s->npwg = sys_le16_to_cpu(s->npwg); 142 s->npwa = sys_le16_to_cpu(s->npwa); 143 s->npdg = sys_le16_to_cpu(s->npdg); 144 s->npda = sys_le16_to_cpu(s->npda); 145 s->nows = sys_le16_to_cpu(s->nows); 146 s->anagrpid = sys_le32_to_cpu(s->anagrpid); 147 s->nvmsetid = sys_le16_to_cpu(s->nvmsetid); 148 s->endgid = sys_le16_to_cpu(s->endgid); 149 for (i = 0; i < 16; i++) { 150 s->lbaf[i] = sys_le32_to_cpu(s->lbaf[i]); 151 } 152 #else 153 ARG_UNUSED(s); 154 #endif 155 } 156 157 /* Readable identifier: nvme%%n%%\0 */ 158 #define NVME_NAMESPACE_NAME_MAX_LENGTH 10 159 160 struct nvme_namespace { 161 struct nvme_controller *ctrlr; 162 struct nvme_namespace_data data; 163 struct disk_info disk; 164 uint32_t id; 165 uint32_t flags; 166 uint32_t boundary; 167 char name[NVME_NAMESPACE_NAME_MAX_LENGTH]; 168 }; 169 170 enum nvme_namespace_flags { 171 NVME_NS_DEALLOCATE_SUPPORTED = 0x1, 172 NVME_NS_FLUSH_SUPPORTED = 0x2, 173 }; 174 175 uint32_t nvme_namespace_get_sector_size(struct nvme_namespace *ns); 176 177 uint64_t nvme_namespace_get_num_sectors(struct nvme_namespace *ns); 178 179 uint64_t nvme_namespace_get_size(struct nvme_namespace *ns); 180 181 uint32_t nvme_namespace_get_flags(struct nvme_namespace *ns); 182 183 const char *nvme_namespace_get_serial_number(struct nvme_namespace *ns); 184 185 const char *nvme_namespace_get_model_number(struct nvme_namespace *ns); 186 187 const struct nvme_namespace_data * 188 nvme_namespace_get_data(struct nvme_namespace *ns); 189 190 uint32_t nvme_namespace_get_stripesize(struct nvme_namespace *ns); 191 192 int nvme_namespace_construct(struct nvme_namespace *ns, 193 uint32_t id, 194 struct nvme_controller *ctrlr); 195 196 int nvme_namespace_disk_setup(struct nvme_namespace *ns, 197 struct disk_info *disk); 198 199 #endif /* ZEPHYR_DRIVERS_DISK_NVME_NVME_NAMESPACE_H_ */ 200