Home | History | Annotate | Line # | Download | only in ic
nvmereg.h revision 1.1
      1 /*	$NetBSD: nvmereg.h,v 1.1 2016/05/01 10:21:02 nonaka Exp $	*/
      2 /*	$OpenBSD: nvmereg.h,v 1.10 2016/04/14 11:18:32 dlg Exp $ */
      3 
      4 /*
      5  * Copyright (c) 2014 David Gwynne <dlg (at) openbsd.org>
      6  *
      7  * Permission to use, copy, modify, and distribute this software for any
      8  * purpose with or without fee is hereby granted, provided that the above
      9  * copyright notice and this permission notice appear in all copies.
     10  *
     11  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
     12  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
     13  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
     14  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
     15  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
     16  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
     17  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
     18  */
     19 
     20 #define NVME_CAP	0x0000	/* Controller Capabilities */
     21 #define  NVME_CAP_MPSMAX(_r)	(12 + (((_r) >> 52) & 0xf)) /* shift */
     22 #define  NVME_CAP_MPSMIN(_r)	(12 + (((_r) >> 48) & 0xf)) /* shift */
     23 #define  NVME_CAP_CSS(_r)	(((_r) >> 37) & 0x7f)
     24 #define  NVME_CAP_CSS_NVM	__BIT(0)
     25 #define  NVME_CAP_NSSRS(_r)	ISSET((_r), __BIT(36))
     26 #define  NVME_CAP_DSTRD(_r)	__BIT(2 + (((_r) >> 32) & 0xf)) /* bytes */
     27 #define  NVME_CAP_TO(_r)	(500 * (((_r) >> 24) & 0xff)) /* ms */
     28 #define  NVME_CAP_AMS(_r)	(((_r) >> 17) & 0x3)
     29 #define  NVME_CAP_AMS_WRR	__BIT(0)
     30 #define  NVME_CAP_AMS_VENDOR	__BIT(1)
     31 #define  NVME_CAP_CQR(_r)	ISSET((_r), __BIT(16))
     32 #define  NVME_CAP_MQES(_r)	(((_r) & 0xffff) + 1)
     33 #define NVME_CAP_LO	0x0000
     34 #define NVME_CAP_HI	0x0004
     35 #define NVME_VS		0x0008	/* Version */
     36 #define  NVME_VS_MJR(_r)	(((_r) >> 16) & 0xffff)
     37 #define  NVME_VS_MNR(_r)	((_r) & 0xffff)
     38 #define  NVME_VS_1_0		0x00010000
     39 #define  NVME_VS_1_1		0x00010100
     40 #define  NVME_VS_1_2		0x00010200
     41 #define NVME_INTMS	0x000c	/* Interrupt Mask Set */
     42 #define NVME_INTMC	0x0010	/* Interrupt Mask Clear */
     43 #define NVME_CC		0x0014	/* Controller Configuration */
     44 #define  NVME_CC_IOCQES(_v)	(((_v) & 0xf) << 20)
     45 #define  NVME_CC_IOCQES_MASK	NVME_CC_IOCQES(0xf)
     46 #define  NVME_CC_IOCQES_R(_v)	(((_v) >> 20) & 0xf)
     47 #define  NVME_CC_IOSQES(_v)	(((_v) & 0xf) << 16)
     48 #define  NVME_CC_IOSQES_MASK	NVME_CC_IOSQES(0xf)
     49 #define  NVME_CC_IOSQES_R(_v)	(((_v) >> 16) & 0xf)
     50 #define  NVME_CC_SHN(_v)	(((_v) & 0x3) << 14)
     51 #define  NVME_CC_SHN_MASK	NVME_CC_SHN(0x3)
     52 #define  NVME_CC_SHN_R(_v)	(((_v) >> 15) & 0x3)
     53 #define  NVME_CC_SHN_NONE	0
     54 #define  NVME_CC_SHN_NORMAL	1
     55 #define  NVME_CC_SHN_ABRUPT	2
     56 #define  NVME_CC_AMS(_v)	(((_v) & 0x7) << 11)
     57 #define  NVME_CC_AMS_MASK	NVME_CC_AMS(0x7)
     58 #define  NVME_CC_AMS_R(_v)	(((_v) >> 11) & 0xf)
     59 #define  NVME_CC_AMS_RR		0 /* round-robin */
     60 #define  NVME_CC_AMS_WRR_U	1 /* weighted round-robin w/ urgent */
     61 #define  NVME_CC_AMS_VENDOR	7 /* vendor */
     62 #define  NVME_CC_MPS(_v)	((((_v) - 12) & 0xf) << 7)
     63 #define  NVME_CC_MPS_MASK	(0xf << 7)
     64 #define  NVME_CC_MPS_R(_v)	(12 + (((_v) >> 7) & 0xf))
     65 #define  NVME_CC_CSS(_v)	(((_v) & 0x7) << 4)
     66 #define  NVME_CC_CSS_MASK	NVME_CC_CSS(0x7)
     67 #define  NVME_CC_CSS_R(_v)	(((_v) >> 4) & 0x7)
     68 #define  NVME_CC_CSS_NVM	0
     69 #define  NVME_CC_EN		__BIT(0)
     70 #define NVME_CSTS	0x001c	/* Controller Status */
     71 #define  NVME_CSTS_SHST_MASK	(0x3 << 2)
     72 #define  NVME_CSTS_SHST_NONE	(0x0 << 2) /* normal operation */
     73 #define  NVME_CSTS_SHST_WAIT	(0x1 << 2) /* shutdown processing occurring */
     74 #define  NVME_CSTS_SHST_DONE	(0x2 << 2) /* shutdown processing complete */
     75 #define  NVME_CSTS_CFS		(1 << 1)
     76 #define  NVME_CSTS_RDY		(1 << 0)
     77 #define NVME_NSSR	0x0020	/* NVM Subsystem Reset (Optional) */
     78 #define NVME_AQA	0x0024	/* Admin Queue Attributes */
     79 				/* Admin Completion Queue Size */
     80 #define  NVME_AQA_ACQS(_v)	(((_v) - 1) << 16)
     81 				/* Admin Submission Queue Size */
     82 #define  NVME_AQA_ASQS(_v)	(((_v) - 1) << 0)
     83 #define NVME_ASQ	0x0028	/* Admin Submission Queue Base Address */
     84 #define NVME_ACQ	0x0030	/* Admin Completion Queue Base Address */
     85 
     86 #define NVME_ADMIN_Q		0
     87 /* Submission Queue Tail Doorbell */
     88 #define NVME_SQTDBL(_q, _s)	(0x1000 + (2 * (_q) + 0) * (_s))
     89 /* Completion Queue Head Doorbell */
     90 #define NVME_CQHDBL(_q, _s)	(0x1000 + (2 * (_q) + 1) * (_s))
     91 
     92 struct nvme_sge {
     93 	uint8_t		id;
     94 	uint8_t		_reserved[15];
     95 } __packed __aligned(8);
     96 
     97 struct nvme_sge_data {
     98 	uint8_t		id;
     99 	uint8_t		_reserved[3];
    100 
    101 	uint32_t	length;
    102 
    103 	uint64_t	address;
    104 } __packed __aligned(8);
    105 
    106 struct nvme_sge_bit_bucket {
    107 	uint8_t		id;
    108 	uint8_t		_reserved[3];
    109 
    110 	uint32_t	length;
    111 
    112 	uint64_t	address;
    113 } __packed __aligned(8);
    114 
    115 struct nvme_sqe {
    116 	uint8_t		opcode;
    117 	uint8_t		flags;
    118 	uint16_t	cid;
    119 
    120 	uint32_t	nsid;
    121 
    122 	uint8_t		_reserved[8];
    123 
    124 	uint64_t	mptr;
    125 
    126 	union {
    127 		uint64_t	prp[2];
    128 		struct nvme_sge	sge;
    129 	} __packed	entry;
    130 
    131 	uint32_t	cdw10;
    132 	uint32_t	cdw11;
    133 	uint32_t	cdw12;
    134 	uint32_t	cdw13;
    135 	uint32_t	cdw14;
    136 	uint32_t	cdw15;
    137 } __packed __aligned(8);
    138 
    139 struct nvme_sqe_q {
    140 	uint8_t		opcode;
    141 	uint8_t		flags;
    142 	uint16_t	cid;
    143 
    144 	uint8_t		_reserved1[20];
    145 
    146 	uint64_t	prp1;
    147 
    148 	uint8_t		_reserved2[8];
    149 
    150 	uint16_t	qid;
    151 	uint16_t	qsize;
    152 
    153 	uint8_t		qflags;
    154 #define NVM_SQE_SQ_QPRIO_URG	(0x0 << 1)
    155 #define NVM_SQE_SQ_QPRIO_HI	(0x1 << 1)
    156 #define NVM_SQE_SQ_QPRIO_MED	(0x2 << 1)
    157 #define NVM_SQE_SQ_QPRIO_LOW	(0x3 << 1)
    158 #define NVM_SQE_CQ_IEN		(1 << 1)
    159 #define NVM_SQE_Q_PC		(1 << 0)
    160 	uint8_t		_reserved3;
    161 	uint16_t	cqid; /* XXX interrupt vector for cq */
    162 
    163 	uint8_t		_reserved4[16];
    164 } __packed __aligned(8);
    165 
    166 struct nvme_sqe_io {
    167 	uint8_t		opcode;
    168 	uint8_t		flags;
    169 	uint16_t	cid;
    170 
    171 	uint32_t	nsid;
    172 
    173 	uint8_t		_reserved[8];
    174 
    175 	uint64_t	mptr;
    176 
    177 	union {
    178 		uint64_t	prp[2];
    179 		struct nvme_sge	sge;
    180 	} __packed	entry;
    181 
    182 	uint64_t	slba;	/* Starting LBA */
    183 
    184 	uint16_t	nlb;	/* Number of Logical Blocks */
    185 	uint16_t	ioflags;
    186 
    187 	uint8_t		dsm;	/* Dataset Management */
    188 	uint8_t		_reserved2[3];
    189 
    190 	uint32_t	eilbrt;	/* Expected Initial Logical Block
    191 				   Reference Tag */
    192 
    193 	uint16_t	elbat;	/* Expected Logical Block
    194 				   Application Tag */
    195 	uint16_t	elbatm;	/* Expected Logical Block
    196 				   Application Tag Mask */
    197 } __packed __aligned(8);
    198 
    199 struct nvme_cqe {
    200 	uint32_t	cdw0;
    201 
    202 	uint32_t	_reserved;
    203 
    204 	uint16_t	sqhd; /* SQ Head Pointer */
    205 	uint16_t	sqid; /* SQ Identifier */
    206 
    207 	uint16_t	cid; /* Command Identifier */
    208 	uint16_t	flags;
    209 #define NVME_CQE_DNR		__BIT(15)
    210 #define NVME_CQE_M		__BIT(14)
    211 #define NVME_CQE_SCT(_f)	((_f) & (0x07 << 8))
    212 #define  NVME_CQE_SCT_GENERIC		(0x00 << 8)
    213 #define  NVME_CQE_SCT_COMMAND		(0x01 << 8)
    214 #define  NVME_CQE_SCT_MEDIAERR		(0x02 << 8)
    215 #define  NVME_CQE_SCT_VENDOR		(0x07 << 8)
    216 #define NVME_CQE_SC(_f)		((_f) & (0x7f << 1))
    217 #define  NVME_CQE_SC_SUCCESS		(0x00 << 1)
    218 #define  NVME_CQE_SC_INVALID_OPCODE	(0x01 << 1)
    219 #define  NVME_CQE_SC_INVALID_FIELD	(0x02 << 1)
    220 #define  NVME_CQE_SC_CID_CONFLICT	(0x03 << 1)
    221 #define  NVME_CQE_SC_DATA_XFER_ERR	(0x04 << 1)
    222 #define  NVME_CQE_SC_ABRT_BY_NO_PWR	(0x05 << 1)
    223 #define  NVME_CQE_SC_INTERNAL_DEV_ERR	(0x06 << 1)
    224 #define  NVME_CQE_SC_CMD_ABRT_REQD	(0x07 << 1)
    225 #define  NVME_CQE_SC_CMD_ABDR_SQ_DEL	(0x08 << 1)
    226 #define  NVME_CQE_SC_CMD_ABDR_FUSE_ERR	(0x09 << 1)
    227 #define  NVME_CQE_SC_CMD_ABDR_FUSE_MISS	(0x0a << 1)
    228 #define  NVME_CQE_SC_INVALID_NS		(0x0b << 1)
    229 #define  NVME_CQE_SC_CMD_SEQ_ERR	(0x0c << 1)
    230 #define  NVME_CQE_SC_INVALID_LAST_SGL	(0x0d << 1)
    231 #define  NVME_CQE_SC_INVALID_NUM_SGL	(0x0e << 1)
    232 #define  NVME_CQE_SC_DATA_SGL_LEN	(0x0f << 1)
    233 #define  NVME_CQE_SC_MDATA_SGL_LEN	(0x10 << 1)
    234 #define  NVME_CQE_SC_SGL_TYPE_INVALID	(0x11 << 1)
    235 #define  NVME_CQE_SC_LBA_RANGE		(0x80 << 1)
    236 #define  NVME_CQE_SC_CAP_EXCEEDED	(0x81 << 1)
    237 #define  NVME_CQE_NS_NOT_RDY		(0x82 << 1)
    238 #define  NVME_CQE_RSV_CONFLICT		(0x83 << 1)
    239 #define NVME_CQE_PHASE		__BIT(0)
    240 } __packed __aligned(8);
    241 
    242 #define NVM_ADMIN_DEL_IOSQ	0x00 /* Delete I/O Submission Queue */
    243 #define NVM_ADMIN_ADD_IOSQ	0x01 /* Create I/O Submission Queue */
    244 #define NVM_ADMIN_GET_LOG_PG	0x02 /* Get Log Page */
    245 #define NVM_ADMIN_DEL_IOCQ	0x04 /* Delete I/O Completion Queue */
    246 #define NVM_ADMIN_ADD_IOCQ	0x05 /* Create I/O Completion Queue */
    247 #define NVM_ADMIN_IDENTIFY	0x06 /* Identify */
    248 #define NVM_ADMIN_ABORT		0x08 /* Abort */
    249 #define NVM_ADMIN_SET_FEATURES	0x09 /* Set Features */
    250 #define NVM_ADMIN_GET_FEATURES	0x0a /* Get Features */
    251 #define NVM_ADMIN_ASYNC_EV_REQ	0x0c /* Asynchronous Event Request */
    252 #define NVM_ADMIN_FW_ACTIVATE	0x10 /* Firmware Activate */
    253 #define NVM_ADMIN_FW_DOWNLOAD	0x11 /* Firmware Image Download */
    254 
    255 #define NVM_CMD_FLUSH		0x00 /* Flush */
    256 #define NVM_CMD_WRITE		0x01 /* Write */
    257 #define NVM_CMD_READ		0x02 /* Read */
    258 #define NVM_CMD_WR_UNCOR	0x04 /* Write Uncorrectable */
    259 #define NVM_CMD_COMPARE		0x05 /* Compare */
    260 #define NVM_CMD_DSM		0x09 /* Dataset Management */
    261 
    262 /* Power State Descriptor Data */
    263 struct nvm_identify_psd {
    264 	uint16_t	mp;		/* Max Power */
    265 	uint16_t	flags;
    266 
    267 	uint32_t	enlat;		/* Entry Latency */
    268 
    269 	uint32_t	exlat;		/* Exit Latency */
    270 
    271 	uint8_t		rrt;		/* Relative Read Throughput */
    272 	uint8_t		rrl;		/* Relative Read Latency */
    273 	uint8_t		rwt;		/* Relative Write Throughput */
    274 	uint8_t		rwl;		/* Relative Write Latency */
    275 
    276 	uint8_t		_reserved[16];
    277 } __packed __aligned(8);
    278 
    279 struct nvm_identify_controller {
    280 	/* Controller Capabilities and Features */
    281 
    282 	uint16_t	vid;		/* PCI Vendor ID */
    283 	uint16_t	ssvid;		/* PCI Subsystem Vendor ID */
    284 
    285 	uint8_t		sn[20];		/* Serial Number */
    286 	uint8_t		mn[40];		/* Model Number */
    287 	uint8_t		fr[8];		/* Firmware Revision */
    288 
    289 	uint8_t		rab;		/* Recommended Arbitration Burst */
    290 	uint8_t		ieee[3];	/* IEEE OUI Identifier */
    291 
    292 	uint8_t		cmic;		/* Controller Multi-Path I/O and
    293 					   Namespace Sharing Capabilities */
    294 	uint8_t		mdts;		/* Maximum Data Transfer Size */
    295 	uint16_t	cntlid;		/* Controller ID */
    296 
    297 	uint8_t		_reserved1[176];
    298 
    299 	/* Admin Command Set Attributes & Optional Controller Capabilities */
    300 
    301 	uint16_t	oacs;		/* Optional Admin Command Support */
    302 	uint8_t		acl;		/* Abort Command Limit */
    303 	uint8_t		aerl;		/* Asynchronous Event Request Limit */
    304 
    305 	uint8_t		frmw;		/* Firmware Updates */
    306 	uint8_t		lpa;		/* Log Page Attributes */
    307 	uint8_t		elpe;		/* Error Log Page Entries */
    308 	uint8_t		npss;		/* Number of Power States Support */
    309 
    310 	uint8_t		avscc;		/* Admin Vendor Specific Command
    311 					   Configuration */
    312 	uint8_t		apsta;		/* Autonomous Power State Transition
    313 					   Attributes */
    314 
    315 	uint8_t		_reserved2[246];
    316 
    317 	/* NVM Command Set Attributes */
    318 
    319 	uint8_t		sqes;		/* Submission Queue Entry Size */
    320 	uint8_t		cqes;		/* Completion Queue Entry Size */
    321 	uint8_t		_reserved3[2];
    322 
    323 	uint32_t	nn;		/* Number of Namespaces */
    324 
    325 	uint16_t	oncs;		/* Optional NVM Command Support */
    326 	uint16_t	fuses;		/* Fused Operation Support */
    327 
    328 	uint8_t		fna;		/* Format NVM Attributes */
    329 	uint8_t		vwc;		/* Volatile Write Cache */
    330 	uint16_t	awun;		/* Atomic Write Unit Normal */
    331 
    332 	uint16_t	awupf;		/* Atomic Write Unit Power Fail */
    333 	uint8_t		nvscc;		/* NVM Vendor Specific Command */
    334 	uint8_t		_reserved4[1];
    335 
    336 	uint16_t	acwu;		/* Atomic Compare & Write Unit */
    337 	uint8_t		_reserved5[2];
    338 
    339 	uint32_t	sgls;		/* SGL Support */
    340 
    341 	uint8_t		_reserved6[164];
    342 
    343 	/* I/O Command Set Attributes */
    344 
    345 	uint8_t		_reserved7[1344];
    346 
    347 	/* Power State Descriptors */
    348 
    349 	struct nvm_identify_psd psd[32]; /* Power State Descriptors */
    350 
    351 	/* Vendor Specific */
    352 
    353 	uint8_t		_reserved8[1024];
    354 } __packed __aligned(8);
    355 
    356 struct nvm_namespace_format {
    357 	uint16_t	ms;		/* Metadata Size */
    358 	uint8_t		lbads;		/* LBA Data Size */
    359 	uint8_t		rp;		/* Relative Performance */
    360 } __packed __aligned(4);
    361 
    362 struct nvm_identify_namespace {
    363 	uint64_t	nsze;		/* Namespace Size */
    364 
    365 	uint64_t	ncap;		/* Namespace Capacity */
    366 
    367 	uint64_t	nuse;		/* Namespace Utilization */
    368 
    369 	uint8_t		nsfeat;		/* Namespace Features */
    370 	uint8_t		nlbaf;		/* Number of LBA Formats */
    371 	uint8_t		flbas;		/* Formatted LBA Size */
    372 #define NVME_ID_NS_FLBAS(_f)			((_f) & 0x0f)
    373 #define NVME_ID_NS_FLBAS_MD			0x10
    374 	uint8_t		mc;		/* Metadata Capabilities */
    375 	uint8_t		dpc;		/* End-to-end Data Protection
    376 					   Capabilities */
    377 	uint8_t		dps;		/* End-to-end Data Protection Type Settings */
    378 
    379 	uint8_t		_reserved1[98];
    380 
    381 	struct nvm_namespace_format
    382 			lbaf[16];	/* LBA Format Support */
    383 
    384 	uint8_t		_reserved2[192];
    385 
    386 	uint8_t		vs[3712];
    387 } __packed __aligned(8);
    388