nvme-loop: fix kernel oops in case of unhandled command
When nvmet_req_init() fails, __nvmet_req_complete() is called to handle the target request via .queue_response(), so nvme_loop_queue_response() shouldn't be called again for handling the failure. This patch fixes this case by the following way: - move blk_mq_start_request() before nvmet_req_init(), so nvme_loop_queue_response() may work well to complete this host request - don't call nvme_cleanup_cmd() which is done in nvme_loop_complete_rq() - don't call nvme_loop_queue_response() which is done via .queue_response() Signed-off-by: Ming Lei <ming.lei@redhat.com> Reviewed-by: Christoph Hellwig <hch@lst.de> [trimmed changelog] Signed-off-by: Keith Busch <keith.busch@intel.com> Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
parent
7ec6074ff0
commit
11d9ea6f2c
|
@ -174,15 +174,12 @@ static blk_status_t nvme_loop_queue_rq(struct blk_mq_hw_ctx *hctx,
|
|||
if (ret)
|
||||
return ret;
|
||||
|
||||
blk_mq_start_request(req);
|
||||
iod->cmd.common.flags |= NVME_CMD_SGL_METABUF;
|
||||
iod->req.port = nvmet_loop_port;
|
||||
if (!nvmet_req_init(&iod->req, &queue->nvme_cq,
|
||||
&queue->nvme_sq, &nvme_loop_ops)) {
|
||||
nvme_cleanup_cmd(req);
|
||||
blk_mq_start_request(req);
|
||||
nvme_loop_queue_response(&iod->req);
|
||||
&queue->nvme_sq, &nvme_loop_ops))
|
||||
return BLK_STS_OK;
|
||||
}
|
||||
|
||||
if (blk_rq_payload_bytes(req)) {
|
||||
iod->sg_table.sgl = iod->first_sgl;
|
||||
|
@ -196,8 +193,6 @@ static blk_status_t nvme_loop_queue_rq(struct blk_mq_hw_ctx *hctx,
|
|||
iod->req.transfer_len = blk_rq_payload_bytes(req);
|
||||
}
|
||||
|
||||
blk_mq_start_request(req);
|
||||
|
||||
schedule_work(&iod->work);
|
||||
return BLK_STS_OK;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue