nvmf: implement Get Log Page - Changed NS List

Change-Id: I6219ace8deba0bfc3e3c7f6a4e00c0098584d5ee
Signed-off-by: Daniel Verkamp <daniel.verkamp@intel.com>
Reviewed-on: https://review.gerrithub.io/405122
Reviewed-by: Changpeng Liu <changpeng.liu@intel.com>
Reviewed-by: Shuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
Reviewed-by: Ben Walker <benjamin.walker@intel.com>
Tested-by: SPDK Automated Test System <sys_sgsw@intel.com>
This commit is contained in:
Daniel Verkamp 2018-03-23 14:20:04 -07:00 committed by Jim Harris
parent 0f15edee2d
commit 26541489ef
5 changed files with 69 additions and 20 deletions

View File

@ -988,10 +988,59 @@ spdk_nvmf_get_firmware_slot_log_page(void *buffer, uint64_t offset, uint32_t len
}
}
void
spdk_nvmf_ctrlr_ns_changed(struct spdk_nvmf_ctrlr *ctrlr, uint32_t nsid)
{
uint16_t max_changes = SPDK_COUNTOF(ctrlr->changed_ns_list.ns_list);
uint16_t i;
bool found = false;
for (i = 0; i < ctrlr->changed_ns_list_count; i++) {
if (ctrlr->changed_ns_list.ns_list[i] == nsid) {
/* nsid is already in the list */
found = true;
break;
}
}
if (!found) {
if (ctrlr->changed_ns_list_count == max_changes) {
/* Out of space - set first entry to FFFFFFFFh and zero-fill the rest. */
ctrlr->changed_ns_list.ns_list[0] = 0xFFFFFFFFu;
for (i = 1; i < max_changes; i++) {
ctrlr->changed_ns_list.ns_list[i] = 0;
}
} else {
ctrlr->changed_ns_list.ns_list[ctrlr->changed_ns_list_count++] = nsid;
}
}
spdk_nvmf_ctrlr_async_event_ns_notice(ctrlr);
}
static void
spdk_nvmf_get_changed_ns_list_log_page(struct spdk_nvmf_ctrlr *ctrlr,
void *buffer, uint64_t offset, uint32_t length)
{
size_t copy_length;
if (offset < sizeof(ctrlr->changed_ns_list)) {
copy_length = spdk_min(length, sizeof(ctrlr->changed_ns_list) - offset);
if (copy_length) {
memcpy(buffer, (char *)&ctrlr->changed_ns_list + offset, copy_length);
}
}
/* Clear log page each time it is read */
ctrlr->changed_ns_list_count = 0;
memset(&ctrlr->changed_ns_list, 0, sizeof(ctrlr->changed_ns_list));
}
static int
spdk_nvmf_ctrlr_get_log_page(struct spdk_nvmf_request *req)
{
struct spdk_nvmf_subsystem *subsystem = req->qpair->ctrlr->subsys;
struct spdk_nvmf_ctrlr *ctrlr = req->qpair->ctrlr;
struct spdk_nvmf_subsystem *subsystem = ctrlr->subsys;
struct spdk_nvme_cmd *cmd = &req->cmd->nvme_cmd;
struct spdk_nvme_cpl *response = &req->rsp->nvme_cpl;
uint64_t offset, len;
@ -1048,6 +1097,9 @@ spdk_nvmf_ctrlr_get_log_page(struct spdk_nvmf_request *req)
case SPDK_NVME_LOG_COMMAND_EFFECTS_LOG:
spdk_nvmf_get_cmds_and_effects_log_page(req->data, offset, len);
return SPDK_NVMF_REQUEST_EXEC_STATUS_COMPLETE;
case SPDK_NVME_LOG_CHANGED_NS_LIST:
spdk_nvmf_get_changed_ns_list_log_page(ctrlr, req->data, offset, len);
return SPDK_NVMF_REQUEST_EXEC_STATUS_COMPLETE;
default:
goto invalid_log_page;
}
@ -1568,12 +1620,7 @@ spdk_nvmf_ctrlr_async_event_ns_notice(struct spdk_nvmf_ctrlr *ctrlr)
event.bits.async_event_type = SPDK_NVME_ASYNC_EVENT_TYPE_NOTICE;
event.bits.async_event_info = SPDK_NVME_ASYNC_EVENT_NS_ATTR_CHANGED;
/* Alternatively, host may request Changed Namespace List log(04h)
* to determine which namespaces have changed. While here, we
* set invalid log page identifier to indicate that host doesn't
* need to send such log page.
*/
event.bits.log_page_identifier = 0;
event.bits.log_page_identifier = SPDK_NVME_LOG_CHANGED_NS_LIST;
/* If there is no outstanding AER request, queue the event. Then
* if an AER is later submitted, this event can be sent as a

View File

@ -189,6 +189,9 @@ struct spdk_nvmf_ctrlr {
union spdk_nvme_async_event_completion notice_event;
uint8_t hostid[16];
uint16_t changed_ns_list_count;
struct spdk_nvme_ns_list changed_ns_list;
TAILQ_ENTRY(spdk_nvmf_ctrlr) link;
};
@ -252,6 +255,7 @@ int spdk_nvmf_ctrlr_process_admin_cmd(struct spdk_nvmf_request *req);
int spdk_nvmf_ctrlr_process_io_cmd(struct spdk_nvmf_request *req);
bool spdk_nvmf_ctrlr_dsm_supported(struct spdk_nvmf_ctrlr *ctrlr);
bool spdk_nvmf_ctrlr_write_zeroes_supported(struct spdk_nvmf_ctrlr *ctrlr);
void spdk_nvmf_ctrlr_ns_changed(struct spdk_nvmf_ctrlr *ctrlr, uint32_t nsid);
int spdk_nvmf_bdev_ctrlr_identify_ns(struct spdk_nvmf_ns *ns, struct spdk_nvme_ns_data *nsdata);

View File

@ -816,7 +816,7 @@ spdk_nvmf_subsystem_ns_changed(struct spdk_nvmf_subsystem *subsystem, uint32_t n
struct spdk_nvmf_ctrlr *ctrlr;
TAILQ_FOREACH(ctrlr, &subsystem->ctrlrs, link) {
spdk_nvmf_ctrlr_async_event_ns_notice(ctrlr);
spdk_nvmf_ctrlr_ns_changed(ctrlr, nsid);
}
}

View File

@ -153,6 +153,11 @@ spdk_nvme_transport_id_compare(const struct spdk_nvme_transport_id *trid1,
return 0;
}
void
spdk_nvmf_ctrlr_ns_changed(struct spdk_nvmf_ctrlr *ctrlr, uint32_t nsid)
{
}
void
spdk_nvmf_ctrlr_destruct(struct spdk_nvmf_ctrlr *ctrlr)
{
@ -186,12 +191,6 @@ spdk_nvmf_poll_group_resume_subsystem(struct spdk_nvmf_poll_group *group,
return 0;
}
int
spdk_nvmf_ctrlr_async_event_ns_notice(struct spdk_nvmf_ctrlr *ctrlr)
{
return 0;
}
static void
test_discovery_log(void)
{

View File

@ -183,6 +183,11 @@ spdk_nvmf_ctrlr_destruct(struct spdk_nvmf_ctrlr *ctrlr)
{
}
void
spdk_nvmf_ctrlr_ns_changed(struct spdk_nvmf_ctrlr *ctrlr, uint32_t nsid)
{
}
int
spdk_bdev_open(struct spdk_bdev *bdev, bool write, spdk_bdev_remove_cb_t remove_cb,
void *remove_ctx, struct spdk_bdev_desc **desc)
@ -207,12 +212,6 @@ spdk_bdev_get_uuid(const struct spdk_bdev *bdev)
return &bdev->uuid;
}
int
spdk_nvmf_ctrlr_async_event_ns_notice(struct spdk_nvmf_ctrlr *ctrlr)
{
return 0;
}
static void
test_spdk_nvmf_subsystem_add_ns(void)
{