Skip to content

Commit 49d82b1

Browse files
committed
Merge tag 'nvme-5.15-2021-09-07' of git://git.infradead.org/nvme into block-5.15
Pull NVMe fixes from Christoph: "nvme fixes for Linux 5.15 - fix nvmet command set reporting for passthrough controllers (Adam Manzanares) - updated - update a MAINTAINERS email address (Chaitanya Kulkarni) - set QUEUE_FLAG_NOWAIT for nvme-multipth (me) - handle errors from add_disk() (Luis Chamberlain) - update the keep alive interval when kato is modified (Tatsuya Sasaki) - fix a buffer overrun in nvmet_subsys_attr_serial (Hannes Reinecke) - do not reset transport on data digest errors in nvme-tcp (Daniel Wagner) - only call synchronize_srcu when clearing current path (Daniel Wagner) - revalidate paths during rescan (Hannes Reinecke)" * tag 'nvme-5.15-2021-09-07' of git://git.infradead.org/nvme: nvme: update MAINTAINERS email address nvme: add error handling support for add_disk() nvme: only call synchronize_srcu when clearing current path nvme: update keep alive interval when kato is modified nvme-tcp: Do not reset transport on data digest errors nvmet: fixup buffer overrun in nvmet_subsys_attr_serial() nvmet: return bool from nvmet_passthru_ctrl and nvmet_is_passthru_req nvmet: looks at the passthrough controller when initializing CAP nvme: move nvme_multi_css into nvme.h nvme-multipath: revalidate paths during rescan nvme-multipath: set QUEUE_FLAG_NOWAIT
2 parents 884f0e8 + aff959c commit 49d82b1

File tree

10 files changed

+132
-31
lines changed

10 files changed

+132
-31
lines changed

MAINTAINERS

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13367,7 +13367,7 @@ F: include/linux/nvme-fc.h
1336713367
NVM EXPRESS TARGET DRIVER
1336813368
M: Christoph Hellwig <[email protected]>
1336913369
M: Sagi Grimberg <[email protected]>
13370-
M: Chaitanya Kulkarni <chaitanya.kulkarni@wdc.com>
13370+
M: Chaitanya Kulkarni <kch@nvidia.com>
1337113371
1337213372
S: Supported
1337313373
W: http://git.infradead.org/nvme.git

drivers/nvme/host/core.c

Lines changed: 57 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -116,6 +116,8 @@ static struct class *nvme_ns_chr_class;
116116
static void nvme_put_subsystem(struct nvme_subsystem *subsys);
117117
static void nvme_remove_invalid_namespaces(struct nvme_ctrl *ctrl,
118118
unsigned nsid);
119+
static void nvme_update_keep_alive(struct nvme_ctrl *ctrl,
120+
struct nvme_command *cmd);
119121

120122
/*
121123
* Prepare a queue for teardown.
@@ -1152,7 +1154,8 @@ static u32 nvme_passthru_start(struct nvme_ctrl *ctrl, struct nvme_ns *ns,
11521154
return effects;
11531155
}
11541156

1155-
static void nvme_passthru_end(struct nvme_ctrl *ctrl, u32 effects)
1157+
static void nvme_passthru_end(struct nvme_ctrl *ctrl, u32 effects,
1158+
struct nvme_command *cmd, int status)
11561159
{
11571160
if (effects & NVME_CMD_EFFECTS_CSE_MASK) {
11581161
nvme_unfreeze(ctrl);
@@ -1167,6 +1170,26 @@ static void nvme_passthru_end(struct nvme_ctrl *ctrl, u32 effects)
11671170
nvme_queue_scan(ctrl);
11681171
flush_work(&ctrl->scan_work);
11691172
}
1173+
1174+
switch (cmd->common.opcode) {
1175+
case nvme_admin_set_features:
1176+
switch (le32_to_cpu(cmd->common.cdw10) & 0xFF) {
1177+
case NVME_FEAT_KATO:
1178+
/*
1179+
* Keep alive commands interval on the host should be
1180+
* updated when KATO is modified by Set Features
1181+
* commands.
1182+
*/
1183+
if (!status)
1184+
nvme_update_keep_alive(ctrl, cmd);
1185+
break;
1186+
default:
1187+
break;
1188+
}
1189+
break;
1190+
default:
1191+
break;
1192+
}
11701193
}
11711194

