mirror of https://github.com/xemu-project/xemu.git
hw/nvme fixes
* Fix CVE-2021-3947 * Controller hotplugging fixes -----BEGIN PGP SIGNATURE----- iQEzBAABCAAdFiEEUigzqnXi3OaiR2bATeGvMW1PDekFAmGXWUcACgkQTeGvMW1P DelFZQgAjcyzkhxqCYRDIwCdnSa/E2kND5vkmF/CIb5CEi4TPOUygVKfW551fhJP 0h8YfK2giD+d61iw+lgEED+4iCiqZzRqOQ62jNyEGejbw2ZTb7chGKEHzHznHx2w /2OamufO9rCS1bzqF0FyAi8dWBEXpIo88tWM717gCWmNEAKighI9gnJfEFqmsPkA g4GrxjtXdx5S0rhBUFKPRZ1fBheb2sUCDxPIV+kalCpYQn/ubjydBC7yAI7f5vNA GdKV8VjdXSEsGhtSSFgfJRyF/Tq4yrB9oWpq+h30QkqtuQlSvqxxxzsJKz7Y+YtA I/QaPATsq4qY8WPBKLvD9Kr4K1x0+Q== =BbXH -----END PGP SIGNATURE----- Merge tag 'nvme-fixes-for-6.2-pull-request' of git://git.infradead.org/qemu-nvme into staging hw/nvme fixes * Fix CVE-2021-3947 * Controller hotplugging fixes # gpg: Signature made Fri 19 Nov 2021 08:59:03 AM CET # gpg: using RSA key 522833AA75E2DCE6A24766C04DE1AF316D4F0DE9 # gpg: Good signature from "Klaus Jensen <its@irrelevant.dk>" [unknown] # gpg: aka "Klaus Jensen <k.jensen@samsung.com>" [unknown] # gpg: WARNING: This key is not certified with a trusted signature! # gpg: There is no indication that the signature belongs to the owner. # Primary key fingerprint: DDCA 4D9C 9EF9 31CC 3468 4272 63D5 6FC5 E55D A838 # Subkey fingerprint: 5228 33AA 75E2 DCE6 A247 66C0 4DE1 AF31 6D4F 0DE9 * tag 'nvme-fixes-for-6.2-pull-request' of git://git.infradead.org/qemu-nvme: hw/nvme: fix buffer overrun in nvme_changed_nslist (CVE-2021-3947) hw/nvme: change nvme-ns 'shared' default hw/nvme: reattach subsystem namespaces on hotplug Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
This commit is contained in:
commit
9c25e1db18
|
@ -110,28 +110,32 @@ multipath I/O.
|
||||||
This will create an NVM subsystem with two controllers. Having controllers
|
This will create an NVM subsystem with two controllers. Having controllers
|
||||||
linked to an ``nvme-subsys`` device allows additional ``nvme-ns`` parameters:
|
linked to an ``nvme-subsys`` device allows additional ``nvme-ns`` parameters:
|
||||||
|
|
||||||
``shared`` (default: ``off``)
|
``shared`` (default: ``on`` since 6.2)
|
||||||
Specifies that the namespace will be attached to all controllers in the
|
Specifies that the namespace will be attached to all controllers in the
|
||||||
subsystem. If set to ``off`` (the default), the namespace will remain a
|
subsystem. If set to ``off``, the namespace will remain a private namespace
|
||||||
private namespace and may only be attached to a single controller at a time.
|
and may only be attached to a single controller at a time. Shared namespaces
|
||||||
|
are always automatically attached to all controllers (also when controllers
|
||||||
|
are hotplugged).
|
||||||
|
|
||||||
``detached`` (default: ``off``)
|
``detached`` (default: ``off``)
|
||||||
If set to ``on``, the namespace will be be available in the subsystem, but
|
If set to ``on``, the namespace will be be available in the subsystem, but
|
||||||
not attached to any controllers initially.
|
not attached to any controllers initially. A shared namespace with this set
|
||||||
|
to ``on`` will never be automatically attached to controllers.
|
||||||
|
|
||||||
Thus, adding
|
Thus, adding
|
||||||
|
|
||||||
.. code-block:: console
|
.. code-block:: console
|
||||||
|
|
||||||
-drive file=nvm-1.img,if=none,id=nvm-1
|
-drive file=nvm-1.img,if=none,id=nvm-1
|
||||||
-device nvme-ns,drive=nvm-1,nsid=1,shared=on
|
-device nvme-ns,drive=nvm-1,nsid=1
|
||||||
-drive file=nvm-2.img,if=none,id=nvm-2
|
-drive file=nvm-2.img,if=none,id=nvm-2
|
||||||
-device nvme-ns,drive=nvm-2,nsid=3,detached=on
|
-device nvme-ns,drive=nvm-2,nsid=3,shared=off,detached=on
|
||||||
|
|
||||||
will cause NSID 1 will be a shared namespace (due to ``shared=on``) that is
|
will cause NSID 1 will be a shared namespace that is initially attached to both
|
||||||
initially attached to both controllers. NSID 3 will be a private namespace
|
controllers. NSID 3 will be a private namespace due to ``shared=off`` and only
|
||||||
(i.e. only attachable to a single controller at a time) and will not be
|
attachable to a single controller at a time. Additionally it will not be
|
||||||
attached to any controller initially (due to ``detached=on``).
|
attached to any controller initially (due to ``detached=on``) or to hotplugged
|
||||||
|
controllers.
|
||||||
|
|
||||||
Optional Features
|
Optional Features
|
||||||
=================
|
=================
|
||||||
|
|
|
@ -39,6 +39,7 @@
|
||||||
|
|
||||||
GlobalProperty hw_compat_6_1[] = {
|
GlobalProperty hw_compat_6_1[] = {
|
||||||
{ "vhost-user-vsock-device", "seqpacket", "off" },
|
{ "vhost-user-vsock-device", "seqpacket", "off" },
|
||||||
|
{ "nvme-ns", "shared", "off" },
|
||||||
};
|
};
|
||||||
const size_t hw_compat_6_1_len = G_N_ELEMENTS(hw_compat_6_1);
|
const size_t hw_compat_6_1_len = G_N_ELEMENTS(hw_compat_6_1);
|
||||||
|
|
||||||
|
|
|
@ -4168,6 +4168,11 @@ static uint16_t nvme_changed_nslist(NvmeCtrl *n, uint8_t rae, uint32_t buf_len,
|
||||||
int i = 0;
|
int i = 0;
|
||||||
uint32_t nsid;
|
uint32_t nsid;
|
||||||
|
|
||||||
|
if (off >= sizeof(nslist)) {
|
||||||
|
trace_pci_nvme_err_invalid_log_page_offset(off, sizeof(nslist));
|
||||||
|
return NVME_INVALID_FIELD | NVME_DNR;
|
||||||
|
}
|
||||||
|
|
||||||
memset(nslist, 0x0, sizeof(nslist));
|
memset(nslist, 0x0, sizeof(nslist));
|
||||||
trans_len = MIN(sizeof(nslist) - off, buf_len);
|
trans_len = MIN(sizeof(nslist) - off, buf_len);
|
||||||
|
|
||||||
|
|
|
@ -465,12 +465,6 @@ static void nvme_ns_realize(DeviceState *dev, Error **errp)
|
||||||
"linked to an nvme-subsys device");
|
"linked to an nvme-subsys device");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ns->params.shared) {
|
|
||||||
error_setg(errp, "shared requires that the nvme device is "
|
|
||||||
"linked to an nvme-subsys device");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
/*
|
/*
|
||||||
* If this namespace belongs to a subsystem (through a link on the
|
* If this namespace belongs to a subsystem (through a link on the
|
||||||
|
@ -532,7 +526,7 @@ static void nvme_ns_realize(DeviceState *dev, Error **errp)
|
||||||
static Property nvme_ns_props[] = {
|
static Property nvme_ns_props[] = {
|
||||||
DEFINE_BLOCK_PROPERTIES(NvmeNamespace, blkconf),
|
DEFINE_BLOCK_PROPERTIES(NvmeNamespace, blkconf),
|
||||||
DEFINE_PROP_BOOL("detached", NvmeNamespace, params.detached, false),
|
DEFINE_PROP_BOOL("detached", NvmeNamespace, params.detached, false),
|
||||||
DEFINE_PROP_BOOL("shared", NvmeNamespace, params.shared, false),
|
DEFINE_PROP_BOOL("shared", NvmeNamespace, params.shared, true),
|
||||||
DEFINE_PROP_UINT32("nsid", NvmeNamespace, params.nsid, 0),
|
DEFINE_PROP_UINT32("nsid", NvmeNamespace, params.nsid, 0),
|
||||||
DEFINE_PROP_UUID("uuid", NvmeNamespace, params.uuid),
|
DEFINE_PROP_UUID("uuid", NvmeNamespace, params.uuid),
|
||||||
DEFINE_PROP_UINT64("eui64", NvmeNamespace, params.eui64, 0),
|
DEFINE_PROP_UINT64("eui64", NvmeNamespace, params.eui64, 0),
|
||||||
|
|
|
@ -14,7 +14,7 @@
|
||||||
int nvme_subsys_register_ctrl(NvmeCtrl *n, Error **errp)
|
int nvme_subsys_register_ctrl(NvmeCtrl *n, Error **errp)
|
||||||
{
|
{
|
||||||
NvmeSubsystem *subsys = n->subsys;
|
NvmeSubsystem *subsys = n->subsys;
|
||||||
int cntlid;
|
int cntlid, nsid;
|
||||||
|
|
||||||
for (cntlid = 0; cntlid < ARRAY_SIZE(subsys->ctrls); cntlid++) {
|
for (cntlid = 0; cntlid < ARRAY_SIZE(subsys->ctrls); cntlid++) {
|
||||||
if (!subsys->ctrls[cntlid]) {
|
if (!subsys->ctrls[cntlid]) {
|
||||||
|
@ -29,12 +29,20 @@ int nvme_subsys_register_ctrl(NvmeCtrl *n, Error **errp)
|
||||||
|
|
||||||
subsys->ctrls[cntlid] = n;
|
subsys->ctrls[cntlid] = n;
|
||||||
|
|
||||||
|
for (nsid = 1; nsid < ARRAY_SIZE(subsys->namespaces); nsid++) {
|
||||||
|
NvmeNamespace *ns = subsys->namespaces[nsid];
|
||||||
|
if (ns && ns->params.shared && !ns->params.detached) {
|
||||||
|
nvme_attach_ns(n, ns);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return cntlid;
|
return cntlid;
|
||||||
}
|
}
|
||||||
|
|
||||||
void nvme_subsys_unregister_ctrl(NvmeSubsystem *subsys, NvmeCtrl *n)
|
void nvme_subsys_unregister_ctrl(NvmeSubsystem *subsys, NvmeCtrl *n)
|
||||||
{
|
{
|
||||||
subsys->ctrls[n->cntlid] = NULL;
|
subsys->ctrls[n->cntlid] = NULL;
|
||||||
|
n->cntlid = -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void nvme_subsys_setup(NvmeSubsystem *subsys)
|
static void nvme_subsys_setup(NvmeSubsystem *subsys)
|
||||||
|
|
Loading…
Reference in New Issue