Skip to content

Commit

Permalink
nvmet: make sn stable once connection was established
Browse files Browse the repository at this point in the history
Once some host has connected to the target, make sure that the serial
number is stable and cannot be changed.

Reviewed-by: Max Gurtovoy <mgurtovoy@nvidia.com>
Signed-off-by: Noam Gottlieb <ngottlieb@nvidia.com>
Signed-off-by: Christoph Hellwig <hch@lst.de>
  • Loading branch information
Noam Gottlieb authored and Christoph Hellwig committed Jun 17, 2021
1 parent e13b061 commit 7ae023c
Show file tree
Hide file tree
Showing 3 changed files with 29 additions and 5 deletions.
6 changes: 6 additions & 0 deletions drivers/nvme/target/admin-cmd.c
Original file line number Diff line number Diff line change
Expand Up @@ -337,6 +337,12 @@ static void nvmet_execute_identify_ctrl(struct nvmet_req *req)
u32 cmd_capsule_size;
u16 status = 0;

if (!subsys->subsys_discovered) {
mutex_lock(&subsys->lock);
subsys->subsys_discovered = true;
mutex_unlock(&subsys->lock);
}

/*
* If there is no model number yet, set it now. It will then remain
* stable for the life time of the subsystem.
Expand Down
27 changes: 22 additions & 5 deletions drivers/nvme/target/configfs.c
Original file line number Diff line number Diff line change
Expand Up @@ -1044,12 +1044,18 @@ static ssize_t nvmet_subsys_attr_serial_show(struct config_item *item,
return snprintf(page, PAGE_SIZE, "%s\n", subsys->serial);
}

static ssize_t nvmet_subsys_attr_serial_store(struct config_item *item,
const char *page, size_t count)
static ssize_t
nvmet_subsys_attr_serial_store_locked(struct nvmet_subsys *subsys,
const char *page, size_t count)
{
struct nvmet_subsys *subsys = to_subsys(item);
int pos, len = strcspn(page, "\n");

if (subsys->subsys_discovered) {
pr_err("Can't set serial number. %s is already assigned\n",
subsys->serial);
return -EINVAL;
}

if (!len || len > NVMET_SN_MAX_SIZE) {
pr_err("Serial Number can not be empty or exceed %d Bytes\n",
NVMET_SN_MAX_SIZE);
Expand All @@ -1063,13 +1069,24 @@ static ssize_t nvmet_subsys_attr_serial_store(struct config_item *item,
}
}

memcpy_and_pad(subsys->serial, NVMET_SN_MAX_SIZE, page, len, ' ');

return count;
}

static ssize_t nvmet_subsys_attr_serial_store(struct config_item *item,
const char *page, size_t count)
{
struct nvmet_subsys *subsys = to_subsys(item);
ssize_t ret;

down_write(&nvmet_config_sem);
mutex_lock(&subsys->lock);
memcpy_and_pad(subsys->serial, NVMET_SN_MAX_SIZE, page, len, ' ');
ret = nvmet_subsys_attr_serial_store_locked(subsys, page, count);
mutex_unlock(&subsys->lock);
up_write(&nvmet_config_sem);

return count;
return ret;
}
CONFIGFS_ATTR(nvmet_subsys_, attr_serial);

Expand Down
1 change: 1 addition & 0 deletions drivers/nvme/target/nvmet.h
Original file line number Diff line number Diff line change
Expand Up @@ -231,6 +231,7 @@ struct nvmet_subsys {

u64 ver;
char serial[NVMET_SN_MAX_SIZE];
bool subsys_discovered;
char *subsysnqn;
bool pi_support;

Expand Down

0 comments on commit 7ae023c

Please sign in to comment.