11721195
int nvme_execute_passthru_rq(struct request *rq)
@@ -1181,7 +1204,7 @@ int nvme_execute_passthru_rq(struct request *rq)
11811204
effects = nvme_passthru_start(ctrl, ns, cmd->common.opcode);
11821205
ret = nvme_execute_rq(disk, rq, false);
11831206
if (effects) /* nothing to be done for zero cmd effects */
1184-
nvme_passthru_end(ctrl, effects);
1207+
nvme_passthru_end(ctrl, effects, cmd, ret);
11851208

11861209
return ret;
11871210
}
@@ -1269,6 +1292,21 @@ void nvme_stop_keep_alive(struct nvme_ctrl *ctrl)
12691292
}
12701293
EXPORT_SYMBOL_GPL(nvme_stop_keep_alive);
12711294

1295+
static void nvme_update_keep_alive(struct nvme_ctrl *ctrl,
1296+
struct nvme_command *cmd)
1297+
{
1298+
unsigned int new_kato =
1299+
DIV_ROUND_UP(le32_to_cpu(cmd->common.cdw11), 1000);
1300+
1301+
dev_info(ctrl->device,
1302+
"keep alive interval updated from %u ms to %u ms\n",
1303+
ctrl->kato * 1000 / 2, new_kato * 1000 / 2);
1304+
1305+
nvme_stop_keep_alive(ctrl);
1306+
ctrl->kato = new_kato;
1307+
nvme_start_keep_alive(ctrl);
1308+
}
1309+
12721310
/*
12731311
* In NVMe 1.0 the CNS field was just a binary controller or namespace
12741312
* flag, thus sending any new CNS opcodes has a big chance of not working.
@@ -1302,11 +1340,6 @@ static int nvme_identify_ctrl(struct nvme_ctrl *dev, struct nvme_id_ctrl **id)
13021340
return error;
13031341
}
13041342

1305-
static bool nvme_multi_css(struct nvme_ctrl *ctrl)
1306-
{
1307-
return (ctrl->ctrl_config & NVME_CC_CSS_MASK) == NVME_CC_CSS_CSI;
1308-
}
1309-
13101343
static int nvme_process_ns_desc(struct nvme_ctrl *ctrl, struct nvme_ns_ids *ids,
13111344
struct nvme_ns_id_desc *cur, bool *csi_seen)
13121345
{
@@ -1874,6 +1907,7 @@ static int nvme_update_ns_info(struct nvme_ns *ns, struct nvme_id_ns *id)
18741907
goto out_unfreeze;
18751908
}
18761909

1910+
set_bit(NVME_NS_READY, &ns->flags);
18771911
blk_mq_unfreeze_queue(ns->disk->queue);
18781912

18791913
if (blk_queue_is_zoned(ns->queue)) {
@@ -1885,6 +1919,7 @@ static int nvme_update_ns_info(struct nvme_ns *ns, struct nvme_id_ns *id)
18851919
if (nvme_ns_head_multipath(ns->head)) {
18861920
blk_mq_freeze_queue(ns->head->disk->queue);
18871921
nvme_update_disk_info(ns->head->disk, ns, id);
1922+
nvme_mpath_revalidate_paths(ns);
18881923
blk_stack_limits(&ns->head->disk->queue->limits,
18891924
&ns->queue->limits, 0);
18901925
disk_update_readahead(ns->head->disk);
@@ -3763,7 +3798,9 @@ static void nvme_alloc_ns(struct nvme_ctrl *ctrl, unsigned nsid,
37633798

37643799
nvme_get_ctrl(ctrl);
37653800

3766-
device_add_disk(ctrl->device, ns->disk, nvme_ns_id_attr_groups);
3801+
if (device_add_disk(ctrl->device, ns->disk, nvme_ns_id_attr_groups))
3802+
goto out_cleanup_ns_from_list;
3803+
37673804
if (!nvme_ns_head_multipath(ns->head))
37683805
nvme_add_ns_cdev(ns);
37693806

@@ -3773,6 +3810,11 @@ static void nvme_alloc_ns(struct nvme_ctrl *ctrl, unsigned nsid,
37733810

37743811
return;
37753812

3813+
out_cleanup_ns_from_list:
3814+
nvme_put_ctrl(ctrl);
3815+
down_write(&ctrl->namespaces_rwsem);
3816+
list_del_init(&ns->list);
3817+
up_write(&ctrl->namespaces_rwsem);
37763818
out_unlink_ns:
37773819
mutex_lock(&ctrl->subsys->lock);
37783820
list_del_rcu(&ns->siblings);
@@ -3795,16 +3837,20 @@ static void nvme_ns_remove(struct nvme_ns *ns)
37953837
if (test_and_set_bit(NVME_NS_REMOVING, &ns->flags))
37963838
return;
37973839

3840+
clear_bit(NVME_NS_READY, &ns->flags);
37983841
set_capacity(ns->disk, 0);
37993842
nvme_fault_inject_fini(&ns->fault_inject);
38003843

38013844
mutex_lock(&ns->ctrl->subsys->lock);
38023845
list_del_rcu(&ns->siblings);
38033846
mutex_unlock(&ns->ctrl->subsys->lock);
38043847

3805-
synchronize_rcu(); /* guarantee not available in head->list */
3806-
nvme_mpath_clear_current_path(ns);
3807-
synchronize_srcu(&ns->head->srcu); /* wait for concurrent submissions */
3848+
/* guarantee not available in head->list */
3849+
synchronize_rcu();
3850+
3851+
/* wait for concurrent submissions */
3852+
if (nvme_mpath_clear_current_path(ns))
3853+
synchronize_srcu(&ns->head->srcu);
38083854

