SHA256
1
0
forked from pool/qemu

Accepting request 910154 from home:jziviani:branches:Virtualization

- Add stable patches from upstream:
  block-nvme-Fix-VFIO_MAP_DMA-failed-No-sp.patch
  hw-net-can-sja1000-fix-buff2frame_bas-an.patch
  hw-pci-host-q35-Ignore-write-of-reserved.patch

OBS-URL: https://build.opensuse.org/request/show/910154
OBS-URL: https://build.opensuse.org/package/show/Virtualization/qemu?expand=0&rev=663
This commit is contained in:
José Ricardo Ziviani 2021-08-04 12:54:54 +00:00 committed by Git OBS Bridge
parent 183c086c65
commit 06c7333dfc
6 changed files with 231 additions and 3 deletions

View File

@ -0,0 +1,92 @@
From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= <philmd@redhat.com>
Date: Fri, 23 Jul 2021 21:58:43 +0200
Subject: block/nvme: Fix VFIO_MAP_DMA failed: No space left on device
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Git-commit: 15a730e7a3aaac180df72cd5730e0617bcf44a5a
When the NVMe block driver was introduced (see commit bdd6a90a9e5,
January 2018), Linux VFIO_IOMMU_MAP_DMA ioctl was only returning
-ENOMEM in case of error. The driver was correctly handling the
error path to recycle its volatile IOVA mappings.
To fix CVE-2019-3882, Linux commit 492855939bdb ("vfio/type1: Limit
DMA mappings per container", April 2019) added the -ENOSPC error to
signal the user exhausted the DMA mappings available for a container.
The block driver started to mis-behave:
qemu-system-x86_64: VFIO_MAP_DMA failed: No space left on device
(qemu)
(qemu) info status
VM status: paused (io-error)
(qemu) c
VFIO_MAP_DMA failed: No space left on device
(qemu) c
VFIO_MAP_DMA failed: No space left on device
(The VM is not resumable from here, hence stuck.)
Fix by handling the new -ENOSPC error (when DMA mappings are
exhausted) without any distinction to the current -ENOMEM error,
so we don't change the behavior on old kernels where the CVE-2019-3882
fix is not present.
An easy way to reproduce this bug is to restrict the DMA mapping
limit (65535 by default) when loading the VFIO IOMMU module:
# modprobe vfio_iommu_type1 dma_entry_limit=666
Cc: qemu-stable@nongnu.org
Cc: Fam Zheng <fam@euphon.net>
Cc: Maxim Levitsky <mlevitsk@redhat.com>
Cc: Alex Williamson <alex.williamson@redhat.com>
Reported-by: Michal Prívozník <mprivozn@redhat.com>
Signed-off-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Message-id: 20210723195843.1032825-1-philmd@redhat.com
Fixes: bdd6a90a9e5 ("block: Add VFIO based NVMe driver")
Buglink: https://bugs.launchpad.net/qemu/+bug/1863333
Resolves: https://gitlab.com/qemu-project/qemu/-/issues/65
Signed-off-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
Signed-off-by: Jose R. Ziviani <jziviani@suse.de>
---
block/nvme.c | 22 ++++++++++++++++++++++
1 file changed, 22 insertions(+)
diff --git a/block/nvme.c b/block/nvme.c
index 2b5421e7aa6e0a3bfaf403203c9b..e8dbbc23177d8e89d67349fc15a8 100644
--- a/block/nvme.c
+++ b/block/nvme.c
@@ -1030,7 +1030,29 @@ try_map:
r = qemu_vfio_dma_map(s->vfio,
qiov->iov[i].iov_base,
len, true, &iova);
+ if (r == -ENOSPC) {
+ /*
+ * In addition to the -ENOMEM error, the VFIO_IOMMU_MAP_DMA
+ * ioctl returns -ENOSPC to signal the user exhausted the DMA
+ * mappings available for a container since Linux kernel commit
+ * 492855939bdb ("vfio/type1: Limit DMA mappings per container",
+ * April 2019, see CVE-2019-3882).
+ *
+ * This block driver already handles this error path by checking
+ * for the -ENOMEM error, so we directly replace -ENOSPC by
+ * -ENOMEM. Beside, -ENOSPC has a specific meaning for blockdev
+ * coroutines: it triggers BLOCKDEV_ON_ERROR_ENOSPC and
+ * BLOCK_ERROR_ACTION_STOP which stops the VM, asking the operator
+ * to add more storage to the blockdev. Not something we can do
+ * easily with an IOMMU :)
+ */
+ r = -ENOMEM;
+ }
if (r == -ENOMEM && retry) {
+ /*
+ * We exhausted the DMA mappings available for our container:
+ * recycle the volatile IOVA mappings.
+ */
retry = false;
trace_nvme_dma_flush_queue_wait(s);
if (s->dma_map_count) {

View File

@ -1,3 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:8ec63ad5df6ad6e4aa0b206d4db157c88cf8ae8bfd8261a7332f7c6a1f24cab8
size 75016
oid sha256:f01e2ec49bb5088e9e97f58d8fc422acb6760c387e1313e49a4d13979a5b48c8
size 77828

View File

@ -0,0 +1,51 @@
From: Pavel Pisa <pisa@cmp.felk.cvut.cz>
Date: Thu, 29 Jul 2021 14:33:27 +0200
Subject: hw/net/can: sja1000 fix buff2frame_bas and buff2frame_pel when dlc is
out of std CAN 8 bytes
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Git-commit: 11744862f27b9ba6488a247d2fd6bb83d9bc3c8d
Problem reported by openEuler fuzz-sig group.
The buff2frame_bas function (hw\net\can\can_sja1000.c)
infoleak(qemu5.x~qemu6.x) or stack-overflow(qemu 4.x).
Reported-by: Qiang Ning <ningqiang1@huawei.com>
Cc: qemu-stable@nongnu.org
Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
Signed-off-by: Pavel Pisa <pisa@cmp.felk.cvut.cz>
Signed-off-by: Jason Wang <jasowang@redhat.com>
Signed-off-by: Jose R. Ziviani <jziviani@suse.de>
---
hw/net/can/can_sja1000.c | 8 ++++++++
1 file changed, 8 insertions(+)
diff --git a/hw/net/can/can_sja1000.c b/hw/net/can/can_sja1000.c
index 42d2f99dfb1d3cd3fa26f56ccb8d..34eea684ced278738bdb26327100 100644
--- a/hw/net/can/can_sja1000.c
+++ b/hw/net/can/can_sja1000.c
@@ -275,6 +275,10 @@ static void buff2frame_pel(const uint8_t *buff, qemu_can_frame *frame)
}
frame->can_dlc = buff[0] & 0x0f;
+ if (frame->can_dlc > 8) {
+ frame->can_dlc = 8;
+ }
+
if (buff[0] & 0x80) { /* Extended */
frame->can_id |= QEMU_CAN_EFF_FLAG;
frame->can_id |= buff[1] << 21; /* ID.28~ID.21 */
@@ -311,6 +315,10 @@ static void buff2frame_bas(const uint8_t *buff, qemu_can_frame *frame)
}
frame->can_dlc = buff[1] & 0x0f;
+ if (frame->can_dlc > 8) {
+ frame->can_dlc = 8;
+ }
+
for (i = 0; i < frame->can_dlc; i++) {
frame->data[i] = buff[2 + i];
}

View File

@ -0,0 +1,71 @@
From: =?UTF-8?q?Philippe=20Mathieu-Daud=C3=A9?= <f4bug@amsat.org>
Date: Wed, 26 May 2021 16:24:38 +0200
Subject: hw/pci-host/q35: Ignore write of reserved PCIEXBAR LENGTH field
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Git-commit: 9b0ca75e0196a72523232063db1e07ae36a5077a
libFuzzer triggered the following assertion:
cat << EOF | qemu-system-i386 -M pc-q35-5.0 \
-nographic -monitor none -serial none \
-qtest stdio -d guest_errors -trace pci\*
outl 0xcf8 0xf2000060
outl 0xcfc 0x8400056e
EOF
pci_cfg_write mch 00:0 @0x60 <- 0x8400056e
Aborted (core dumped)
This is because guest wrote MCH_HOST_BRIDGE_PCIEXBAR_LENGTH_RVD
(reserved value) to the PCIE XBAR register.
There is no indication on the datasheet about what occurs when
this value is written. Simply ignore it on QEMU (and report an
guest error):
pci_cfg_write mch 00:0 @0x60 <- 0x8400056e
Q35: Reserved PCIEXBAR LENGTH
pci_cfg_read mch 00:0 @0x0 -> 0x8086
pci_cfg_read mch 00:0 @0x0 -> 0x29c08086
...
Cc: qemu-stable@nongnu.org
Reported-by: Alexander Bulekov <alxndr@bu.edu>
BugLink: https://bugs.launchpad.net/qemu/+bug/1878641
Fixes: df2d8b3ed4 ("q35: Introduce q35 pc based chipset emulator")
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Signed-off-by: Philippe Mathieu-Daudé <f4bug@amsat.org>
Message-Id: <20210526142438.281477-1-f4bug@amsat.org>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Reviewed-by: Alexander Bulekov <alxndr@bu.edu>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Jose R. Ziviani <jziviani@suse.de>
---
hw/pci-host/q35.c | 3 +++
1 file changed, 3 insertions(+)
diff --git a/hw/pci-host/q35.c b/hw/pci-host/q35.c
index 2eb729dff5854aff586d9ac813f9..0f37cf056a9af4081f2350400ab2 100644
--- a/hw/pci-host/q35.c
+++ b/hw/pci-host/q35.c
@@ -29,6 +29,7 @@
*/
#include "qemu/osdep.h"
+#include "qemu/log.h"
#include "hw/i386/pc.h"
#include "hw/pci-host/q35.h"
#include "hw/qdev-properties.h"
@@ -318,6 +319,8 @@ static void mch_update_pciexbar(MCHPCIState *mch)
addr_mask |= MCH_HOST_BRIDGE_PCIEXBAR_64ADMSK;
break;
case MCH_HOST_BRIDGE_PCIEXBAR_LENGTH_RVD:
+ qemu_log_mask(LOG_GUEST_ERROR, "Q35: Reserved PCIEXBAR LENGTH\n");
+ return;
default:
abort();
}

View File

@ -1,3 +1,11 @@
-------------------------------------------------------------------
Tue Aug 3 20:39:25 UTC 2021 - José Ricardo Ziviani <jose.ziviani@suse.com>
- Add stable patches from upstream:
block-nvme-Fix-VFIO_MAP_DMA-failed-No-sp.patch
hw-net-can-sja1000-fix-buff2frame_bas-an.patch
hw-pci-host-q35-Ignore-write-of-reserved.patch
-------------------------------------------------------------------
Fri Jul 23 19:43:33 UTC 2021 - José Ricardo Ziviani <jose.ziviani@suse.com>

View File

@ -1,5 +1,5 @@
#
# spec file
# spec file for package qemu
#
# Copyright (c) 2021 SUSE LLC
#
@ -223,6 +223,9 @@ Patch00087: hw-nvme-fix-pin-based-interrupt-behavior.patch
Patch00088: hw-rdma-Fix-possible-mremap-overflow-in-.patch
Patch00089: pvrdma-Ensure-correct-input-on-ring-init.patch
Patch00090: pvrdma-Fix-the-ring-init-error-flow-CVE-.patch
Patch00091: hw-pci-host-q35-Ignore-write-of-reserved.patch
Patch00092: block-nvme-Fix-VFIO_MAP_DMA-failed-No-sp.patch
Patch00093: hw-net-can-sja1000-fix-buff2frame_bas-an.patch
# Patches applied in roms/seabios/:
Patch01000: seabios-use-python2-explicitly-as-needed.patch
Patch01001: seabios-switch-to-python3-as-needed.patch
@ -1159,6 +1162,9 @@ This package records qemu testsuite results and represents successful testing.
%patch00088 -p1
%patch00089 -p1
%patch00090 -p1
%patch00091 -p1
%patch00092 -p1
%patch00093 -p1
%patch01000 -p1
%patch01001 -p1
%patch01002 -p1