xref: /illumos-gate/usr/src/lib/libnvme/common/libnvme_impl.h (revision 5b080c3aadfabef156c72cedee796d7b3bac5180)
1533affcbSRobert Mustacchi /*
2533affcbSRobert Mustacchi  * This file and its contents are supplied under the terms of the
3533affcbSRobert Mustacchi  * Common Development and Distribution License ("CDDL"), version 1.0.
4533affcbSRobert Mustacchi  * You may only use this file in accordance with the terms of version
5533affcbSRobert Mustacchi  * 1.0 of the CDDL.
6533affcbSRobert Mustacchi  *
7533affcbSRobert Mustacchi  * A full copy of the text of the CDDL should have accompanied this
8533affcbSRobert Mustacchi  * source.  A copy of the CDDL is also available via the Internet at
9533affcbSRobert Mustacchi  * http://www.illumos.org/license/CDDL.
10533affcbSRobert Mustacchi  */
11533affcbSRobert Mustacchi 
12533affcbSRobert Mustacchi /*
13533affcbSRobert Mustacchi  * Copyright 2024 Oxide Computer Company
14533affcbSRobert Mustacchi  */
15533affcbSRobert Mustacchi 
16533affcbSRobert Mustacchi #ifndef _LIBNVME_IMPL_H
17533affcbSRobert Mustacchi #define	_LIBNVME_IMPL_H
18533affcbSRobert Mustacchi 
19533affcbSRobert Mustacchi /*
20533affcbSRobert Mustacchi  * Implementation structures and related for libnvme.
21533affcbSRobert Mustacchi  */
22533affcbSRobert Mustacchi 
23533affcbSRobert Mustacchi #include <libnvme.h>
24533affcbSRobert Mustacchi #include <libdevinfo.h>
25533affcbSRobert Mustacchi #include <stdbool.h>
26533affcbSRobert Mustacchi #include <nvme_common.h>
27533affcbSRobert Mustacchi #include <synch.h>
28533affcbSRobert Mustacchi 
29533affcbSRobert Mustacchi #ifdef __cplusplus
30533affcbSRobert Mustacchi extern "C" {
31533affcbSRobert Mustacchi #endif
32533affcbSRobert Mustacchi 
33533affcbSRobert Mustacchi /*
34533affcbSRobert Mustacchi  * Maximum size of an internal error message.
35533affcbSRobert Mustacchi  */
36533affcbSRobert Mustacchi #define	NVME_ERR_LEN	1024
37533affcbSRobert Mustacchi 
38533affcbSRobert Mustacchi typedef struct nvme_err_data {
39533affcbSRobert Mustacchi 	nvme_err_t ne_err;
40533affcbSRobert Mustacchi 	int32_t ne_syserr;
41533affcbSRobert Mustacchi 	char ne_errmsg[NVME_ERR_LEN];
42533affcbSRobert Mustacchi 	size_t ne_errlen;
43533affcbSRobert Mustacchi 	uint32_t ne_ctrl_sct;
44533affcbSRobert Mustacchi 	uint32_t ne_ctrl_sc;
45533affcbSRobert Mustacchi } nvme_err_data_t;
46533affcbSRobert Mustacchi 
47533affcbSRobert Mustacchi struct nvme {
48533affcbSRobert Mustacchi 	nvme_err_data_t nh_err;
49533affcbSRobert Mustacchi 	di_node_t nh_devinfo;
50533affcbSRobert Mustacchi };
51533affcbSRobert Mustacchi 
52533affcbSRobert Mustacchi struct nvme_ctrl_disc {
53533affcbSRobert Mustacchi 	di_node_t ncd_devi;
54533affcbSRobert Mustacchi 	di_minor_t ncd_minor;
55533affcbSRobert Mustacchi };
56533affcbSRobert Mustacchi 
57533affcbSRobert Mustacchi struct nvme_ctrl_iter {
58533affcbSRobert Mustacchi 	nvme_t *ni_nvme;
59533affcbSRobert Mustacchi 	bool ni_done;
60533affcbSRobert Mustacchi 	di_node_t ni_cur;
61533affcbSRobert Mustacchi 	nvme_ctrl_disc_t ni_disc;
62533affcbSRobert Mustacchi };
63533affcbSRobert Mustacchi 
64533affcbSRobert Mustacchi struct nvme_ctrl {
65533affcbSRobert Mustacchi 	nvme_t *nc_nvme;
66533affcbSRobert Mustacchi 	nvme_err_data_t nc_err;
67533affcbSRobert Mustacchi 	di_node_t nc_devi;
68533affcbSRobert Mustacchi 	di_minor_t nc_minor;
69533affcbSRobert Mustacchi 	char *nc_devi_path;
70533affcbSRobert Mustacchi 	int32_t nc_inst;
71533affcbSRobert Mustacchi 	int nc_fd;
72533affcbSRobert Mustacchi 	nvme_version_t nc_vers;
73533affcbSRobert Mustacchi 	nvme_identify_ctrl_t nc_info;
74533affcbSRobert Mustacchi 	const struct nvme_vsd *nc_vsd;
75533affcbSRobert Mustacchi };
76533affcbSRobert Mustacchi 
77533affcbSRobert Mustacchi struct nvme_ns_disc {
78533affcbSRobert Mustacchi 	uint32_t nnd_nsid;
79533affcbSRobert Mustacchi 	nvme_ns_disc_level_t nnd_level;
80533affcbSRobert Mustacchi 	nvme_ns_disc_flags_t nnd_flags;
81533affcbSRobert Mustacchi 	uint8_t nnd_eui64[8];
82533affcbSRobert Mustacchi 	uint8_t nnd_nguid[16];
83533affcbSRobert Mustacchi };
84533affcbSRobert Mustacchi 
85533affcbSRobert Mustacchi struct nvme_ns_iter {
86533affcbSRobert Mustacchi 	nvme_ctrl_t *nni_ctrl;
87533affcbSRobert Mustacchi 	nvme_ns_disc_level_t nni_level;
88533affcbSRobert Mustacchi 	bool nni_err;
89533affcbSRobert Mustacchi 	bool nni_done;
90533affcbSRobert Mustacchi 	size_t nni_cur_idx;
91533affcbSRobert Mustacchi 	nvme_ns_disc_t nni_disc;
92533affcbSRobert Mustacchi };
93533affcbSRobert Mustacchi 
94533affcbSRobert Mustacchi struct nvme_ns {
95533affcbSRobert Mustacchi 	nvme_ctrl_t *nn_ctrl;
96533affcbSRobert Mustacchi 	uint32_t nn_nsid;
97533affcbSRobert Mustacchi };
98533affcbSRobert Mustacchi 
99533affcbSRobert Mustacchi struct nvme_nvm_lba_fmt {
100533affcbSRobert Mustacchi 	uint32_t nnlf_id;
101533affcbSRobert Mustacchi 	uint32_t nnlf_ms;
102533affcbSRobert Mustacchi 	uint64_t nnlf_lbasz;
103533affcbSRobert Mustacchi 	uint32_t nnlf_rel;
104533affcbSRobert Mustacchi };
105533affcbSRobert Mustacchi 
106533affcbSRobert Mustacchi struct nvme_ctrl_info {
107533affcbSRobert Mustacchi 	nvme_info_err_t nci_err;
108533affcbSRobert Mustacchi 	int32_t nci_syserr;
109533affcbSRobert Mustacchi 	char nci_errmsg[NVME_ERR_LEN];
110533affcbSRobert Mustacchi 	size_t nci_errlen;
111533affcbSRobert Mustacchi 	/*
112533affcbSRobert Mustacchi 	 * The NVMe strings are generally ASCII strings that have trailing
113533affcbSRobert Mustacchi 	 * spaces on them ala SCSI. We transform that into a C style string
114533affcbSRobert Mustacchi 	 * without trailing padding. The +1 assumes we need to add a terminator.
115533affcbSRobert Mustacchi 	 */
116533affcbSRobert Mustacchi 	char nci_serial[NVME_SERIAL_SZ + 1];
117533affcbSRobert Mustacchi 	char nci_model[NVME_MODEL_SZ + 1];
118533affcbSRobert Mustacchi 	char nci_fwrev[NVME_FWVER_SZ + 1];
119533affcbSRobert Mustacchi 	bool nci_lbaf_valid[NVME_MAX_LBAF];
120533affcbSRobert Mustacchi 	nvme_nvm_lba_fmt_t nci_lbaf[NVME_MAX_LBAF];
121533affcbSRobert Mustacchi 	/*
122533affcbSRobert Mustacchi 	 * Only information below here should be persisted. That is, the above
123533affcbSRobert Mustacchi 	 * information is meant to be specific to the library.
124533affcbSRobert Mustacchi 	 */
125533affcbSRobert Mustacchi 	nvme_version_t nci_vers;
126533affcbSRobert Mustacchi 	int32_t nci_inst;
127533affcbSRobert Mustacchi 	char nci_dev_path[PATH_MAX];
128533affcbSRobert Mustacchi 	nvme_identify_ctrl_t nci_info;
129533affcbSRobert Mustacchi 	nvme_identify_nsid_t nci_ns;
130533affcbSRobert Mustacchi 	nvme_ctrl_transport_t nci_tport;
131533affcbSRobert Mustacchi 	uint16_t nci_vid;
132533affcbSRobert Mustacchi 	uint16_t nci_did;
133533affcbSRobert Mustacchi 	uint16_t nci_subvid;
134533affcbSRobert Mustacchi 	uint16_t nci_subsys;
135533affcbSRobert Mustacchi 	uint8_t nci_rev;
136533affcbSRobert Mustacchi 	uint32_t nci_mps_min;
137533affcbSRobert Mustacchi 	uint32_t nci_mps_max;
138533affcbSRobert Mustacchi 	uint32_t nci_nintrs;
139533affcbSRobert Mustacchi };
140533affcbSRobert Mustacchi 
141533affcbSRobert Mustacchi /*
142533affcbSRobert Mustacchi  * Internal nvlist_t keys for control information.
143533affcbSRobert Mustacchi  */
144533affcbSRobert Mustacchi #define	NVME_NVL_CI_VERS	"version"
145533affcbSRobert Mustacchi #define	NVME_NVL_CI_VERS_0	0
146533affcbSRobert Mustacchi #define	NVME_NVL_CI_INST	"inst"
147533affcbSRobert Mustacchi #define	NVME_NVL_CI_MAJOR	"nvme-major-version"
148533affcbSRobert Mustacchi #define	NVME_NVL_CI_MINOR	"nvme-minor-version"
149533affcbSRobert Mustacchi #define	NVME_NVL_CI_DEV_PATH	"dev-path"
150533affcbSRobert Mustacchi #define	NVME_NVL_CI_ID_CTRL	"identify-controller"
151533affcbSRobert Mustacchi #define	NVME_NVL_CI_ID_NS	"identify-namespace"
152533affcbSRobert Mustacchi #define	NVME_NVL_CI_TPORT	"transport"
153533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_VID	"pci-vendor-id"
154533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_DID	"pci-device-id"
155533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_SUBVID	"pci-subsystem-vendor-id"
156533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_SUBSYS	"pci-subsystem-id"
157533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_REV	"pci-revision-id"
158533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_MPSMIN	"pci-memory-page-size-min"
159533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_MPSMAX	"pci-memory-page-size-max"
160533affcbSRobert Mustacchi #define	NVME_NVL_CI_PCI_NINTRS	"pci-num-interrupts"
161533affcbSRobert Mustacchi 
162533affcbSRobert Mustacchi struct nvme_ns_info {
163533affcbSRobert Mustacchi 	nvme_info_err_t nni_err;
164533affcbSRobert Mustacchi 	int32_t nni_syserr;
165533affcbSRobert Mustacchi 	char nni_errmsg[NVME_ERR_LEN];
166533affcbSRobert Mustacchi 	size_t nni_errlen;
167533affcbSRobert Mustacchi 	uint32_t nni_nsid;
168533affcbSRobert Mustacchi 	nvme_version_t nni_vers;
169533affcbSRobert Mustacchi 	nvme_ns_disc_level_t nni_level;
170533affcbSRobert Mustacchi 	nvme_ioctl_ns_info_t nni_info;
171533affcbSRobert Mustacchi 	bool nni_lbaf_valid[NVME_MAX_LBAF];
172533affcbSRobert Mustacchi 	nvme_nvm_lba_fmt_t nni_lbaf[NVME_MAX_LBAF];
173533affcbSRobert Mustacchi };
174533affcbSRobert Mustacchi 
175533affcbSRobert Mustacchi typedef enum {
176533affcbSRobert Mustacchi 	NVME_LOG_REQ_F_RAE		= 1 << 0,
177533affcbSRobert Mustacchi 	NVME_LOG_REQ_F_BCAST_NS_OK	= 1 << 1
178533affcbSRobert Mustacchi } nvme_log_req_flags_t;
179533affcbSRobert Mustacchi 
180533affcbSRobert Mustacchi struct nvme_log_req {
181533affcbSRobert Mustacchi 	nvme_ctrl_t *nlr_ctrl;
182533affcbSRobert Mustacchi 	uint32_t nlr_need;
183533affcbSRobert Mustacchi 	uint32_t nlr_allow;
184533affcbSRobert Mustacchi 	nvme_csi_t nlr_csi;
185533affcbSRobert Mustacchi 	uint32_t nlr_lid;
186533affcbSRobert Mustacchi 	uint32_t nlr_lsp;
187533affcbSRobert Mustacchi 	uint32_t nlr_lsi;
188533affcbSRobert Mustacchi 	uint32_t nlr_nsid;
189533affcbSRobert Mustacchi 	nvme_log_req_flags_t nlr_flags;
190533affcbSRobert Mustacchi 	void *nlr_output;
191533affcbSRobert Mustacchi 	size_t nlr_output_len;
192533affcbSRobert Mustacchi 	uint64_t nlr_offset;
193533affcbSRobert Mustacchi };
194533affcbSRobert Mustacchi 
195533affcbSRobert Mustacchi /*
196533affcbSRobert Mustacchi  * This structure is used internally to describe information about a given log
197533affcbSRobert Mustacchi  * page.
198533affcbSRobert Mustacchi  */
199533affcbSRobert Mustacchi typedef enum {
200533affcbSRobert Mustacchi 	/*
201533affcbSRobert Mustacchi 	 * This indicates that the log page is actually implemented.
202533affcbSRobert Mustacchi 	 */
203533affcbSRobert Mustacchi 	NVME_LOG_DISC_F_IMPL		= 1 << 0
204533affcbSRobert Mustacchi } nvme_log_disc_flags_t;
205533affcbSRobert Mustacchi 
206533affcbSRobert Mustacchi struct nvme_log_disc {
207533affcbSRobert Mustacchi 	const char		*nld_short;
208533affcbSRobert Mustacchi 	const char		*nld_desc;
209533affcbSRobert Mustacchi 	uint32_t		nld_lid;
210533affcbSRobert Mustacchi 	nvme_csi_t		nld_csi;
211533affcbSRobert Mustacchi 	nvme_log_disc_kind_t	nld_kind;
212533affcbSRobert Mustacchi 	nvme_log_disc_source_t	nld_srcs;
213533affcbSRobert Mustacchi 	nvme_log_disc_fields_t	nld_fields;
214533affcbSRobert Mustacchi 	nvme_log_disc_scope_t	nld_scope;
215533affcbSRobert Mustacchi 	nvme_log_disc_flags_t	nld_flags;
216533affcbSRobert Mustacchi 	nvme_log_size_kind_t	nld_size_kind;
217533affcbSRobert Mustacchi 	uint64_t		nld_alloc_len;
218533affcbSRobert Mustacchi 	nvme_log_page_var_len_f	nld_var_func;
219533affcbSRobert Mustacchi };
220533affcbSRobert Mustacchi 
221533affcbSRobert Mustacchi struct nvme_log_iter {
222533affcbSRobert Mustacchi 	nvme_ctrl_t *nli_ctrl;
223533affcbSRobert Mustacchi 	nvme_log_disc_scope_t nli_scope;
224533affcbSRobert Mustacchi 	bool nli_std_done;
225533affcbSRobert Mustacchi 	bool nli_vs_done;
226533affcbSRobert Mustacchi 	size_t nli_cur_idx;
227533affcbSRobert Mustacchi 	nvme_log_disc_t nli_nld;
228533affcbSRobert Mustacchi };
229533affcbSRobert Mustacchi 
230533affcbSRobert Mustacchi /*
231533affcbSRobert Mustacchi  * Feature discovery and iteration.
232533affcbSRobert Mustacchi  */
233533affcbSRobert Mustacchi struct nvme_feat_disc {
234533affcbSRobert Mustacchi 	const char *nfd_short;
235533affcbSRobert Mustacchi 	const char *nfd_spec;
236533affcbSRobert Mustacchi 	uint32_t nfd_fid;
237533affcbSRobert Mustacchi 	nvme_feat_kind_t nfd_kind;
238533affcbSRobert Mustacchi 	nvme_feat_scope_t nfd_scope;
239533affcbSRobert Mustacchi 	nvme_feat_flags_t nfd_flags;
240533affcbSRobert Mustacchi 	nvme_feat_csi_t nfd_csi;
241533affcbSRobert Mustacchi 	nvme_get_feat_fields_t nfd_in_get;
242533affcbSRobert Mustacchi 	nvme_set_feat_fields_t nfd_in_set;
243533affcbSRobert Mustacchi 	nvme_feat_output_t nfd_out_get;
244533affcbSRobert Mustacchi 	nvme_feat_output_t nfd_out_set;
245533affcbSRobert Mustacchi 	uint64_t nfd_len;
246533affcbSRobert Mustacchi 	nvme_feat_impl_t nfd_impl;
247533affcbSRobert Mustacchi };
248533affcbSRobert Mustacchi 
249533affcbSRobert Mustacchi struct nvme_feat_iter {
250533affcbSRobert Mustacchi 	nvme_ctrl_t *nfi_ctrl;
251533affcbSRobert Mustacchi 	nvme_feat_scope_t nfi_scope;
252533affcbSRobert Mustacchi 	size_t nfi_cur_idx;
253533affcbSRobert Mustacchi 	nvme_feat_disc_t nfi_disc;
254533affcbSRobert Mustacchi };
255533affcbSRobert Mustacchi 
256533affcbSRobert Mustacchi struct nvme_get_feat_req {
257533affcbSRobert Mustacchi 	nvme_ctrl_t *gfr_ctrl;
258533affcbSRobert Mustacchi 	uint32_t gfr_need;
259533affcbSRobert Mustacchi 	uint32_t gfr_allow;
260533affcbSRobert Mustacchi 	nvme_feat_flags_t gfr_flags;
261533affcbSRobert Mustacchi 	uint32_t gfr_fid;
262533affcbSRobert Mustacchi 	uint32_t gfr_sel;
263533affcbSRobert Mustacchi 	uint32_t gfr_nsid;
264533affcbSRobert Mustacchi 	uint32_t gfr_cdw11;
265533affcbSRobert Mustacchi 	void *gfr_buf;
266533affcbSRobert Mustacchi 	size_t gfr_len;
267533affcbSRobert Mustacchi 	uint64_t gfr_targ_len;
268533affcbSRobert Mustacchi 	/*
269533affcbSRobert Mustacchi 	 * The following are set on exec.
270533affcbSRobert Mustacchi 	 */
271533affcbSRobert Mustacchi 	bool gfr_results_valid;
272533affcbSRobert Mustacchi 	uint32_t gfr_cdw0;
273533affcbSRobert Mustacchi };
274533affcbSRobert Mustacchi 
275533affcbSRobert Mustacchi /*
276533affcbSRobert Mustacchi  * Identify command request
277533affcbSRobert Mustacchi  */
278533affcbSRobert Mustacchi struct nvme_id_req {
279533affcbSRobert Mustacchi 	nvme_ctrl_t *nir_ctrl;
280533affcbSRobert Mustacchi 	const nvme_identify_info_t *nir_info;
281533affcbSRobert Mustacchi 	nvme_identify_req_field_t nir_need;
282533affcbSRobert Mustacchi 	nvme_identify_req_field_t nir_allow;
283533affcbSRobert Mustacchi 	uint32_t nir_nsid;
284533affcbSRobert Mustacchi 	uint32_t nir_ctrlid;
285533affcbSRobert Mustacchi 	void *nir_buf;
286533affcbSRobert Mustacchi };
287533affcbSRobert Mustacchi 
288533affcbSRobert Mustacchi /*
289533affcbSRobert Mustacchi  * Vendor unique command support.
290533affcbSRobert Mustacchi  */
291533affcbSRobert Mustacchi struct nvme_vuc_disc {
292533affcbSRobert Mustacchi 	const char *nvd_short;
293533affcbSRobert Mustacchi 	const char *nvd_desc;
294533affcbSRobert Mustacchi 	uint8_t nvd_opc;
295533affcbSRobert Mustacchi 	nvme_vuc_disc_impact_t nvd_impact;
296533affcbSRobert Mustacchi 	nvme_vuc_disc_io_t nvd_dt;
297533affcbSRobert Mustacchi 	nvme_vuc_disc_lock_t nvd_lock;
298533affcbSRobert Mustacchi };
299533affcbSRobert Mustacchi 
300533affcbSRobert Mustacchi struct nvme_vuc_iter {
301533affcbSRobert Mustacchi 	nvme_ctrl_t *nvi_ctrl;
302533affcbSRobert Mustacchi 	size_t nvi_cur_idx;
303533affcbSRobert Mustacchi };
304533affcbSRobert Mustacchi 
305533affcbSRobert Mustacchi struct nvme_vuc_req {
306533affcbSRobert Mustacchi 	nvme_ctrl_t *nvr_ctrl;
307533affcbSRobert Mustacchi 	uint32_t nvr_need;
308533affcbSRobert Mustacchi 	uint32_t nvr_opcode;
309533affcbSRobert Mustacchi 	uint32_t nvr_timeout;
310533affcbSRobert Mustacchi 	uint32_t nvr_nsid;
311533affcbSRobert Mustacchi 	uint32_t nvr_cdw12;
312533affcbSRobert Mustacchi 	uint32_t nvr_cdw13;
313533affcbSRobert Mustacchi 	uint32_t nvr_cdw14;
314533affcbSRobert Mustacchi 	uint32_t nvr_cdw15;
315533affcbSRobert Mustacchi 	uint32_t nvr_impact;
316533affcbSRobert Mustacchi 	size_t nvr_outlen;
317533affcbSRobert Mustacchi 	size_t nvr_inlen;
318533affcbSRobert Mustacchi 	void *nvr_output;
319533affcbSRobert Mustacchi 	const void *nvr_input;
320533affcbSRobert Mustacchi 	/*
321533affcbSRobert Mustacchi 	 * The following values are set on exec.
322533affcbSRobert Mustacchi 	 */
323533affcbSRobert Mustacchi 	bool nvr_results_valid;
324533affcbSRobert Mustacchi 	uint32_t nvr_cdw0;
325533affcbSRobert Mustacchi };
326533affcbSRobert Mustacchi 
327533affcbSRobert Mustacchi /*
328533affcbSRobert Mustacchi  * If we ever support updating the boot partition ID, our expectation is that we
329533affcbSRobert Mustacchi  * end up doing that through other library interfaces even if it uses the same
330533affcbSRobert Mustacchi  * underlying ioctl. That ultimately will keep things simpler from a consumer
331533affcbSRobert Mustacchi  * perspective.
332533affcbSRobert Mustacchi  */
333533affcbSRobert Mustacchi struct nvme_fw_commit_req {
334533affcbSRobert Mustacchi 	nvme_ctrl_t *fwc_ctrl;
335533affcbSRobert Mustacchi 	uint32_t fwc_need;
336533affcbSRobert Mustacchi 	uint32_t fwc_slot;
337533affcbSRobert Mustacchi 	uint32_t fwc_action;
338533affcbSRobert Mustacchi };
339533affcbSRobert Mustacchi 
340533affcbSRobert Mustacchi /*
341533affcbSRobert Mustacchi  * Format request data.
342533affcbSRobert Mustacchi  */
343533affcbSRobert Mustacchi struct nvme_format_req {
344533affcbSRobert Mustacchi 	nvme_ctrl_t *nfr_ctrl;
345533affcbSRobert Mustacchi 	uint32_t nfr_need;
346533affcbSRobert Mustacchi 	bool nfr_ns;
347533affcbSRobert Mustacchi 	uint32_t nfr_lbaf;
348533affcbSRobert Mustacchi 	uint32_t nfr_ses;
349533affcbSRobert Mustacchi 	uint32_t nfr_nsid;
350533affcbSRobert Mustacchi };
351533affcbSRobert Mustacchi 
352533affcbSRobert Mustacchi /*
353533affcbSRobert Mustacchi  * WDC e6 request. This was made an opaque request style structure to try to
354533affcbSRobert Mustacchi  * safeguard us against future changes where something like the optional mode
355533affcbSRobert Mustacchi  * byte was required (right now it's just always zero).
356533affcbSRobert Mustacchi  */
357533affcbSRobert Mustacchi struct nvme_wdc_e6_req {
358533affcbSRobert Mustacchi 	uint32_t wer_need;
359533affcbSRobert Mustacchi 	nvme_vuc_req_t *wer_vuc;
360533affcbSRobert Mustacchi };
361533affcbSRobert Mustacchi 
362533affcbSRobert Mustacchi /*
363533affcbSRobert Mustacchi  * Common interfaces for operation success and failure. There are currently
364533affcbSRobert Mustacchi  * errors that can exist on four different objects in the library and there is
365533affcbSRobert Mustacchi  * one success() and error() function for each of them. See the theory statement
366533affcbSRobert Mustacchi  * section on errors in libnvme.c for more information. Note, all namespace and
367533affcbSRobert Mustacchi  * request structures set errors on the controller.
368533affcbSRobert Mustacchi  *
369533affcbSRobert Mustacchi  * The controller has an extra error path that is used for converting ioctls to
370533affcbSRobert Mustacchi  * semantic errors. It takes care of translating the different kinds of kernel
371533affcbSRobert Mustacchi  * errors to the library's errors. Our goal is to never programmatically leak
372533affcbSRobert Mustacchi  * the kernel ioctls and their error codes as they do not promise stability
373533affcbSRobert Mustacchi  * unlike our aspirations. It also doesn't allow for variable arguments and only
374533affcbSRobert Mustacchi  * takes a single description.
375533affcbSRobert Mustacchi  */
376533affcbSRobert Mustacchi extern bool nvme_error(nvme_t *, nvme_err_t, int32_t, const char *,
377533affcbSRobert Mustacchi     ...)  __PRINTFLIKE(4);
378533affcbSRobert Mustacchi extern bool nvme_success(nvme_t *);
379533affcbSRobert Mustacchi 
380533affcbSRobert Mustacchi extern bool nvme_ctrl_error(nvme_ctrl_t *, nvme_err_t, int32_t, const char *,
381533affcbSRobert Mustacchi     ...)  __PRINTFLIKE(4);
382533affcbSRobert Mustacchi extern bool nvme_ioctl_error(nvme_ctrl_t *, const nvme_ioctl_common_t *,
383533affcbSRobert Mustacchi     const char *);
384533affcbSRobert Mustacchi extern bool nvme_ioctl_syserror(nvme_ctrl_t *, int, const char *);
385533affcbSRobert Mustacchi extern bool nvme_ctrl_success(nvme_ctrl_t *);
386533affcbSRobert Mustacchi 
387533affcbSRobert Mustacchi extern bool nvme_info_error(nvme_ctrl_info_t *, nvme_info_err_t, int32_t,
388533affcbSRobert Mustacchi     const char *, ...)  __PRINTFLIKE(4);
389533affcbSRobert Mustacchi extern bool nvme_info_success(nvme_ctrl_info_t *);
390533affcbSRobert Mustacchi 
391533affcbSRobert Mustacchi extern bool nvme_ns_info_error(nvme_ns_info_t *, nvme_info_err_t, int32_t,
392533affcbSRobert Mustacchi     const char *, ...)  __PRINTFLIKE(4);
393533affcbSRobert Mustacchi extern bool nvme_ns_info_success(nvme_ns_info_t *);
394533affcbSRobert Mustacchi 
395533affcbSRobert Mustacchi /*
396533affcbSRobert Mustacchi  * Common functions for preserving and restoring error data. This comes up when
397533affcbSRobert Mustacchi  * utilizing callback functions for discovery where we call libnvme functions.
398533affcbSRobert Mustacchi  */
399533affcbSRobert Mustacchi extern void nvme_err_save(const nvme_t *, nvme_err_data_t *);
400533affcbSRobert Mustacchi extern void nvme_err_set(nvme_t *, const nvme_err_data_t *);
401533affcbSRobert Mustacchi extern void nvme_ctrl_err_save(const nvme_ctrl_t *, nvme_err_data_t *);
402533affcbSRobert Mustacchi extern void nvme_ctrl_err_set(nvme_ctrl_t *, const nvme_err_data_t *);
403533affcbSRobert Mustacchi 
404533affcbSRobert Mustacchi /*
405533affcbSRobert Mustacchi  * Common functions for issuing ioctls to a controller.
406533affcbSRobert Mustacchi  */
407533affcbSRobert Mustacchi extern bool nvme_ioc_ctrl_info(nvme_ctrl_t *, nvme_ioctl_ctrl_info_t *);
408533affcbSRobert Mustacchi extern bool nvme_ioc_ns_info(nvme_ctrl_t *, uint32_t, nvme_ioctl_ns_info_t *);
409533affcbSRobert Mustacchi 
410533affcbSRobert Mustacchi /*
411533affcbSRobert Mustacchi  * Common validation template functions.
412533affcbSRobert Mustacchi  */
413533affcbSRobert Mustacchi extern bool nvme_field_miss_err(nvme_ctrl_t *, const nvme_field_info_t *,
414533affcbSRobert Mustacchi     size_t, nvme_err_t, const char *, uint32_t);
415533affcbSRobert Mustacchi 
416533affcbSRobert Mustacchi typedef struct {
417533affcbSRobert Mustacchi 	const nvme_field_info_t *chk_fields;
418533affcbSRobert Mustacchi 	size_t chk_index;
419533affcbSRobert Mustacchi 	nvme_err_t chk_field_range;
420533affcbSRobert Mustacchi 	nvme_err_t chk_field_unsup;
421533affcbSRobert Mustacchi 	nvme_err_t chk_field_unuse;
422533affcbSRobert Mustacchi } nvme_field_check_t;
423533affcbSRobert Mustacchi 
424533affcbSRobert Mustacchi extern bool nvme_field_check_one(nvme_ctrl_t *, uint64_t, const char *,
425533affcbSRobert Mustacchi     const nvme_field_check_t *, uint32_t allow);
426533affcbSRobert Mustacchi 
427533affcbSRobert Mustacchi /*
428533affcbSRobert Mustacchi  * Misc. functions.
429533affcbSRobert Mustacchi  */
430533affcbSRobert Mustacchi extern const char *nvme_tporttostr(nvme_ctrl_transport_t);
431533affcbSRobert Mustacchi extern nvme_ns_disc_level_t nvme_ns_state_to_disc_level(nvme_ns_state_t);
432533affcbSRobert Mustacchi extern const char *nvme_nsleveltostr(nvme_ns_disc_level_t);
433533affcbSRobert Mustacchi 
434533affcbSRobert Mustacchi /*
435533affcbSRobert Mustacchi  * Version related information and functions. There are statically declared
436533affcbSRobert Mustacchi  * version structures in the library for use for internal comparisons. Note, we
437533affcbSRobert Mustacchi  * have attempted to avoid a general comparison function in the internal API so
438533affcbSRobert Mustacchi  * that way it's always clear what we're comparing to a version and can't
439533affcbSRobert Mustacchi  * reverse things.
440533affcbSRobert Mustacchi  */
441533affcbSRobert Mustacchi extern const nvme_version_t nvme_vers_1v0;
442533affcbSRobert Mustacchi extern const nvme_version_t nvme_vers_1v1;
443533affcbSRobert Mustacchi extern const nvme_version_t nvme_vers_1v2;
444533affcbSRobert Mustacchi extern const nvme_version_t nvme_vers_1v3;
445533affcbSRobert Mustacchi extern const nvme_version_t nvme_vers_1v4;
446533affcbSRobert Mustacchi extern const nvme_version_t nvme_vers_2v0;
447533affcbSRobert Mustacchi 
448533affcbSRobert Mustacchi extern bool nvme_vers_ctrl_atleast(const nvme_ctrl_t *, const nvme_version_t *);
449533affcbSRobert Mustacchi extern bool nvme_vers_ctrl_info_atleast(const nvme_ctrl_info_t *,
450533affcbSRobert Mustacchi     const nvme_version_t *);
451533affcbSRobert Mustacchi extern bool nvme_vers_ns_info_atleast(const nvme_ns_info_t *,
452533affcbSRobert Mustacchi     const nvme_version_t *);
453533affcbSRobert Mustacchi 
454533affcbSRobert Mustacchi /*
455533affcbSRobert Mustacchi  * Vendor-specific information.
456533affcbSRobert Mustacchi  */
4577655c6d5SRobert Mustacchi typedef struct nvme_vsd_ident {
4587655c6d5SRobert Mustacchi 	const char *nvdi_human;
4597655c6d5SRobert Mustacchi 	bool nvdi_subsys;
4607655c6d5SRobert Mustacchi 	uint16_t nvdi_vid;
4617655c6d5SRobert Mustacchi 	uint16_t nvdi_did;
4627655c6d5SRobert Mustacchi 	uint16_t nvdi_svid;
4637655c6d5SRobert Mustacchi 	uint16_t nvdi_sdid;
4647655c6d5SRobert Mustacchi } nvme_vsd_ident_t;
4657655c6d5SRobert Mustacchi 
466533affcbSRobert Mustacchi typedef struct nvme_vsd {
4677655c6d5SRobert Mustacchi 	const nvme_vsd_ident_t *nvd_ident;
4687655c6d5SRobert Mustacchi 	size_t nvd_nident;
4697655c6d5SRobert Mustacchi 	const nvme_log_page_info_t *const *nvd_logs;
470533affcbSRobert Mustacchi 	size_t nvd_nlogs;
471533affcbSRobert Mustacchi 	const nvme_vuc_disc_t *nvd_vuc;
472533affcbSRobert Mustacchi 	size_t nvd_nvuc;
473533affcbSRobert Mustacchi } nvme_vsd_t;
474533affcbSRobert Mustacchi 
4757655c6d5SRobert Mustacchi extern const nvme_log_page_info_t ocp_log_smart;
4767655c6d5SRobert Mustacchi extern const nvme_log_page_info_t ocp_log_errrec;
4777655c6d5SRobert Mustacchi extern const nvme_log_page_info_t ocp_log_fwact;
4787655c6d5SRobert Mustacchi extern const nvme_log_page_info_t ocp_log_lat;
4797655c6d5SRobert Mustacchi extern const nvme_log_page_info_t ocp_log_devcap;
4807655c6d5SRobert Mustacchi extern const nvme_log_page_info_t ocp_log_unsup;
4817655c6d5SRobert Mustacchi 
482533affcbSRobert Mustacchi extern const nvme_vsd_t wdc_sn840;
4837655c6d5SRobert Mustacchi extern const nvme_vsd_t wdc_sn65x;
4847655c6d5SRobert Mustacchi extern const nvme_vsd_t micron_7300;
4857655c6d5SRobert Mustacchi extern const nvme_vsd_t micron_74x0;
4867655c6d5SRobert Mustacchi extern const nvme_vsd_t micron_x500;
4877655c6d5SRobert Mustacchi extern const nvme_vsd_t intel_p5510;
4887655c6d5SRobert Mustacchi extern const nvme_vsd_t solidigm_p5x20;
4897655c6d5SRobert Mustacchi extern const nvme_vsd_t solidigm_ps10x0;
490*5b080c3aSRobert Mustacchi extern const nvme_vsd_t kioxia_cd8;
491533affcbSRobert Mustacchi 
492533affcbSRobert Mustacchi extern void nvme_vendor_map_ctrl(nvme_ctrl_t *);
493533affcbSRobert Mustacchi extern bool nvme_vendor_vuc_supported(nvme_ctrl_t *, const char *);
494533affcbSRobert Mustacchi 
495533affcbSRobert Mustacchi /*
496533affcbSRobert Mustacchi  * Internal formatting functions that probably could be external.
497533affcbSRobert Mustacchi  */
498533affcbSRobert Mustacchi #define	NVME_NGUID_NAMELEN	33
499533affcbSRobert Mustacchi #define	NVME_EUI64_NAMELEN	17
500533affcbSRobert Mustacchi 
501533affcbSRobert Mustacchi extern int nvme_format_nguid(const uint8_t [16], char *, size_t);
5022c6ce8c7SToomas Soome extern int nvme_format_eui64(const uint8_t [8], char *, size_t);
503533affcbSRobert Mustacchi 
504533affcbSRobert Mustacchi #ifdef __cplusplus
505533affcbSRobert Mustacchi }
506533affcbSRobert Mustacchi #endif
507533affcbSRobert Mustacchi 
508533affcbSRobert Mustacchi #endif /* _LIBNVME_IMPL_H */
509