1aa1207eaSJohn Baldwin /*-
2aa1207eaSJohn Baldwin * SPDX-License-Identifier: BSD-2-Clause
3aa1207eaSJohn Baldwin *
4aa1207eaSJohn Baldwin * Copyright (c) 2022-2024 Chelsio Communications, Inc.
5aa1207eaSJohn Baldwin * Written by: John Baldwin <jhb@FreeBSD.org>
6aa1207eaSJohn Baldwin */
7aa1207eaSJohn Baldwin
8aa1207eaSJohn Baldwin #ifndef __NVMF_TRANSPORT_INTERNAL_H__
9aa1207eaSJohn Baldwin #define __NVMF_TRANSPORT_INTERNAL_H__
10aa1207eaSJohn Baldwin
11*365b89e8SJohn Baldwin #include <sys/_nv.h>
12aa1207eaSJohn Baldwin #include <sys/memdesc.h>
13aa1207eaSJohn Baldwin
14aa1207eaSJohn Baldwin /*
15aa1207eaSJohn Baldwin * Interface between the transport-independent APIs in
16aa1207eaSJohn Baldwin * nvmf_transport.c and individual transports.
17aa1207eaSJohn Baldwin */
18aa1207eaSJohn Baldwin
19aa1207eaSJohn Baldwin struct module;
20aa1207eaSJohn Baldwin struct nvmf_io_request;
21aa1207eaSJohn Baldwin
22aa1207eaSJohn Baldwin struct nvmf_transport_ops {
23aa1207eaSJohn Baldwin /* Queue pair management. */
24aa1207eaSJohn Baldwin struct nvmf_qpair *(*allocate_qpair)(bool controller,
25*365b89e8SJohn Baldwin const nvlist_t *nvl);
26aa1207eaSJohn Baldwin void (*free_qpair)(struct nvmf_qpair *qp);
27aa1207eaSJohn Baldwin
28aa1207eaSJohn Baldwin /* Capsule operations. */
29aa1207eaSJohn Baldwin struct nvmf_capsule *(*allocate_capsule)(struct nvmf_qpair *qp,
30aa1207eaSJohn Baldwin int how);
31aa1207eaSJohn Baldwin void (*free_capsule)(struct nvmf_capsule *nc);
32aa1207eaSJohn Baldwin int (*transmit_capsule)(struct nvmf_capsule *nc);
33aa1207eaSJohn Baldwin uint8_t (*validate_command_capsule)(struct nvmf_capsule *nc);
34aa1207eaSJohn Baldwin
35aa1207eaSJohn Baldwin /* Transferring controller data. */
36aa1207eaSJohn Baldwin size_t (*capsule_data_len)(const struct nvmf_capsule *nc);
37aa1207eaSJohn Baldwin int (*receive_controller_data)(struct nvmf_capsule *nc,
38aa1207eaSJohn Baldwin uint32_t data_offset, struct nvmf_io_request *io);
39aa1207eaSJohn Baldwin u_int (*send_controller_data)(struct nvmf_capsule *nc,
40aa1207eaSJohn Baldwin uint32_t data_offset, struct mbuf *m, size_t len);
41aa1207eaSJohn Baldwin
42aa1207eaSJohn Baldwin enum nvmf_trtype trtype;
43aa1207eaSJohn Baldwin int priority;
44aa1207eaSJohn Baldwin };
45aa1207eaSJohn Baldwin
46aa1207eaSJohn Baldwin /* Either an Admin or I/O Submission/Completion Queue pair. */
47aa1207eaSJohn Baldwin struct nvmf_qpair {
48aa1207eaSJohn Baldwin struct nvmf_transport *nq_transport;
49aa1207eaSJohn Baldwin struct nvmf_transport_ops *nq_ops;
50aa1207eaSJohn Baldwin bool nq_controller;
51aa1207eaSJohn Baldwin
52aa1207eaSJohn Baldwin /* Callback to invoke for a received capsule. */
53aa1207eaSJohn Baldwin nvmf_capsule_receive_t *nq_receive;
54aa1207eaSJohn Baldwin void *nq_receive_arg;
55aa1207eaSJohn Baldwin
56aa1207eaSJohn Baldwin /* Callback to invoke for an error. */
57aa1207eaSJohn Baldwin nvmf_qpair_error_t *nq_error;
58aa1207eaSJohn Baldwin void *nq_error_arg;
59aa1207eaSJohn Baldwin
60aa1207eaSJohn Baldwin bool nq_admin;
61aa1207eaSJohn Baldwin };
62aa1207eaSJohn Baldwin
63aa1207eaSJohn Baldwin struct nvmf_io_request {
64aa1207eaSJohn Baldwin /*
65aa1207eaSJohn Baldwin * Data buffer contains io_len bytes in the backing store
66aa1207eaSJohn Baldwin * described by mem.
67aa1207eaSJohn Baldwin */
68aa1207eaSJohn Baldwin struct memdesc io_mem;
69aa1207eaSJohn Baldwin size_t io_len;
70aa1207eaSJohn Baldwin nvmf_io_complete_t *io_complete;
71aa1207eaSJohn Baldwin void *io_complete_arg;
72aa1207eaSJohn Baldwin };
73aa1207eaSJohn Baldwin
74aa1207eaSJohn Baldwin /*
75aa1207eaSJohn Baldwin * Fabrics Command and Response Capsules. The Fabrics host
76aa1207eaSJohn Baldwin * (initiator) and controller (target) drivers work with capsules that
77aa1207eaSJohn Baldwin * are transmitted and received by a specific transport.
78aa1207eaSJohn Baldwin */
79aa1207eaSJohn Baldwin struct nvmf_capsule {
80aa1207eaSJohn Baldwin struct nvmf_qpair *nc_qpair;
81aa1207eaSJohn Baldwin
82aa1207eaSJohn Baldwin /* Either a SQE or CQE. */
83aa1207eaSJohn Baldwin union {
84aa1207eaSJohn Baldwin struct nvme_command nc_sqe;
85aa1207eaSJohn Baldwin struct nvme_completion nc_cqe;
86aa1207eaSJohn Baldwin };
87aa1207eaSJohn Baldwin int nc_qe_len;
88aa1207eaSJohn Baldwin
89aa1207eaSJohn Baldwin /*
90aa1207eaSJohn Baldwin * Is SQHD in received capsule valid? False for locally-
91aa1207eaSJohn Baldwin * synthesized responses.
92aa1207eaSJohn Baldwin */
93aa1207eaSJohn Baldwin bool nc_sqhd_valid;
94aa1207eaSJohn Baldwin
95aa1207eaSJohn Baldwin bool nc_send_data;
96aa1207eaSJohn Baldwin struct nvmf_io_request nc_data;
97aa1207eaSJohn Baldwin };
98aa1207eaSJohn Baldwin
99aa1207eaSJohn Baldwin static void __inline
nvmf_qpair_error(struct nvmf_qpair * nq,int error)100aa1207eaSJohn Baldwin nvmf_qpair_error(struct nvmf_qpair *nq, int error)
101aa1207eaSJohn Baldwin {
102aa1207eaSJohn Baldwin nq->nq_error(nq->nq_error_arg, error);
103aa1207eaSJohn Baldwin }
104aa1207eaSJohn Baldwin
105aa1207eaSJohn Baldwin static void __inline
nvmf_capsule_received(struct nvmf_qpair * nq,struct nvmf_capsule * nc)106aa1207eaSJohn Baldwin nvmf_capsule_received(struct nvmf_qpair *nq, struct nvmf_capsule *nc)
107aa1207eaSJohn Baldwin {
108aa1207eaSJohn Baldwin nq->nq_receive(nq->nq_receive_arg, nc);
109aa1207eaSJohn Baldwin }
110aa1207eaSJohn Baldwin
111aa1207eaSJohn Baldwin static void __inline
nvmf_complete_io_request(struct nvmf_io_request * io,size_t xfered,int error)112aa1207eaSJohn Baldwin nvmf_complete_io_request(struct nvmf_io_request *io, size_t xfered, int error)
113aa1207eaSJohn Baldwin {
114aa1207eaSJohn Baldwin io->io_complete(io->io_complete_arg, xfered, error);
115aa1207eaSJohn Baldwin }
116aa1207eaSJohn Baldwin
117aa1207eaSJohn Baldwin int nvmf_transport_module_handler(struct module *, int, void *);
118aa1207eaSJohn Baldwin
119aa1207eaSJohn Baldwin #define NVMF_TRANSPORT(name, ops) \
120aa1207eaSJohn Baldwin static moduledata_t nvmf_transport_##name##_mod = { \
121aa1207eaSJohn Baldwin "nvmf/" #name, \
122aa1207eaSJohn Baldwin nvmf_transport_module_handler, \
123aa1207eaSJohn Baldwin &(ops) \
124aa1207eaSJohn Baldwin }; \
125aa1207eaSJohn Baldwin DECLARE_MODULE(nvmf_transport_##name, nvmf_transport_##name##_mod, \
126aa1207eaSJohn Baldwin SI_SUB_DRIVERS, SI_ORDER_ANY); \
127aa1207eaSJohn Baldwin MODULE_DEPEND(nvmf_transport_##name, nvmf_transport, 1, 1, 1)
128aa1207eaSJohn Baldwin
129aa1207eaSJohn Baldwin #endif /* !__NVMF_TRANSPORT_INTERNAL_H__ */
130