nvmf: stub out Abort command support
Add handling of the Abort command in virtual subsystems. This doesn't actually abort any requests - the spdk_nvmf_request_abort() implementation just fails all abort requests - but at least this gives us a place to hook up actual abort handling later. Change-Id: Iafaa393c6f9e7f404af91747cbd81c64ab4810bb Signed-off-by: Daniel Verkamp <daniel.verkamp@intel.com> Reviewed-on: https://review.gerrithub.io/365905 Tested-by: SPDK Automated Test System <sys_sgsw@intel.com> Reviewed-by: Jim Harris <james.r.harris@intel.com> Reviewed-by: Ben Walker <benjamin.walker@intel.com>
This commit is contained in:
parent
27becf40d0
commit
2d34864a61
@ -311,3 +311,10 @@ spdk_nvmf_request_exec(struct spdk_nvmf_request *req)
|
|||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
spdk_nvmf_request_abort(struct spdk_nvmf_request *req)
|
||||||
|
{
|
||||||
|
/* TODO: implement abort, at least for commands that are still queued in software */
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
@ -73,4 +73,6 @@ spdk_nvmf_request_exec(struct spdk_nvmf_request *req);
|
|||||||
|
|
||||||
int spdk_nvmf_request_complete(struct spdk_nvmf_request *req);
|
int spdk_nvmf_request_complete(struct spdk_nvmf_request *req);
|
||||||
|
|
||||||
|
int spdk_nvmf_request_abort(struct spdk_nvmf_request *req);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -273,6 +273,7 @@ spdk_nvmf_session_connect(struct spdk_nvmf_conn *conn,
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
conn->sq_head_max = cmd->sqsize;
|
conn->sq_head_max = cmd->sqsize;
|
||||||
|
conn->qid = cmd->qid;
|
||||||
|
|
||||||
if (cmd->qid == 0) {
|
if (cmd->qid == 0) {
|
||||||
conn->type = CONN_TYPE_AQ;
|
conn->type = CONN_TYPE_AQ;
|
||||||
@ -405,6 +406,26 @@ spdk_nvmf_session_disconnect(struct spdk_nvmf_conn *conn)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct spdk_nvmf_conn *
|
||||||
|
spdk_nvmf_session_get_conn(struct spdk_nvmf_session *session, uint16_t qid)
|
||||||
|
{
|
||||||
|
struct spdk_nvmf_conn *conn;
|
||||||
|
|
||||||
|
TAILQ_FOREACH(conn, &session->connections, link) {
|
||||||
|
if (conn->qid == qid) {
|
||||||
|
return conn;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct spdk_nvmf_request *
|
||||||
|
spdk_nvmf_conn_get_request(struct spdk_nvmf_conn *conn, uint16_t cid)
|
||||||
|
{
|
||||||
|
/* TODO: track list of outstanding requests in conn? */
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
static uint64_t
|
static uint64_t
|
||||||
nvmf_prop_get_cap(struct spdk_nvmf_session *session)
|
nvmf_prop_get_cap(struct spdk_nvmf_session *session)
|
||||||
{
|
{
|
||||||
|
@ -55,6 +55,7 @@ struct spdk_nvmf_conn {
|
|||||||
struct spdk_nvmf_session *sess;
|
struct spdk_nvmf_session *sess;
|
||||||
enum conn_type type;
|
enum conn_type type;
|
||||||
|
|
||||||
|
uint16_t qid;
|
||||||
uint16_t sq_head;
|
uint16_t sq_head;
|
||||||
uint16_t sq_head_max;
|
uint16_t sq_head_max;
|
||||||
|
|
||||||
@ -102,6 +103,10 @@ void spdk_nvmf_session_connect(struct spdk_nvmf_conn *conn,
|
|||||||
struct spdk_nvmf_fabric_connect_data *data,
|
struct spdk_nvmf_fabric_connect_data *data,
|
||||||
struct spdk_nvmf_fabric_connect_rsp *rsp);
|
struct spdk_nvmf_fabric_connect_rsp *rsp);
|
||||||
|
|
||||||
|
struct spdk_nvmf_conn *spdk_nvmf_session_get_conn(struct spdk_nvmf_session *session, uint16_t qid);
|
||||||
|
|
||||||
|
struct spdk_nvmf_request *spdk_nvmf_conn_get_request(struct spdk_nvmf_conn *conn, uint16_t cid);
|
||||||
|
|
||||||
void
|
void
|
||||||
spdk_nvmf_property_get(struct spdk_nvmf_session *session,
|
spdk_nvmf_property_get(struct spdk_nvmf_session *session,
|
||||||
struct spdk_nvmf_fabric_prop_get_cmd *cmd,
|
struct spdk_nvmf_fabric_prop_get_cmd *cmd,
|
||||||
|
@ -286,6 +286,53 @@ nvmf_virtual_ctrlr_identify(struct spdk_nvmf_request *req)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
nvmf_virtual_ctrlr_abort(struct spdk_nvmf_request *req)
|
||||||
|
{
|
||||||
|
struct spdk_nvmf_session *session = req->conn->sess;
|
||||||
|
struct spdk_nvme_cpl *rsp = &req->rsp->nvme_cpl;
|
||||||
|
struct spdk_nvme_cmd *cmd = &req->cmd->nvme_cmd;
|
||||||
|
uint32_t cdw10 = cmd->cdw10;
|
||||||
|
uint16_t cid = cdw10 >> 16;
|
||||||
|
uint16_t sqid = cdw10 & 0xFFFFu;
|
||||||
|
struct spdk_nvmf_conn *conn;
|
||||||
|
struct spdk_nvmf_request *req_to_abort;
|
||||||
|
|
||||||
|
SPDK_TRACELOG(SPDK_TRACE_NVMF, "abort sqid=%u cid=%u\n", sqid, cid);
|
||||||
|
|
||||||
|
rsp->cdw0 = 1; /* Command not aborted */
|
||||||
|
|
||||||
|
conn = spdk_nvmf_session_get_conn(session, sqid);
|
||||||
|
if (conn == NULL) {
|
||||||
|
SPDK_TRACELOG(SPDK_TRACE_NVMF, "sqid %u not found\n", sqid);
|
||||||
|
rsp->status.sct = SPDK_NVME_SCT_GENERIC;
|
||||||
|
rsp->status.sc = SPDK_NVME_SC_INVALID_FIELD;
|
||||||
|
return SPDK_NVMF_REQUEST_EXEC_STATUS_COMPLETE;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* NOTE: This relies on the assumption that all connections for a session will be handled
|
||||||
|
* on the same thread. If this assumption becomes untrue, this will need to pass a message
|
||||||
|
* to the thread handling conn, and the abort will need to be asynchronous.
|
||||||
|
*/
|
||||||
|
req_to_abort = spdk_nvmf_conn_get_request(conn, cid);
|
||||||
|
if (req_to_abort == NULL) {
|
||||||
|
SPDK_TRACELOG(SPDK_TRACE_NVMF, "cid %u not found\n", cid);
|
||||||
|
rsp->status.sct = SPDK_NVME_SCT_GENERIC;
|
||||||
|
rsp->status.sc = SPDK_NVME_SC_INVALID_FIELD;
|
||||||
|
return SPDK_NVMF_REQUEST_EXEC_STATUS_COMPLETE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (spdk_nvmf_request_abort(req_to_abort) == 0) {
|
||||||
|
SPDK_TRACELOG(SPDK_TRACE_NVMF, "abort session=%p req=%p sqid=%u cid=%u successful\n",
|
||||||
|
session, req_to_abort, sqid, cid);
|
||||||
|
rsp->cdw0 = 0; /* Command successfully aborted */
|
||||||
|
}
|
||||||
|
rsp->status.sct = SPDK_NVME_SCT_GENERIC;
|
||||||
|
rsp->status.sc = SPDK_NVME_SC_SUCCESS;
|
||||||
|
return SPDK_NVMF_REQUEST_EXEC_STATUS_COMPLETE;
|
||||||
|
}
|
||||||
|
|
||||||
static int
|
static int
|
||||||
nvmf_virtual_ctrlr_get_features(struct spdk_nvmf_request *req)
|
nvmf_virtual_ctrlr_get_features(struct spdk_nvmf_request *req)
|
||||||
{
|
{
|
||||||
@ -351,6 +398,8 @@ nvmf_virtual_ctrlr_process_admin_cmd(struct spdk_nvmf_request *req)
|
|||||||
return nvmf_virtual_ctrlr_get_log_page(req);
|
return nvmf_virtual_ctrlr_get_log_page(req);
|
||||||
case SPDK_NVME_OPC_IDENTIFY:
|
case SPDK_NVME_OPC_IDENTIFY:
|
||||||
return nvmf_virtual_ctrlr_identify(req);
|
return nvmf_virtual_ctrlr_identify(req);
|
||||||
|
case SPDK_NVME_OPC_ABORT:
|
||||||
|
return nvmf_virtual_ctrlr_abort(req);
|
||||||
case SPDK_NVME_OPC_GET_FEATURES:
|
case SPDK_NVME_OPC_GET_FEATURES:
|
||||||
return nvmf_virtual_ctrlr_get_features(req);
|
return nvmf_virtual_ctrlr_get_features(req);
|
||||||
case SPDK_NVME_OPC_SET_FEATURES:
|
case SPDK_NVME_OPC_SET_FEATURES:
|
||||||
|
@ -39,6 +39,19 @@
|
|||||||
|
|
||||||
|
|
||||||
SPDK_LOG_REGISTER_TRACE_FLAG("nvmf", SPDK_TRACE_NVMF)
|
SPDK_LOG_REGISTER_TRACE_FLAG("nvmf", SPDK_TRACE_NVMF)
|
||||||
|
|
||||||
|
struct spdk_nvmf_conn *
|
||||||
|
spdk_nvmf_session_get_conn(struct spdk_nvmf_session *session, uint16_t qid)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct spdk_nvmf_request *
|
||||||
|
spdk_nvmf_conn_get_request(struct spdk_nvmf_conn *conn, uint16_t cid)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
spdk_nvmf_session_get_features_number_of_queues(struct spdk_nvmf_request *req)
|
spdk_nvmf_session_get_features_number_of_queues(struct spdk_nvmf_request *req)
|
||||||
{
|
{
|
||||||
@ -97,6 +110,12 @@ spdk_nvmf_request_complete(struct spdk_nvmf_request *req)
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
spdk_nvmf_request_abort(struct spdk_nvmf_request *req)
|
||||||
|
{
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
const char *
|
const char *
|
||||||
spdk_bdev_get_name(const struct spdk_bdev *bdev)
|
spdk_bdev_get_name(const struct spdk_bdev *bdev)
|
||||||
{
|
{
|
||||||
|
Loading…
Reference in New Issue
Block a user