38093855
if (!nvme_ns_head_multipath(ns->head))
38103856
nvme_cdev_del(&ns->cdev, &ns->cdev_device);

drivers/nvme/host/multipath.c

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -147,6 +147,21 @@ void nvme_mpath_clear_ctrl_paths(struct nvme_ctrl *ctrl)
147147
mutex_unlock(&ctrl->scan_lock);
148148
}
149149

150+
void nvme_mpath_revalidate_paths(struct nvme_ns *ns)
151+
{
152+
struct nvme_ns_head *head = ns->head;
153+
sector_t capacity = get_capacity(head->disk);
154+
int node;
155+
156+
list_for_each_entry_rcu(ns, &head->list, siblings) {
157+
if (capacity != get_capacity(ns->disk))
158+
clear_bit(NVME_NS_READY, &ns->flags);
159+
}
160+
161+
for_each_node(node)
162+
rcu_assign_pointer(head->current_path[node], NULL);
163+
}
164+
150165
static bool nvme_path_is_disabled(struct nvme_ns *ns)
151166
{
152167
/*
@@ -158,7 +173,7 @@ static bool nvme_path_is_disabled(struct nvme_ns *ns)
158173
ns->ctrl->state != NVME_CTRL_DELETING)
159174
return true;
160175
if (test_bit(NVME_NS_ANA_PENDING, &ns->flags) ||
161-
test_bit(NVME_NS_REMOVING, &ns->flags))
176+
!test_bit(NVME_NS_READY, &ns->flags))
162177
return true;
163178
return false;
164179
}
@@ -465,6 +480,8 @@ int nvme_mpath_alloc_disk(struct nvme_ctrl *ctrl, struct nvme_ns_head *head)
465480
ctrl->subsys->instance, head->instance);
466481

467482
blk_queue_flag_set(QUEUE_FLAG_NONROT, head->disk->queue);
483+
blk_queue_flag_set(QUEUE_FLAG_NOWAIT, head->disk->queue);
484+
468485
/* set to a default value of 512 until the disk is validated */
469486
blk_queue_logical_block_size(head->disk->queue, 512);
470487
blk_set_stacking_limits(&head->disk->queue->limits);

drivers/nvme/host/nvme.h

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -456,6 +456,7 @@ struct nvme_ns {
456456
#define NVME_NS_DEAD 1
457457
#define NVME_NS_ANA_PENDING 2
458458
#define NVME_NS_FORCE_RO 3
459+
#define NVME_NS_READY 4
459460

460461
struct cdev cdev;
461462
struct device cdev_device;
@@ -748,6 +749,7 @@ void nvme_mpath_init_ctrl(struct nvme_ctrl *ctrl);
748749
void nvme_mpath_uninit(struct nvme_ctrl *ctrl);
749750
void nvme_mpath_stop(struct nvme_ctrl *ctrl);
750751
bool nvme_mpath_clear_current_path(struct nvme_ns *ns);
752+
void nvme_mpath_revalidate_paths(struct nvme_ns *ns);
751753
void nvme_mpath_clear_ctrl_paths(struct nvme_ctrl *ctrl);
752754
void nvme_mpath_shutdown_disk(struct nvme_ns_head *head);
753755

@@ -795,6 +797,9 @@ static inline bool nvme_mpath_clear_current_path(struct nvme_ns *ns)
795797
{
796798
return false;
797799
}
800+
static inline void nvme_mpath_revalidate_paths(struct nvme_ns *ns)
801+
{
802+
}
798803
static inline void nvme_mpath_clear_ctrl_paths(struct nvme_ctrl *ctrl)
799804
{
800805
}
@@ -887,4 +892,9 @@ struct nvme_ctrl *nvme_ctrl_from_file(struct file *file);
887892
struct nvme_ns *nvme_find_get_ns(struct nvme_ctrl *ctrl, unsigned nsid);
888893
void nvme_put_ns(struct nvme_ns *ns);
889894

895+
static inline bool nvme_multi_css(struct nvme_ctrl *ctrl)
896+
{
897+
return (ctrl->ctrl_config & NVME_CC_CSS_MASK) == NVME_CC_CSS_CSI;
898+
}
899+
890900
#endif /* _NVME_H */

drivers/nvme/host/tcp.c

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,7 @@ struct nvme_tcp_request {
4545
u32 pdu_len;
4646
u32 pdu_sent;
4747
u16 ttag;
48+
__le16 status;
4849
struct list_head entry;
4950
struct llist_node lentry;
5051
__le32 ddgst;
@@ -485,6 +486,7 @@ static void nvme_tcp_error_recovery(struct nvme_ctrl *ctrl)
485486
static int nvme_tcp_process_nvme_cqe(struct nvme_tcp_queue *queue,
486487
struct nvme_completion *cqe)
487488
{
489+
struct nvme_tcp_request *req;
488490
struct request *rq;
489491

490492
rq = nvme_find_rq(nvme_tcp_tagset(queue), cqe->command_id);
@@ -496,7 +498,11 @@ static int nvme_tcp_process_nvme_cqe(struct nvme_tcp_queue *queue,
496498
return -EINVAL;
497499
}
498500

499-
if (!nvme_try_complete_req(rq, cqe->status, cqe->result))
501+
req = blk_mq_rq_to_pdu(rq);
502+
if (req->status == cpu_to_le16(NVME_SC_SUCCESS))
503+
req->status = cqe->status;
504+
505+
if (!nvme_try_complete_req(rq, req->status, cqe->result))
500506
nvme_complete_rq(rq);
501507
queue->nr_cqe++;
502508

@@ -758,7 +764,8 @@ static int nvme_tcp_recv_data(struct nvme_tcp_queue *queue, struct sk_buff *skb,
758764
queue->ddgst_remaining = NVME_TCP_DIGEST_LENGTH;
759765
} else {
760766
if (pdu->hdr.flags & NVME_TCP_F_DATA_SUCCESS) {
761-
nvme_tcp_end_request(rq, NVME_SC_SUCCESS);
767+
nvme_tcp_end_request(rq,
768+
le16_to_cpu(req->status));
762769
queue->nr_cqe++;
763770
}
764771
nvme_tcp_init_recv_ctx(queue);
@@ -788,18 +795,24 @@ static int nvme_tcp_recv_ddgst(struct nvme_tcp_queue *queue,
788795
return 0;
789796

790797
if (queue->recv_ddgst != queue->exp_ddgst) {
798+
struct request *rq = nvme_cid_to_rq(nvme_tcp_tagset(queue),
799+
pdu->command_id);
800+
struct nvme_tcp_request *req = blk_mq_rq_to_pdu(rq);
801+
802+
req->status = cpu_to_le16(NVME_SC_DATA_XFER_ERROR);
803+
791804
dev_err(queue->ctrl->ctrl.device,
792805
"data digest error: recv %#x expected %#x\n",
793806
le32_to_cpu(queue->recv_ddgst),
794807
le32_to_cpu(queue->exp_ddgst));
795-
return -EIO;
796808
}
797809

798810
if (pdu->hdr.flags & NVME_TCP_F_DATA_SUCCESS) {
799811
struct request *rq = nvme_cid_to_rq(nvme_tcp_tagset(queue),
800812
pdu->command_id);
813+
struct nvme_tcp_request *req = blk_mq_rq_to_pdu(rq);
801814

802-
nvme_tcp_end_request(rq, NVME_SC_SUCCESS);
815+
nvme_tcp_end_request(rq, le16_to_cpu(req->status));
803816
queue->nr_cqe++;
804817
}
805818

@@ -2293,6 +2306,7 @@ static blk_status_t nvme_tcp_setup_cmd_pdu(struct nvme_ns *ns,
22932306
return ret;
22942307

22952308
req->state = NVME_TCP_SEND_CMD_PDU;
2309+
req->status = cpu_to_le16(NVME_SC_SUCCESS);
22962310
req->offset = 0;
22972311
req->data_sent = 0;
22982312
req->pdu_len = 0;

drivers/nvme/target/admin-cmd.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1015,7 +1015,7 @@ u16 nvmet_parse_admin_cmd(struct nvmet_req *req)
10151015
if (unlikely(ret))
10161016
return ret;
10171017

1018-
if (nvmet_req_passthru_ctrl(req))
1018+
if (nvmet_is_passthru_req(req))
10191019
return nvmet_parse_passthru_admin_cmd(req);
10201020

10211021
switch (cmd->common.opcode) {

drivers/nvme/target/configfs.c

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1028,7 +1028,7 @@ nvmet_subsys_attr_version_store_locked(struct nvmet_subsys *subsys,
10281028
}
10291029

10301030
/* passthru subsystems use the underlying controller's version */
1031-
if (nvmet_passthru_ctrl(subsys))
1031+
if (nvmet_is_passthru_subsys(subsys))
10321032
return -EINVAL;
10331033

10341034
ret = sscanf(page, "%d.%d.%d\n", &major, &minor, &tertiary);
@@ -1067,7 +1067,8 @@ static ssize_t nvmet_subsys_attr_serial_show(struct config_item *item,
10671067
{
10681068
struct nvmet_subsys *subsys = to_subsys(item);
10691069

1070-
return snprintf(page, PAGE_SIZE, "%s\n", subsys->serial);
1070+
return snprintf(page, PAGE_SIZE, "%*s\n",
1071+
NVMET_SN_MAX_SIZE, subsys->serial);
10711072
}
10721073

10731074
static ssize_t

drivers/nvme/target/core.c

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -553,7 +553,7 @@ int nvmet_ns_enable(struct nvmet_ns *ns)
553553
mutex_lock(&subsys->lock);
554554
ret = 0;
555555

556-
if (nvmet_passthru_ctrl(subsys)) {
556+
if (nvmet_is_passthru_subsys(subsys)) {
557557
pr_info("cannot enable both passthru and regular namespaces for a single subsystem");
558558
goto out_unlock;
559559
}
@@ -869,7 +869,7 @@ static u16 nvmet_parse_io_cmd(struct nvmet_req *req)
869869
if (unlikely(ret))
870870
return ret;
871871

872-
if (nvmet_req_passthru_ctrl(req))
872+
if (nvmet_is_passthru_req(req))
873873
return nvmet_parse_passthru_io_cmd(req);
874874

875875
ret = nvmet_req_find_ns(req);
@@ -1206,6 +1206,9 @@ static void nvmet_init_cap(struct nvmet_ctrl *ctrl)
12061206
ctrl->cap |= (15ULL << 24);
12071207
/* maximum queue entries supported: */
12081208
ctrl->cap |= NVMET_QUEUE_SIZE - 1;
1209+
1210+
if (nvmet_is_passthru_subsys(ctrl->subsys))
1211+
nvmet_passthrough_override_cap(ctrl);
12091212
}
12101213

12111214
struct nvmet_ctrl *nvmet_ctrl_find_get(const char *subsysnqn,
@@ -1363,8 +1366,6 @@ u16 nvmet_alloc_ctrl(const char *subsysnqn, const char *hostnqn,
13631366
goto out_put_subsystem;
13641367
mutex_init(&ctrl->lock);
13651368

1366-
nvmet_init_cap(ctrl);
1367-
13681369
ctrl->port = req->port;
13691370

13701371
INIT_WORK(&ctrl->async_event_work, nvmet_async_event_work);
@@ -1378,6 +1379,7 @@ u16 nvmet_alloc_ctrl(const char *subsysnqn, const char *hostnqn,
13781379

13791380
kref_init(&ctrl->ref);
13801381
ctrl->subsys = subsys;
1382+
nvmet_init_cap(ctrl);
13811383
WRITE_ONCE(ctrl->aen_enabled, NVMET_AEN_CFG_OPTIONAL);
13821384

13831385
ctrl->changed_ns_list = kmalloc_array(NVME_MAX_CHANGED_NAMESPACES,

0 commit comments

Comments
 (0)