nvme: add Get/Set Feature wrappers with NSID
Some features are per namespace and require a namespace ID; the existing get/set feature functions do not allow passing NSID, so add new API functions that do: * spdk_nvme_ctrlr_cmd_get_feature_ns * spdk_nvme_ctrlr_cmd_set_feature_ns Change-Id: Ia7dc96e57badf1a56489785fb288493592b58b80 Signed-off-by: Jakub Radtke <jakub.radtke@intel.com> Reviewed-on: https://review.gerrithub.io/414706 Tested-by: SPDK Automated Test System <sys_sgsw@intel.com> Reviewed-by: Ben Walker <benjamin.walker@intel.com> Reviewed-by: Shuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
This commit is contained in:
parent
caac0ed9e8
commit
b3497d5da7
@ -876,6 +876,62 @@ int spdk_nvme_ctrlr_cmd_get_feature(struct spdk_nvme_ctrlr *ctrlr,
|
||||
void *payload, uint32_t payload_size,
|
||||
spdk_nvme_cmd_cb cb_fn, void *cb_arg);
|
||||
|
||||
/**
|
||||
* \brief Get specific feature from given NVMe controller.
|
||||
*
|
||||
* \param ctrlr NVMe controller to query.
|
||||
* \param feature The feature identifier.
|
||||
* \param cdw11 as defined by the specification for this command.
|
||||
* \param payload The pointer to the payload buffer.
|
||||
* \param payload_size The size of payload buffer.
|
||||
* \param cb_fn Callback function to invoke when the feature has been retrieved.
|
||||
* \param cb_arg Argument to pass to the callback function.
|
||||
* \param ns_is The namespace identifier.
|
||||
*
|
||||
* \return 0 if successfully submitted, ENOMEM if resources could not be allocated
|
||||
* for this request
|
||||
*
|
||||
* This function is thread safe and can be called at any point while the controller
|
||||
* is attached to the SPDK NVMe driver.
|
||||
*
|
||||
* Call \ref spdk_nvme_ctrlr_process_admin_completions() to poll for completion
|
||||
* of commands submitted through this function.
|
||||
*
|
||||
* \sa spdk_nvme_ctrlr_cmd_set_feature_ns()
|
||||
*/
|
||||
int spdk_nvme_ctrlr_cmd_get_feature_ns(struct spdk_nvme_ctrlr *ctrlr, uint8_t feature,
|
||||
uint32_t cdw11, void *payload, uint32_t payload_size,
|
||||
spdk_nvme_cmd_cb cb_fn, void *cb_arg, uint32_t ns_id);
|
||||
|
||||
/**
|
||||
* \brief Set specific feature for the given NVMe controller and namespace ID.
|
||||
*
|
||||
* \param ctrlr NVMe controller to manipulate.
|
||||
* \param feature The feature identifier.
|
||||
* \param cdw11 as defined by the specification for this command.
|
||||
* \param cdw12 as defined by the specification for this command.
|
||||
* \param payload The pointer to the payload buffer.
|
||||
* \param payload_size The size of payload buffer.
|
||||
* \param cb_fn Callback function to invoke when the feature has been set.
|
||||
* \param cb_arg Argument to pass to the callback function.
|
||||
* \param ns_is The namespace identifier.
|
||||
*
|
||||
* \return 0 if successfully submitted, ENOMEM if resources could not be allocated
|
||||
* for this request.
|
||||
*
|
||||
* This function is thread safe and can be called at any point while the controller
|
||||
* is attached to the SPDK NVMe driver.
|
||||
*
|
||||
* Call \ref spdk_nvme_ctrlr_process_admin_completions() to poll for completion
|
||||
* of commands submitted through this function.
|
||||
*
|
||||
* \sa spdk_nvme_ctrlr_cmd_get_feature_ns()
|
||||
*/
|
||||
int spdk_nvme_ctrlr_cmd_set_feature_ns(struct spdk_nvme_ctrlr *ctrlr, uint8_t feature,
|
||||
uint32_t cdw11, uint32_t cdw12, void *payload,
|
||||
uint32_t payload_size, spdk_nvme_cmd_cb cb_fn,
|
||||
void *cb_arg, uint32_t ns_id);
|
||||
|
||||
/**
|
||||
* \brief Attach the specified namespace to controllers.
|
||||
*
|
||||
|
@ -340,6 +340,66 @@ spdk_nvme_ctrlr_cmd_get_feature(struct spdk_nvme_ctrlr *ctrlr, uint8_t feature,
|
||||
return rc;
|
||||
}
|
||||
|
||||
int
|
||||
spdk_nvme_ctrlr_cmd_get_feature_ns(struct spdk_nvme_ctrlr *ctrlr, uint8_t feature,
|
||||
uint32_t cdw11, void *payload,
|
||||
uint32_t payload_size, spdk_nvme_cmd_cb cb_fn,
|
||||
void *cb_arg, uint32_t ns_id)
|
||||
{
|
||||
struct nvme_request *req;
|
||||
struct spdk_nvme_cmd *cmd;
|
||||
int rc;
|
||||
|
||||
nvme_robust_mutex_lock(&ctrlr->ctrlr_lock);
|
||||
req = nvme_allocate_request_user_copy(ctrlr->adminq, payload, payload_size, cb_fn, cb_arg,
|
||||
false);
|
||||
if (req == NULL) {
|
||||
nvme_robust_mutex_unlock(&ctrlr->ctrlr_lock);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
cmd = &req->cmd;
|
||||
cmd->opc = SPDK_NVME_OPC_GET_FEATURES;
|
||||
cmd->cdw10 = feature;
|
||||
cmd->cdw11 = cdw11;
|
||||
cmd->nsid = ns_id;
|
||||
|
||||
rc = nvme_ctrlr_submit_admin_request(ctrlr, req);
|
||||
nvme_robust_mutex_unlock(&ctrlr->ctrlr_lock);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
int spdk_nvme_ctrlr_cmd_set_feature_ns(struct spdk_nvme_ctrlr *ctrlr, uint8_t feature,
|
||||
uint32_t cdw11, uint32_t cdw12, void *payload,
|
||||
uint32_t payload_size, spdk_nvme_cmd_cb cb_fn,
|
||||
void *cb_arg, uint32_t ns_id)
|
||||
{
|
||||
struct nvme_request *req;
|
||||
struct spdk_nvme_cmd *cmd;
|
||||
int rc;
|
||||
|
||||
nvme_robust_mutex_lock(&ctrlr->ctrlr_lock);
|
||||
req = nvme_allocate_request_user_copy(ctrlr->adminq, payload, payload_size, cb_fn, cb_arg,
|
||||
true);
|
||||
if (req == NULL) {
|
||||
nvme_robust_mutex_unlock(&ctrlr->ctrlr_lock);
|
||||
return -ENOMEM;
|
||||
}
|
||||
|
||||
cmd = &req->cmd;
|
||||
cmd->opc = SPDK_NVME_OPC_SET_FEATURES;
|
||||
cmd->cdw10 = feature;
|
||||
cmd->cdw11 = cdw11;
|
||||
cmd->cdw12 = cdw12;
|
||||
cmd->nsid = ns_id;
|
||||
|
||||
rc = nvme_ctrlr_submit_admin_request(ctrlr, req);
|
||||
nvme_robust_mutex_unlock(&ctrlr->ctrlr_lock);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
int
|
||||
nvme_ctrlr_cmd_set_num_queues(struct spdk_nvme_ctrlr *ctrlr,
|
||||
uint32_t num_queues, spdk_nvme_cmd_cb cb_fn, void *cb_arg)
|
||||
|
@ -56,6 +56,11 @@ uint16_t abort_sqid = 1;
|
||||
uint32_t namespace_management_nsid = 1;
|
||||
uint32_t format_nvme_nsid = 1;
|
||||
|
||||
uint32_t expected_feature_ns = 2;
|
||||
uint32_t expected_feature_cdw10 = SPDK_NVME_FEAT_LBA_RANGE_TYPE;
|
||||
uint32_t expected_feature_cdw11 = 1;
|
||||
uint32_t expected_feature_cdw12 = 1;
|
||||
|
||||
typedef void (*verify_request_fn_t)(struct nvme_request *req);
|
||||
verify_request_fn_t verify_fn;
|
||||
|
||||
@ -103,6 +108,15 @@ static void verify_set_feature_cmd(struct nvme_request *req)
|
||||
CU_ASSERT(req->cmd.cdw12 == feature_cdw12);
|
||||
}
|
||||
|
||||
static void verify_set_feature_ns_cmd(struct nvme_request *req)
|
||||
{
|
||||
CU_ASSERT(req->cmd.opc == SPDK_NVME_OPC_SET_FEATURES);
|
||||
CU_ASSERT(req->cmd.cdw10 == expected_feature_cdw10);
|
||||
CU_ASSERT(req->cmd.cdw11 == expected_feature_cdw11);
|
||||
CU_ASSERT(req->cmd.cdw12 == expected_feature_cdw12);
|
||||
CU_ASSERT(req->cmd.nsid == expected_feature_ns);
|
||||
}
|
||||
|
||||
static void verify_get_feature_cmd(struct nvme_request *req)
|
||||
{
|
||||
CU_ASSERT(req->cmd.opc == SPDK_NVME_OPC_GET_FEATURES);
|
||||
@ -110,6 +124,14 @@ static void verify_get_feature_cmd(struct nvme_request *req)
|
||||
CU_ASSERT(req->cmd.cdw11 == get_feature_cdw11);
|
||||
}
|
||||
|
||||
static void verify_get_feature_ns_cmd(struct nvme_request *req)
|
||||
{
|
||||
CU_ASSERT(req->cmd.opc == SPDK_NVME_OPC_GET_FEATURES);
|
||||
CU_ASSERT(req->cmd.cdw10 == expected_feature_cdw10);
|
||||
CU_ASSERT(req->cmd.cdw11 == expected_feature_cdw11);
|
||||
CU_ASSERT(req->cmd.nsid == expected_feature_ns);
|
||||
}
|
||||
|
||||
static void verify_abort_cmd(struct nvme_request *req)
|
||||
{
|
||||
CU_ASSERT(req->cmd.opc == SPDK_NVME_OPC_ABORT);
|
||||
@ -423,6 +445,29 @@ test_set_feature_cmd(void)
|
||||
spdk_nvme_ctrlr_cmd_set_feature(&ctrlr, feature, feature_cdw11, feature_cdw12, NULL, 0, NULL, NULL);
|
||||
}
|
||||
|
||||
static void
|
||||
test_get_feature_ns_cmd(void)
|
||||
{
|
||||
DECLARE_AND_CONSTRUCT_CTRLR();
|
||||
|
||||
verify_fn = verify_get_feature_ns_cmd;
|
||||
|
||||
spdk_nvme_ctrlr_cmd_get_feature_ns(&ctrlr, expected_feature_cdw10,
|
||||
expected_feature_cdw11, NULL, 0,
|
||||
NULL, NULL, expected_feature_ns);
|
||||
}
|
||||
|
||||
static void
|
||||
test_set_feature_ns_cmd(void)
|
||||
{
|
||||
DECLARE_AND_CONSTRUCT_CTRLR();
|
||||
|
||||
verify_fn = verify_set_feature_ns_cmd;
|
||||
|
||||
spdk_nvme_ctrlr_cmd_set_feature_ns(&ctrlr, expected_feature_cdw10,
|
||||
expected_feature_cdw11, expected_feature_cdw12,
|
||||
NULL, 0, NULL, NULL, expected_feature_ns);
|
||||
}
|
||||
|
||||
static void
|
||||
test_get_feature_cmd(void)
|
||||
@ -574,7 +619,9 @@ int main(int argc, char **argv)
|
||||
if (
|
||||
CU_add_test(suite, "test ctrlr cmd get_log_pages", test_get_log_pages) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd set_feature", test_set_feature_cmd) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd set_feature_ns", test_set_feature_ns_cmd) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd get_feature", test_get_feature_cmd) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd get_feature_ns", test_get_feature_ns_cmd) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd abort_cmd", test_abort_cmd) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd io_raw_cmd", test_io_raw_cmd) == NULL
|
||||
|| CU_add_test(suite, "test ctrlr cmd io_raw_cmd_with_md", test_io_raw_cmd_with_md) == NULL
|
||||
|
Loading…
Reference in New Issue
Block a user