nvme: move the fabrics queue ready check routines to core

queue_rq() in pci only checks if the dispatched queue (nvmeq) is ready,
e.g. not being suspended. Since nvme_alloc_admin_tags() in reset flow
restarts the admin queue, users are able to submit admin commands to a
controller before reset_work() completes. Commands submitted under this
condition may interfere with commands that performs identify, IO queue
setup in reset_work(), and may result in a hang described in the
following patch.

As seen in the fabrics, user commands are prevented from being executed
under inproper controller states. We may reuse this logic to maintain a
clear admin queue during reset_work().

Signed-off-by: Tao Chiu <taochiu@synology.com>
Signed-off-by: Cody Wong <codywong@synology.com>
Reviewed-by: Leon Chien <leonchien@synology.com>
Reviewed-by: Keith Busch <kbusch@kernel.org>
Signed-off-by: Christoph Hellwig <hch@lst.de>

authored by Tao Chiu and committed by Christoph Hellwig a9715744 51ad06cd

+83 -78
+60
drivers/nvme/host/core.c
··· 639 639 return req; 640 640 } 641 641 642 + /* 643 + * For something we're not in a state to send to the device the default action 644 + * is to busy it and retry it after the controller state is recovered. However, 645 + * if the controller is deleting or if anything is marked for failfast or 646 + * nvme multipath it is immediately failed. 647 + * 648 + * Note: commands used to initialize the controller will be marked for failfast. 649 + * Note: nvme cli/ioctl commands are marked for failfast. 650 + */ 651 + blk_status_t nvme_fail_nonready_command(struct nvme_ctrl *ctrl, 652 + struct request *rq) 653 + { 654 + if (ctrl->state != NVME_CTRL_DELETING_NOIO && 655 + ctrl->state != NVME_CTRL_DEAD && 656 + !test_bit(NVME_CTRL_FAILFAST_EXPIRED, &ctrl->flags) && 657 + !blk_noretry_request(rq) && !(rq->cmd_flags & REQ_NVME_MPATH)) 658 + return BLK_STS_RESOURCE; 659 + return nvme_host_path_error(rq); 660 + } 661 + EXPORT_SYMBOL_GPL(nvme_fail_nonready_command); 662 + 663 + bool __nvme_check_ready(struct nvme_ctrl *ctrl, struct request *rq, 664 + bool queue_live) 665 + { 666 + struct nvme_request *req = nvme_req(rq); 667 + 668 + /* 669 + * currently we have a problem sending passthru commands 670 + * on the admin_q if the controller is not LIVE because we can't 671 + * make sure that they are going out after the admin connect, 672 + * controller enable and/or other commands in the initialization 673 + * sequence. until the controller will be LIVE, fail with 674 + * BLK_STS_RESOURCE so that they will be rescheduled. 675 + */ 676 + if (rq->q == ctrl->admin_q && (req->flags & NVME_REQ_USERCMD)) 677 + return false; 678 + 679 + if (ctrl->ops->flags & NVME_F_FABRICS) { 680 + /* 681 + * Only allow commands on a live queue, except for the connect 682 + * command, which is require to set the queue live in the 683 + * appropinquate states. 684 + */ 685 + switch (ctrl->state) { 686 + case NVME_CTRL_CONNECTING: 687 + if (blk_rq_is_passthrough(rq) && nvme_is_fabrics(req->cmd) && 688 + req->cmd->fabrics.fctype == nvme_fabrics_type_connect) 689 + return true; 690 + break; 691 + default: 692 + break; 693 + case NVME_CTRL_DEAD: 694 + return false; 695 + } 696 + } 697 + 698 + return queue_live; 699 + } 700 + EXPORT_SYMBOL_GPL(__nvme_check_ready); 701 + 642 702 static int nvme_toggle_streams(struct nvme_ctrl *ctrl, bool enable) 643 703 { 644 704 struct nvme_command c;
-57
drivers/nvme/host/fabrics.c
··· 533 533 return NULL; 534 534 } 535 535 536 - /* 537 - * For something we're not in a state to send to the device the default action 538 - * is to busy it and retry it after the controller state is recovered. However, 539 - * if the controller is deleting or if anything is marked for failfast or 540 - * nvme multipath it is immediately failed. 541 - * 542 - * Note: commands used to initialize the controller will be marked for failfast. 543 - * Note: nvme cli/ioctl commands are marked for failfast. 544 - */ 545 - blk_status_t nvmf_fail_nonready_command(struct nvme_ctrl *ctrl, 546 - struct request *rq) 547 - { 548 - if (ctrl->state != NVME_CTRL_DELETING_NOIO && 549 - ctrl->state != NVME_CTRL_DEAD && 550 - !test_bit(NVME_CTRL_FAILFAST_EXPIRED, &ctrl->flags) && 551 - !blk_noretry_request(rq) && !(rq->cmd_flags & REQ_NVME_MPATH)) 552 - return BLK_STS_RESOURCE; 553 - return nvme_host_path_error(rq); 554 - } 555 - EXPORT_SYMBOL_GPL(nvmf_fail_nonready_command); 556 - 557 - bool __nvmf_check_ready(struct nvme_ctrl *ctrl, struct request *rq, 558 - bool queue_live) 559 - { 560 - struct nvme_request *req = nvme_req(rq); 561 - 562 - /* 563 - * currently we have a problem sending passthru commands 564 - * on the admin_q if the controller is not LIVE because we can't 565 - * make sure that they are going out after the admin connect, 566 - * controller enable and/or other commands in the initialization 567 - * sequence. until the controller will be LIVE, fail with 568 - * BLK_STS_RESOURCE so that they will be rescheduled. 569 - */ 570 - if (rq->q == ctrl->admin_q && (req->flags & NVME_REQ_USERCMD)) 571 - return false; 572 - 573 - /* 574 - * Only allow commands on a live queue, except for the connect command, 575 - * which is require to set the queue live in the appropinquate states. 576 - */ 577 - switch (ctrl->state) { 578 - case NVME_CTRL_CONNECTING: 579 - if (blk_rq_is_passthrough(rq) && nvme_is_fabrics(req->cmd) && 580 - req->cmd->fabrics.fctype == nvme_fabrics_type_connect) 581 - return true; 582 - break; 583 - default: 584 - break; 585 - case NVME_CTRL_DEAD: 586 - return false; 587 - } 588 - 589 - return queue_live; 590 - } 591 - EXPORT_SYMBOL_GPL(__nvmf_check_ready); 592 - 593 536 static const match_table_t opt_tokens = { 594 537 { NVMF_OPT_TRANSPORT, "transport=%s" }, 595 538 { NVMF_OPT_TRADDR, "traddr=%s" },
-13
drivers/nvme/host/fabrics.h
··· 184 184 void nvmf_free_options(struct nvmf_ctrl_options *opts); 185 185 int nvmf_get_address(struct nvme_ctrl *ctrl, char *buf, int size); 186 186 bool nvmf_should_reconnect(struct nvme_ctrl *ctrl); 187 - blk_status_t nvmf_fail_nonready_command(struct nvme_ctrl *ctrl, 188 - struct request *rq); 189 - bool __nvmf_check_ready(struct nvme_ctrl *ctrl, struct request *rq, 190 - bool queue_live); 191 187 bool nvmf_ip_options_match(struct nvme_ctrl *ctrl, 192 188 struct nvmf_ctrl_options *opts); 193 - 194 - static inline bool nvmf_check_ready(struct nvme_ctrl *ctrl, struct request *rq, 195 - bool queue_live) 196 - { 197 - if (likely(ctrl->state == NVME_CTRL_LIVE || 198 - ctrl->state == NVME_CTRL_DELETING)) 199 - return true; 200 - return __nvmf_check_ready(ctrl, rq, queue_live); 201 - } 202 189 203 190 #endif /* _NVME_FABRICS_H */
+2 -2
drivers/nvme/host/fc.c
··· 2766 2766 blk_status_t ret; 2767 2767 2768 2768 if (ctrl->rport->remoteport.port_state != FC_OBJSTATE_ONLINE || 2769 - !nvmf_check_ready(&queue->ctrl->ctrl, rq, queue_ready)) 2770 - return nvmf_fail_nonready_command(&queue->ctrl->ctrl, rq); 2769 + !nvme_check_ready(&queue->ctrl->ctrl, rq, queue_ready)) 2770 + return nvme_fail_nonready_command(&queue->ctrl->ctrl, rq); 2771 2771 2772 2772 ret = nvme_setup_cmd(ns, rq); 2773 2773 if (ret)
+15
drivers/nvme/host/nvme.h
··· 638 638 struct nvme_command *cmd, blk_mq_req_flags_t flags); 639 639 void nvme_cleanup_cmd(struct request *req); 640 640 blk_status_t nvme_setup_cmd(struct nvme_ns *ns, struct request *req); 641 + blk_status_t nvme_fail_nonready_command(struct nvme_ctrl *ctrl, 642 + struct request *req); 643 + bool __nvme_check_ready(struct nvme_ctrl *ctrl, struct request *rq, 644 + bool queue_live); 645 + 646 + static inline bool nvme_check_ready(struct nvme_ctrl *ctrl, struct request *rq, 647 + bool queue_live) 648 + { 649 + if (likely(ctrl->state == NVME_CTRL_LIVE)) 650 + return true; 651 + if (ctrl->ops->flags & NVME_F_FABRICS && 652 + ctrl->state == NVME_CTRL_DELETING) 653 + return true; 654 + return __nvme_check_ready(ctrl, rq, queue_live); 655 + } 641 656 int nvme_submit_sync_cmd(struct request_queue *q, struct nvme_command *cmd, 642 657 void *buf, unsigned bufflen); 643 658 int __nvme_submit_sync_cmd(struct request_queue *q, struct nvme_command *cmd,
+2 -2
drivers/nvme/host/rdma.c
··· 2050 2050 2051 2051 WARN_ON_ONCE(rq->tag < 0); 2052 2052 2053 - if (!nvmf_check_ready(&queue->ctrl->ctrl, rq, queue_ready)) 2054 - return nvmf_fail_nonready_command(&queue->ctrl->ctrl, rq); 2053 + if (!nvme_check_ready(&queue->ctrl->ctrl, rq, queue_ready)) 2054 + return nvme_fail_nonready_command(&queue->ctrl->ctrl, rq); 2055 2055 2056 2056 dev = queue->device->dev; 2057 2057
+2 -2
drivers/nvme/host/tcp.c
··· 2338 2338 bool queue_ready = test_bit(NVME_TCP_Q_LIVE, &queue->flags); 2339 2339 blk_status_t ret; 2340 2340 2341 - if (!nvmf_check_ready(&queue->ctrl->ctrl, rq, queue_ready)) 2342 - return nvmf_fail_nonready_command(&queue->ctrl->ctrl, rq); 2341 + if (!nvme_check_ready(&queue->ctrl->ctrl, rq, queue_ready)) 2342 + return nvme_fail_nonready_command(&queue->ctrl->ctrl, rq); 2343 2343 2344 2344 ret = nvme_tcp_setup_cmd_pdu(ns, rq); 2345 2345 if (unlikely(ret))
+2 -2
drivers/nvme/target/loop.c
··· 138 138 bool queue_ready = test_bit(NVME_LOOP_Q_LIVE, &queue->flags); 139 139 blk_status_t ret; 140 140 141 - if (!nvmf_check_ready(&queue->ctrl->ctrl, req, queue_ready)) 142 - return nvmf_fail_nonready_command(&queue->ctrl->ctrl, req); 141 + if (!nvme_check_ready(&queue->ctrl->ctrl, req, queue_ready)) 142 + return nvme_fail_nonready_command(&queue->ctrl->ctrl, req); 143 143 144 144 ret = nvme_setup_cmd(ns, req); 145 145 if (ret)