nvmf: Transports are no longer global

Create one transport per nvmf target. Today, there is just
one global nvmf target, but this paves the way for multiple.

Change-Id: Iaa1f8c5e7b3c1e87621ef2a636c68c2dd8fd929e
Signed-off-by: Ben Walker <benjamin.walker@intel.com>
Reviewed-on: https://review.gerrithub.io/371748
Reviewed-by: Daniel Verkamp <daniel.verkamp@intel.com>
Tested-by: SPDK Automated Test System <sys_sgsw@intel.com>
This commit is contained in:
Ben Walker 2017-07-24 16:30:07 -07:00 committed by Daniel Verkamp
parent 269910c05c
commit 31d033f944
14 changed files with 212 additions and 136 deletions

View File

@ -263,7 +263,7 @@ nvmf_tgt_shutdown_subsystem_by_nqn(const char *nqn)
static void
acceptor_poll(void *arg)
{
spdk_nvmf_acceptor_poll();
spdk_nvmf_tgt_poll();
}
static void

View File

@ -167,7 +167,7 @@ int spdk_nvmf_subsystem_set_sn(struct spdk_nvmf_subsystem *subsystem, const char
const char *spdk_nvmf_subsystem_get_nqn(struct spdk_nvmf_subsystem *subsystem);
enum spdk_nvmf_subtype spdk_nvmf_subsystem_get_type(struct spdk_nvmf_subsystem *subsystem);
void spdk_nvmf_acceptor_poll(void);
void spdk_nvmf_tgt_poll(void);
void spdk_nvmf_handle_connect(struct spdk_nvmf_request *req);

View File

@ -163,7 +163,7 @@ nvmf_init_nvme_ctrlr_properties(struct spdk_nvmf_ctrlr *ctrlr)
static void ctrlr_destruct(struct spdk_nvmf_ctrlr *ctrlr)
{
TAILQ_REMOVE(&ctrlr->subsys->ctrlrs, ctrlr, link);
ctrlr->transport->ctrlr_fini(ctrlr);
ctrlr->transport->ops->ctrlr_fini(ctrlr);
}
void
@ -174,7 +174,7 @@ spdk_nvmf_ctrlr_destruct(struct spdk_nvmf_ctrlr *ctrlr)
TAILQ_REMOVE(&ctrlr->qpairs, qpair, link);
ctrlr->num_qpairs--;
qpair->transport->qpair_fini(qpair);
qpair->transport->ops->qpair_fini(qpair);
}
ctrlr_destruct(ctrlr);
@ -288,7 +288,7 @@ spdk_nvmf_ctrlr_connect(struct spdk_nvmf_qpair *qpair,
}
/* Establish a new ctrlr */
ctrlr = qpair->transport->ctrlr_init();
ctrlr = qpair->transport->ops->ctrlr_init(qpair->transport);
if (ctrlr == NULL) {
SPDK_ERRLOG("Memory allocation failure\n");
rsp->status.sc = SPDK_NVME_SC_INTERNAL_DEVICE_ERROR;
@ -313,9 +313,9 @@ spdk_nvmf_ctrlr_connect(struct spdk_nvmf_qpair *qpair,
memcpy(ctrlr->hostid, data->hostid, sizeof(ctrlr->hostid));
if (qpair->transport->ctrlr_add_qpair(ctrlr, qpair)) {
if (qpair->transport->ops->ctrlr_add_qpair(ctrlr, qpair)) {
rsp->status.sc = SPDK_NVME_SC_INTERNAL_DEVICE_ERROR;
qpair->transport->ctrlr_fini(ctrlr);
qpair->transport->ops->ctrlr_fini(ctrlr);
free(ctrlr);
return;
}
@ -374,7 +374,7 @@ spdk_nvmf_ctrlr_connect(struct spdk_nvmf_qpair *qpair,
return;
}
if (qpair->transport->ctrlr_add_qpair(ctrlr, qpair)) {
if (qpair->transport->ops->ctrlr_add_qpair(ctrlr, qpair)) {
INVALID_CONNECT_CMD(qid);
return;
}
@ -399,8 +399,8 @@ spdk_nvmf_ctrlr_disconnect(struct spdk_nvmf_qpair *qpair)
ctrlr->num_qpairs--;
TAILQ_REMOVE(&ctrlr->qpairs, qpair, link);
qpair->transport->ctrlr_remove_qpair(ctrlr, qpair);
qpair->transport->qpair_fini(qpair);
qpair->transport->ops->ctrlr_remove_qpair(ctrlr, qpair);
qpair->transport->ops->qpair_fini(qpair);
if (ctrlr->num_qpairs == 0) {
ctrlr_destruct(ctrlr);
@ -654,7 +654,7 @@ spdk_nvmf_ctrlr_poll(struct spdk_nvmf_ctrlr *ctrlr)
}
TAILQ_FOREACH_SAFE(qpair, &ctrlr->qpairs, link, tmp) {
if (qpair->transport->qpair_poll(qpair) < 0) {
if (qpair->transport->ops->qpair_poll(qpair) < 0) {
SPDK_ERRLOG("Transport poll failed for qpair %p; closing connection\n", qpair);
spdk_nvmf_ctrlr_disconnect(qpair);
}

View File

@ -51,7 +51,7 @@ enum spdk_nvmf_qpair_type {
};
struct spdk_nvmf_qpair {
const struct spdk_nvmf_transport *transport;
struct spdk_nvmf_transport *transport;
struct spdk_nvmf_ctrlr *ctrlr;
enum spdk_nvmf_qpair_type type;
@ -92,7 +92,7 @@ struct spdk_nvmf_ctrlr {
} async_event_config;
struct spdk_nvmf_request *aer_req;
uint8_t hostid[16];
const struct spdk_nvmf_transport *transport;
struct spdk_nvmf_transport *transport;
TAILQ_ENTRY(spdk_nvmf_ctrlr) link;
};

View File

@ -58,7 +58,7 @@ nvmf_update_discovery_log(void)
struct spdk_nvmf_subsystem_allowed_listener *allowed_listener;
struct spdk_nvmf_listen_addr *listen_addr;
struct spdk_nvmf_discovery_log_page_entry *entry;
const struct spdk_nvmf_transport *transport;
struct spdk_nvmf_transport *transport;
struct spdk_nvmf_discovery_log_page *disc_log;
size_t cur_size;
@ -99,10 +99,10 @@ nvmf_update_discovery_log(void)
entry->subtype = subsystem->subtype;
snprintf(entry->subnqn, sizeof(entry->subnqn), "%s", subsystem->subnqn);
transport = spdk_nvmf_transport_get(listen_addr->trid.trtype);
transport = spdk_nvmf_tgt_get_transport(&g_nvmf_tgt, listen_addr->trid.trtype);
assert(transport != NULL);
transport->listen_addr_discover(listen_addr, entry);
transport->ops->listen_addr_discover(transport, listen_addr, entry);
numrec++;
}

View File

@ -52,8 +52,6 @@ int
spdk_nvmf_tgt_init(uint16_t max_queue_depth, uint16_t max_qpairs_per_ctrlr,
uint32_t in_capsule_data_size, uint32_t max_io_size)
{
int rc;
g_nvmf_tgt.max_qpairs_per_ctrlr = max_qpairs_per_ctrlr;
g_nvmf_tgt.max_queue_depth = max_queue_depth;
g_nvmf_tgt.in_capsule_data_size = in_capsule_data_size;
@ -64,18 +62,13 @@ spdk_nvmf_tgt_init(uint16_t max_queue_depth, uint16_t max_qpairs_per_ctrlr,
g_nvmf_tgt.current_subsystem_id = 0;
TAILQ_INIT(&g_nvmf_tgt.subsystems);
TAILQ_INIT(&g_nvmf_tgt.listen_addrs);
TAILQ_INIT(&g_nvmf_tgt.transports);
SPDK_TRACELOG(SPDK_TRACE_NVMF, "Max Queue Pairs Per Controller: %d\n", max_qpairs_per_ctrlr);
SPDK_TRACELOG(SPDK_TRACE_NVMF, "Max Queue Depth: %d\n", max_queue_depth);
SPDK_TRACELOG(SPDK_TRACE_NVMF, "Max In Capsule Data: %d bytes\n", in_capsule_data_size);
SPDK_TRACELOG(SPDK_TRACE_NVMF, "Max I/O Size: %d bytes\n", max_io_size);
rc = spdk_nvmf_transport_init();
if (rc < 0) {
SPDK_ERRLOG("Transport initialization failed\n");
return -1;
}
return 0;
}
@ -83,6 +76,7 @@ int
spdk_nvmf_tgt_fini(void)
{
struct spdk_nvmf_listen_addr *listen_addr, *listen_addr_tmp;
struct spdk_nvmf_transport *transport, *transport_tmp;
TAILQ_FOREACH_SAFE(listen_addr, &g_nvmf_tgt.listen_addrs, link, listen_addr_tmp) {
TAILQ_REMOVE(&g_nvmf_tgt.listen_addrs, listen_addr, link);
@ -91,21 +85,32 @@ spdk_nvmf_tgt_fini(void)
spdk_nvmf_listen_addr_destroy(listen_addr);
}
spdk_nvmf_transport_fini();
TAILQ_FOREACH_SAFE(transport, &g_nvmf_tgt.transports, link, transport_tmp) {
TAILQ_REMOVE(&g_nvmf_tgt.transports, transport, link);
spdk_nvmf_transport_destroy(transport);
}
return 0;
}
struct spdk_nvmf_transport *
spdk_nvmf_tgt_get_transport(struct spdk_nvmf_tgt *tgt, enum spdk_nvme_transport_type type)
{
struct spdk_nvmf_transport *transport;
TAILQ_FOREACH(transport, &tgt->transports, link) {
if (transport->ops->type == type) {
return transport;
}
}
return NULL;
}
struct spdk_nvmf_listen_addr *
spdk_nvmf_listen_addr_create(struct spdk_nvme_transport_id *trid)
{
struct spdk_nvmf_listen_addr *listen_addr;
const struct spdk_nvmf_transport *transport;
transport = spdk_nvmf_transport_get(trid->trtype);
if (!transport) {
return NULL;
}
listen_addr = calloc(1, sizeof(*listen_addr));
if (!listen_addr) {
@ -120,15 +125,28 @@ spdk_nvmf_listen_addr_create(struct spdk_nvme_transport_id *trid)
void
spdk_nvmf_listen_addr_destroy(struct spdk_nvmf_listen_addr *addr)
{
const struct spdk_nvmf_transport *transport;
struct spdk_nvmf_transport *transport;
transport = spdk_nvmf_transport_get(addr->trid.trtype);
assert(transport != NULL);
transport->listen_addr_remove(addr);
transport = spdk_nvmf_tgt_get_transport(&g_nvmf_tgt, addr->trid.trtype);
if (!transport) {
SPDK_ERRLOG("Attempted to destroy listener without a valid transport\n");
return;
}
transport->ops->listen_addr_remove(transport, addr);
free(addr);
}
void
spdk_nvmf_tgt_poll(void)
{
struct spdk_nvmf_transport *transport, *tmp;
TAILQ_FOREACH_SAFE(transport, &g_nvmf_tgt.transports, link, tmp) {
transport->ops->acceptor_poll(transport);
}
}
SPDK_TRACE_REGISTER_FN(nvmf_trace)
{
spdk_trace_register_object(OBJECT_NVMF_IO, 'r');

View File

@ -87,6 +87,7 @@ struct spdk_nvmf_tgt {
size_t discovery_log_page_size;
TAILQ_HEAD(, spdk_nvmf_listen_addr) listen_addrs;
uint32_t current_subsystem_id;
TAILQ_HEAD(, spdk_nvmf_transport) transports;
};
extern struct spdk_nvmf_tgt g_nvmf_tgt;
@ -94,6 +95,9 @@ extern struct spdk_nvmf_tgt g_nvmf_tgt;
struct spdk_nvmf_listen_addr *spdk_nvmf_listen_addr_create(struct spdk_nvme_transport_id *trid);
void spdk_nvmf_listen_addr_destroy(struct spdk_nvmf_listen_addr *addr);
struct spdk_nvmf_transport *spdk_nvmf_tgt_get_transport(struct spdk_nvmf_tgt *tgt,
enum spdk_nvme_transport_type);
#define OBJECT_NVMF_IO 0x30
#define TRACE_GROUP_NVMF 0x3

View File

@ -258,7 +258,8 @@ spdk_nvmf_rdma_qpair_destroy(struct spdk_nvmf_rdma_qpair *rdma_qpair)
}
static struct spdk_nvmf_rdma_qpair *
spdk_nvmf_rdma_qpair_create(struct rdma_cm_id *id, struct ibv_comp_channel *channel,
spdk_nvmf_rdma_qpair_create(struct spdk_nvmf_transport *transport,
struct rdma_cm_id *id, struct ibv_comp_channel *channel,
uint16_t max_queue_depth, uint16_t max_rw_depth, uint32_t subsystem_id)
{
struct spdk_nvmf_rdma_qpair *rdma_qpair;
@ -310,7 +311,7 @@ spdk_nvmf_rdma_qpair_create(struct rdma_cm_id *id, struct ibv_comp_channel *chan
}
qpair = &rdma_qpair->qpair;
qpair->transport = &spdk_nvmf_transport_rdma;
qpair->transport = transport;
id->context = qpair;
rdma_qpair->cm_id = id;
@ -534,7 +535,7 @@ spdk_nvmf_rdma_request_transfer_data(struct spdk_nvmf_request *req)
}
static int
nvmf_rdma_connect(struct rdma_cm_event *event)
nvmf_rdma_connect(struct spdk_nvmf_transport *transport, struct rdma_cm_event *event)
{
struct spdk_nvmf_rdma_qpair *rdma_qpair = NULL;
struct spdk_nvmf_rdma_listen_addr *addr;
@ -613,7 +614,7 @@ nvmf_rdma_connect(struct rdma_cm_event *event)
max_queue_depth, max_rw_depth);
/* Init the NVMf rdma transport connection */
rdma_qpair = spdk_nvmf_rdma_qpair_create(event->id, addr->comp_channel, max_queue_depth,
rdma_qpair = spdk_nvmf_rdma_qpair_create(transport, event->id, addr->comp_channel, max_queue_depth,
max_rw_depth, subsystem_id);
if (rdma_qpair == NULL) {
SPDK_ERRLOG("Error on nvmf connection creation\n");
@ -912,35 +913,45 @@ spdk_nvmf_rdma_handle_pending_rdma_rw(struct spdk_nvmf_qpair *qpair)
/* Public API callbacks begin here */
static int
spdk_nvmf_rdma_init(uint16_t max_queue_depth, uint32_t max_io_size,
uint32_t in_capsule_data_size)
static struct spdk_nvmf_transport *
spdk_nvmf_rdma_create(struct spdk_nvmf_tgt *tgt)
{
int rc;
struct spdk_nvmf_transport *transport;
transport = calloc(1, sizeof(*transport));
if (!transport) {
return NULL;
}
transport->tgt = tgt;
transport->ops = &spdk_nvmf_transport_rdma;
SPDK_NOTICELOG("*** RDMA Transport Init ***\n");
pthread_mutex_lock(&g_rdma.lock);
g_rdma.max_queue_depth = max_queue_depth;
g_rdma.max_io_size = max_io_size;
g_rdma.in_capsule_data_size = in_capsule_data_size;
g_rdma.max_queue_depth = tgt->max_queue_depth;
g_rdma.max_io_size = tgt->max_io_size;
g_rdma.in_capsule_data_size = tgt->in_capsule_data_size;
g_rdma.event_channel = rdma_create_event_channel();
if (g_rdma.event_channel == NULL) {
SPDK_ERRLOG("rdma_create_event_channel() failed, %s\n", strerror(errno));
free(transport);
pthread_mutex_unlock(&g_rdma.lock);
return -1;
return NULL;
}
rc = fcntl(g_rdma.event_channel->fd, F_SETFL, O_NONBLOCK);
if (rc < 0) {
SPDK_ERRLOG("fcntl to set fd to non-blocking failed\n");
free(transport);
pthread_mutex_unlock(&g_rdma.lock);
return -1;
return NULL;
}
pthread_mutex_unlock(&g_rdma.lock);
return 0;
return transport;
}
static void
@ -953,7 +964,7 @@ spdk_nvmf_rdma_listen_addr_free(struct spdk_nvmf_rdma_listen_addr *addr)
free(addr);
}
static int
spdk_nvmf_rdma_fini(void)
spdk_nvmf_rdma_destroy(struct spdk_nvmf_transport *transport)
{
pthread_mutex_lock(&g_rdma.lock);
@ -963,11 +974,14 @@ spdk_nvmf_rdma_fini(void)
}
pthread_mutex_unlock(&g_rdma.lock);
free(transport);
return 0;
}
static int
spdk_nvmf_rdma_listen_remove(struct spdk_nvmf_listen_addr *listen_addr)
spdk_nvmf_rdma_listen_remove(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr)
{
struct spdk_nvmf_rdma_listen_addr *addr, *tmp;
@ -1017,7 +1031,7 @@ spdk_nvmf_rdma_addr_listen_init(struct spdk_nvmf_rdma_listen_addr *addr)
}
static void
spdk_nvmf_rdma_acceptor_poll(void)
spdk_nvmf_rdma_acceptor_poll(struct spdk_nvmf_transport *transport)
{
struct rdma_cm_event *event;
int rc;
@ -1057,7 +1071,7 @@ spdk_nvmf_rdma_acceptor_poll(void)
switch (event->event) {
case RDMA_CM_EVENT_CONNECT_REQUEST:
rc = nvmf_rdma_connect(event);
rc = nvmf_rdma_connect(transport, event);
if (rc < 0) {
SPDK_ERRLOG("Unable to process connect event. rc: %d\n", rc);
break;
@ -1091,7 +1105,8 @@ spdk_nvmf_rdma_acceptor_poll(void)
}
static int
spdk_nvmf_rdma_listen(struct spdk_nvmf_listen_addr *listen_addr)
spdk_nvmf_rdma_listen(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr)
{
struct spdk_nvmf_rdma_listen_addr *addr;
struct sockaddr_in saddr;
@ -1177,7 +1192,8 @@ spdk_nvmf_rdma_listen(struct spdk_nvmf_listen_addr *listen_addr)
}
static void
spdk_nvmf_rdma_discover(struct spdk_nvmf_listen_addr *listen_addr,
spdk_nvmf_rdma_discover(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr,
struct spdk_nvmf_discovery_log_page_entry *entry)
{
entry->trtype = SPDK_NVMF_TRTYPE_RDMA;
@ -1193,7 +1209,7 @@ spdk_nvmf_rdma_discover(struct spdk_nvmf_listen_addr *listen_addr,
}
static struct spdk_nvmf_ctrlr *
spdk_nvmf_rdma_ctrlr_init(void)
spdk_nvmf_rdma_ctrlr_init(struct spdk_nvmf_transport *transport)
{
struct spdk_nvmf_rdma_ctrlr *rdma_ctrlr;
int i;
@ -1222,7 +1238,7 @@ spdk_nvmf_rdma_ctrlr_init(void)
SLIST_INSERT_HEAD(&rdma_ctrlr->data_buf_pool, buf, link);
}
rdma_ctrlr->ctrlr.transport = &spdk_nvmf_transport_rdma;
rdma_ctrlr->ctrlr.transport = transport;
return &rdma_ctrlr->ctrlr;
}
@ -1575,10 +1591,10 @@ spdk_nvmf_rdma_qpair_is_idle(struct spdk_nvmf_qpair *qpair)
return false;
}
const struct spdk_nvmf_transport spdk_nvmf_transport_rdma = {
const struct spdk_nvmf_transport_ops spdk_nvmf_transport_rdma = {
.type = SPDK_NVME_TRANSPORT_RDMA,
.transport_init = spdk_nvmf_rdma_init,
.transport_fini = spdk_nvmf_rdma_fini,
.create = spdk_nvmf_rdma_create,
.destroy = spdk_nvmf_rdma_destroy,
.acceptor_poll = spdk_nvmf_rdma_acceptor_poll,

View File

@ -59,7 +59,7 @@ spdk_nvmf_request_complete(struct spdk_nvmf_request *req)
response->cid, response->cdw0, response->rsvd1,
*(uint16_t *)&response->status);
if (req->qpair->transport->req_complete(req)) {
if (req->qpair->transport->ops->req_complete(req)) {
SPDK_ERRLOG("Transport request completion error!\n");
return -1;
}

View File

@ -118,7 +118,7 @@ nvmf_subsystem_removable(struct spdk_nvmf_subsystem *subsystem)
if (subsystem->is_removed) {
TAILQ_FOREACH(ctrlr, &subsystem->ctrlrs, link) {
TAILQ_FOREACH(qpair, &ctrlr->qpairs, link) {
if (!qpair->transport->qpair_is_idle(qpair)) {
if (!qpair->transport->ops->qpair_is_idle(qpair)) {
return false;
}
}
@ -262,7 +262,7 @@ struct spdk_nvmf_listen_addr *
spdk_nvmf_tgt_listen(struct spdk_nvme_transport_id *trid)
{
struct spdk_nvmf_listen_addr *listen_addr;
const struct spdk_nvmf_transport *transport;
struct spdk_nvmf_transport *transport;
int rc;
TAILQ_FOREACH(listen_addr, &g_nvmf_tgt.listen_addrs, link) {
@ -271,18 +271,23 @@ spdk_nvmf_tgt_listen(struct spdk_nvme_transport_id *trid)
}
}
transport = spdk_nvmf_transport_get(trid->trtype);
transport = spdk_nvmf_tgt_get_transport(&g_nvmf_tgt, trid->trtype);
if (!transport) {
SPDK_ERRLOG("Unknown transport '%u'\n", trid->trtype);
return NULL;
transport = spdk_nvmf_transport_create(&g_nvmf_tgt, trid->trtype);
if (!transport) {
SPDK_ERRLOG("Transport initialization failed\n");
return NULL;
}
TAILQ_INSERT_TAIL(&g_nvmf_tgt.transports, transport, link);
}
listen_addr = spdk_nvmf_listen_addr_create(trid);
if (!listen_addr) {
return NULL;
}
rc = transport->listen_addr_add(listen_addr);
rc = transport->ops->listen_addr_add(transport, listen_addr);
if (rc < 0) {
free(listen_addr);
SPDK_ERRLOG("Unable to listen on address '%s'\n", trid->traddr);

View File

@ -42,71 +42,56 @@
#include "nvmf_internal.h"
static const struct spdk_nvmf_transport *const g_transports[] = {
static const struct spdk_nvmf_transport_ops *const g_transport_ops[] = {
#ifdef SPDK_CONFIG_RDMA
&spdk_nvmf_transport_rdma,
#endif
};
#define NUM_TRANSPORTS (SPDK_COUNTOF(g_transports))
#define NUM_TRANSPORTS (SPDK_COUNTOF(g_transport_ops))
int
spdk_nvmf_transport_init(void)
struct spdk_nvmf_transport *
spdk_nvmf_transport_create(struct spdk_nvmf_tgt *tgt,
enum spdk_nvme_transport_type type)
{
size_t i;
int count = 0;
const struct spdk_nvmf_transport_ops *ops = NULL;
struct spdk_nvmf_transport *transport;
for (i = 0; i != NUM_TRANSPORTS; i++) {
if (g_transports[i]->transport_init(g_nvmf_tgt.max_queue_depth, g_nvmf_tgt.max_io_size,
g_nvmf_tgt.in_capsule_data_size) < 0) {
SPDK_NOTICELOG("Transport type %s init failed\n",
spdk_nvme_transport_id_trtype_str(g_transports[i]->type));
} else {
count++;
if (g_transport_ops[i]->type == type) {
ops = g_transport_ops[i];
break;
}
}
return count;
if (!ops) {
SPDK_ERRLOG("Transport type %s unavailable.\n",
spdk_nvme_transport_id_trtype_str(type));
return NULL;
}
transport = ops->create(tgt);
if (!transport) {
SPDK_ERRLOG("Unable to create new transport of type %s\n",
spdk_nvme_transport_id_trtype_str(type));
return NULL;
}
transport->ops = ops;
transport->tgt = tgt;
return transport;
}
int
spdk_nvmf_transport_fini(void)
spdk_nvmf_transport_destroy(struct spdk_nvmf_transport *transport)
{
size_t i;
int count = 0;
for (i = 0; i != NUM_TRANSPORTS; i++) {
if (g_transports[i]->transport_fini() < 0) {
SPDK_NOTICELOG("Transport type %s fini failed\n",
spdk_nvme_transport_id_trtype_str(g_transports[i]->type));
} else {
count++;
}
}
return count;
return transport->ops->destroy(transport);
}
void
spdk_nvmf_acceptor_poll(void)
spdk_nvmf_transport_poll(struct spdk_nvmf_transport *transport)
{
size_t i;
for (i = 0; i != NUM_TRANSPORTS; i++) {
g_transports[i]->acceptor_poll();
}
}
const struct spdk_nvmf_transport *
spdk_nvmf_transport_get(enum spdk_nvme_transport_type type)
{
size_t i;
for (i = 0; i != NUM_TRANSPORTS; i++) {
if (type == g_transports[i]->type) {
return g_transports[i];
}
}
return NULL;
transport->ops->acceptor_poll(transport);
}

View File

@ -42,49 +42,58 @@
struct spdk_nvmf_listen_addr;
struct spdk_nvmf_transport {
struct spdk_nvmf_tgt *tgt;
const struct spdk_nvmf_transport_ops *ops;
TAILQ_ENTRY(spdk_nvmf_transport) link;
};
struct spdk_nvmf_transport_ops {
/**
* Transport type
*/
enum spdk_nvme_transport_type type;
/**
* Initialize the transport.
* Create a transport for the given target
*/
int (*transport_init)(uint16_t max_queue_depth, uint32_t max_io_size,
uint32_t in_capsule_data_size);
struct spdk_nvmf_transport *(*create)(struct spdk_nvmf_tgt *tgt);
/**
* Shut down the transport.
* Destroy the transport
*/
int (*transport_fini)(void);
int (*destroy)(struct spdk_nvmf_transport *transport);
/**
* Check for new connections on the transport.
*/
void (*acceptor_poll)(void);
void (*acceptor_poll)(struct spdk_nvmf_transport *transport);
/**
* Instruct the acceptor to listen on the address provided. This
* may be called multiple times.
*/
int (*listen_addr_add)(struct spdk_nvmf_listen_addr *listen_addr);
int (*listen_addr_add)(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr);
/**
* Instruct to remove listening on the address provided. This
* may be called multiple times.
*/
int (*listen_addr_remove)(struct spdk_nvmf_listen_addr *listen_addr);
int (*listen_addr_remove)(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr);
/**
* Fill out a discovery log entry for a specific listen address.
*/
void (*listen_addr_discover)(struct spdk_nvmf_listen_addr *listen_addr,
void (*listen_addr_discover)(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr,
struct spdk_nvmf_discovery_log_page_entry *entry);
/**
* Create a new ctrlr
*/
struct spdk_nvmf_ctrlr *(*ctrlr_init)(void);
struct spdk_nvmf_ctrlr *(*ctrlr_init)(struct spdk_nvmf_transport *transport);
/**
* Destroy a ctrlr
@ -123,11 +132,12 @@ struct spdk_nvmf_transport {
bool (*qpair_is_idle)(struct spdk_nvmf_qpair *qpair);
};
int spdk_nvmf_transport_init(void);
int spdk_nvmf_transport_fini(void);
struct spdk_nvmf_transport *spdk_nvmf_transport_create(struct spdk_nvmf_tgt *tgt,
enum spdk_nvme_transport_type type);
int spdk_nvmf_transport_destroy(struct spdk_nvmf_transport *transport);
const struct spdk_nvmf_transport *spdk_nvmf_transport_get(enum spdk_nvme_transport_type type);
void spdk_nvmf_transport_poll(struct spdk_nvmf_transport *transport);
extern const struct spdk_nvmf_transport spdk_nvmf_transport_rdma;
extern const struct spdk_nvmf_transport_ops spdk_nvmf_transport_rdma;
#endif /* SPDK_NVMF_TRANSPORT_H */

View File

@ -80,27 +80,46 @@ spdk_bdev_get_name(const struct spdk_bdev *bdev)
}
static int
test_transport1_listen_addr_add(struct spdk_nvmf_listen_addr *listen_addr)
test_transport1_listen_addr_add(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr)
{
return 0;
}
static void
test_transport1_listen_addr_discover(struct spdk_nvmf_listen_addr *listen_addr,
test_transport1_listen_addr_discover(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr,
struct spdk_nvmf_discovery_log_page_entry *entry)
{
entry->trtype = 42;
}
static const struct spdk_nvmf_transport test_transport1 = {
static const struct spdk_nvmf_transport_ops test_transport1_ops = {
.listen_addr_add = test_transport1_listen_addr_add,
.listen_addr_discover = test_transport1_listen_addr_discover,
};
const struct spdk_nvmf_transport *
spdk_nvmf_transport_get(enum spdk_nvme_transport_type trtype)
static struct spdk_nvmf_transport test_transport1 = {
.ops = &test_transport1_ops,
};
struct spdk_nvmf_transport *
spdk_nvmf_transport_create(struct spdk_nvmf_tgt *tgt,
enum spdk_nvme_transport_type type)
{
if (type == SPDK_NVME_TRANSPORT_RDMA) {
test_transport1.tgt = tgt;
return &test_transport1;
}
return NULL;
}
struct spdk_nvmf_transport *
spdk_nvmf_tgt_get_transport(struct spdk_nvmf_tgt *tgt, enum spdk_nvme_transport_type trtype)
{
if (trtype == SPDK_NVME_TRANSPORT_RDMA) {
test_transport1.tgt = tgt;
return &test_transport1;
}

View File

@ -67,27 +67,46 @@ spdk_nvmf_listen_addr_destroy(struct spdk_nvmf_listen_addr *addr)
}
static int
test_transport1_listen_addr_add(struct spdk_nvmf_listen_addr *listen_addr)
test_transport1_listen_addr_add(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr)
{
return 0;
}
static void
test_transport1_listen_addr_discover(struct spdk_nvmf_listen_addr *listen_addr,
test_transport1_listen_addr_discover(struct spdk_nvmf_transport *transport,
struct spdk_nvmf_listen_addr *listen_addr,
struct spdk_nvmf_discovery_log_page_entry *entry)
{
entry->trtype = 42;
}
static const struct spdk_nvmf_transport test_transport1 = {
static const struct spdk_nvmf_transport_ops test_transport1_ops = {
.listen_addr_add = test_transport1_listen_addr_add,
.listen_addr_discover = test_transport1_listen_addr_discover,
};
const struct spdk_nvmf_transport *
spdk_nvmf_transport_get(enum spdk_nvme_transport_type trtype)
static struct spdk_nvmf_transport test_transport1 = {
.ops = &test_transport1_ops,
};
struct spdk_nvmf_transport *
spdk_nvmf_transport_create(struct spdk_nvmf_tgt *tgt,
enum spdk_nvme_transport_type type)
{
if (type == SPDK_NVME_TRANSPORT_RDMA) {
test_transport1.tgt = tgt;
return &test_transport1;
}
return NULL;
}
struct spdk_nvmf_transport *
spdk_nvmf_tgt_get_transport(struct spdk_nvmf_tgt *tgt, enum spdk_nvme_transport_type trtype)
{
if (trtype == SPDK_NVME_TRANSPORT_RDMA) {
test_transport1.tgt = tgt;
return &test_transport1;
}