Message ID | 20200930220414.562527-7-kbusch@kernel.org |
---|---|
State | New |
Headers | show |
Series | nvme qemu cleanups and fixes | expand |
> -----Original Message----- > From: Keith Busch <kbusch@kernel.org> > Sent: Wednesday, September 30, 2020 6:04 PM > To: qemu-block@nongnu.org; qemu-devel@nongnu.org; Klaus Jensen > <k.jensen@samsung.com> > Cc: Niklas Cassel <Niklas.Cassel@wdc.com>; Dmitry Fomichev > <Dmitry.Fomichev@wdc.com>; Kevin Wolf <kwolf@redhat.com>; Philippe > Mathieu-Daudé <philmd@redhat.com>; Keith Busch <kbusch@kernel.org> > Subject: [PATCH 6/9] hw/block/nvme: reject io commands if only admin > command set selected > > From: Klaus Jensen <k.jensen@samsung.com> > > If the host sets CC.CSS to 111b, all commands submitted to I/O queues > should be completed with status Invalid Command Opcode. > > Note that this is technically a v1.4 feature, but it does not hurt to > implement before we finally bump the reported version implemented. > > Signed-off-by: Klaus Jensen <k.jensen@samsung.com> > Signed-off-by: Keith Busch <kbusch@kernel.org> Reviewed-by: Dmitry Fomichev <dmitry.fomichev@wdc.com> > --- > hw/block/nvme.c | 4 ++++ > include/block/nvme.h | 5 +++++ > 2 files changed, 9 insertions(+) > > diff --git a/hw/block/nvme.c b/hw/block/nvme.c > index ec7363ea40..80730e1c03 100644 > --- a/hw/block/nvme.c > +++ b/hw/block/nvme.c > @@ -1026,6 +1026,10 @@ static uint16_t nvme_io_cmd(NvmeCtrl *n, > NvmeRequest *req) > trace_pci_nvme_io_cmd(nvme_cid(req), nsid, nvme_sqid(req), > req->cmd.opcode, nvme_io_opc_str(req->cmd.opcode)); > > + if (NVME_CC_CSS(n->bar.cc) == NVME_CC_CSS_ADMIN_ONLY) { > + return NVME_INVALID_OPCODE | NVME_DNR; > + } > + > if (!nvme_nsid_valid(n, nsid)) { > return NVME_INVALID_NSID | NVME_DNR; > } > diff --git a/include/block/nvme.h b/include/block/nvme.h > index 521533fd2a..6de2d5aa75 100644 > --- a/include/block/nvme.h > +++ b/include/block/nvme.h > @@ -115,6 +115,11 @@ enum NvmeCcMask { > #define NVME_CC_IOSQES(cc) ((cc >> CC_IOSQES_SHIFT) & > CC_IOSQES_MASK) > #define NVME_CC_IOCQES(cc) ((cc >> CC_IOCQES_SHIFT) & > CC_IOCQES_MASK) > > +enum NvmeCcCss { > + NVME_CC_CSS_NVM = 0x0, > + NVME_CC_CSS_ADMIN_ONLY = 0x7, > +}; > + > enum NvmeCstsShift { > CSTS_RDY_SHIFT = 0, > CSTS_CFS_SHIFT = 1, > -- > 2.24.1
diff --git a/hw/block/nvme.c b/hw/block/nvme.c index ec7363ea40..80730e1c03 100644 --- a/hw/block/nvme.c +++ b/hw/block/nvme.c @@ -1026,6 +1026,10 @@ static uint16_t nvme_io_cmd(NvmeCtrl *n, NvmeRequest *req) trace_pci_nvme_io_cmd(nvme_cid(req), nsid, nvme_sqid(req), req->cmd.opcode, nvme_io_opc_str(req->cmd.opcode)); + if (NVME_CC_CSS(n->bar.cc) == NVME_CC_CSS_ADMIN_ONLY) { + return NVME_INVALID_OPCODE | NVME_DNR; + } + if (!nvme_nsid_valid(n, nsid)) { return NVME_INVALID_NSID | NVME_DNR; } diff --git a/include/block/nvme.h b/include/block/nvme.h index 521533fd2a..6de2d5aa75 100644 --- a/include/block/nvme.h +++ b/include/block/nvme.h @@ -115,6 +115,11 @@ enum NvmeCcMask { #define NVME_CC_IOSQES(cc) ((cc >> CC_IOSQES_SHIFT) & CC_IOSQES_MASK) #define NVME_CC_IOCQES(cc) ((cc >> CC_IOCQES_SHIFT) & CC_IOCQES_MASK) +enum NvmeCcCss { + NVME_CC_CSS_NVM = 0x0, + NVME_CC_CSS_ADMIN_ONLY = 0x7, +}; + enum NvmeCstsShift { CSTS_RDY_SHIFT = 0, CSTS_CFS_SHIFT = 1,