diff --git a/qemu.git-041e32b8d9d076980b4e35317c0339e57ab888f1.patch b/qemu.git-041e32b8d9d076980b4e35317c0339e57ab888f1.patch new file mode 100644 index 0000000..7865750 --- /dev/null +++ b/qemu.git-041e32b8d9d076980b4e35317c0339e57ab888f1.patch @@ -0,0 +1,47 @@ +From 041e32b8d9d076980b4e35317c0339e57ab888f1 Mon Sep 17 00:00:00 2001 +From: Max Reitz +Date: Sun, 11 Jun 2017 14:37:14 +0200 +Subject: [PATCH] qemu-nbd: Ignore SIGPIPE + +qemu proper has done so for 13 years +(8a7ddc38a60648257dc0645ab4a05b33d6040063), qemu-img and qemu-io have +done so for four years (526eda14a68d5b3596be715505289b541288ef2a). +Ignoring this signal is especially important in qemu-nbd because +otherwise a client can easily take down the qemu-nbd server by dropping +the connection when the server wants to send something, for example: + +$ qemu-nbd -x foo -f raw -t null-co:// & +[1] 12726 +$ qemu-io -c quit nbd://localhost/bar +can't open device nbd://localhost/bar: No export with name 'bar' available +[1] + 12726 broken pipe qemu-nbd -x foo -f raw -t null-co:// + +In this case, the client sends an NBD_OPT_ABORT and closes the +connection (because it is not required to wait for a reply), but the +server replies with an NBD_REP_ACK (because it is required to reply). + +Signed-off-by: Max Reitz +Message-Id: <20170611123714.31292-1-mreitz@redhat.com> +Signed-off-by: Paolo Bonzini +--- + qemu-nbd.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/qemu-nbd.c b/qemu-nbd.c +index 9464a04..4dd3fd4 100644 +--- a/qemu-nbd.c ++++ b/qemu-nbd.c +@@ -581,6 +581,10 @@ int main(int argc, char **argv) + sa_sigterm.sa_handler = termsig_handler; + sigaction(SIGTERM, &sa_sigterm, NULL); + ++#ifdef CONFIG_POSIX ++ signal(SIGPIPE, SIG_IGN); ++#endif ++ + qcrypto_init(&error_fatal); + + module_call_init(MODULE_INIT_QOM); +-- +1.8.3.1 + diff --git a/qemu.git-04bf2526ce87f21b32c9acba1c5518708c243ad0.patch b/qemu.git-04bf2526ce87f21b32c9acba1c5518708c243ad0.patch new file mode 100644 index 0000000..478a0fb --- /dev/null +++ b/qemu.git-04bf2526ce87f21b32c9acba1c5518708c243ad0.patch @@ -0,0 +1,43 @@ +From 04bf2526ce87f21b32c9acba1c5518708c243ad0 Mon Sep 17 00:00:00 2001 +From: Prasad J Pandit +Date: Wed, 12 Jul 2017 18:08:40 +0530 +Subject: [PATCH] exec: use qemu_ram_ptr_length to access guest ram + +When accessing guest's ram block during DMA operation, use +'qemu_ram_ptr_length' to get ram block pointer. It ensures +that DMA operation of given length is possible; And avoids +any OOB memory access situations. + +Reported-by: Alex +Signed-off-by: Prasad J Pandit +Message-Id: <20170712123840.29328-1-ppandit@redhat.com> +Signed-off-by: Paolo Bonzini +--- + exec.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/exec.c b/exec.c +index a083ff8..ad103ce 100644 +--- a/exec.c ++++ b/exec.c +@@ -2929,7 +2929,7 @@ static MemTxResult address_space_write_continue(AddressSpace *as, hwaddr addr, + } + } else { + /* RAM case */ +- ptr = qemu_map_ram_ptr(mr->ram_block, addr1); ++ ptr = qemu_ram_ptr_length(mr->ram_block, addr1, &l); + memcpy(ptr, buf, l); + invalidate_and_set_dirty(mr, addr1, l); + } +@@ -3020,7 +3020,7 @@ MemTxResult address_space_read_continue(AddressSpace *as, hwaddr addr, + } + } else { + /* RAM case */ +- ptr = qemu_map_ram_ptr(mr->ram_block, addr1); ++ ptr = qemu_ram_ptr_length(mr->ram_block, addr1, &l); + memcpy(buf, ptr, l); + } + +-- +1.8.3.1 + diff --git a/qemu.git-0c9390d978cbf61e8f16c9f580fa96b305c43568.patch b/qemu.git-0c9390d978cbf61e8f16c9f580fa96b305c43568.patch new file mode 100644 index 0000000..278bcbf --- /dev/null +++ b/qemu.git-0c9390d978cbf61e8f16c9f580fa96b305c43568.patch @@ -0,0 +1,197 @@ +From 0c9390d978cbf61e8f16c9f580fa96b305c43568 Mon Sep 17 00:00:00 2001 +From: Eric Blake +Date: Thu, 8 Jun 2017 17:26:17 -0500 +Subject: [PATCH] nbd: Fix regression on resiliency to port scan + +Back in qemu 2.5, qemu-nbd was immune to port probes (a transient +server would not quit, regardless of how many probe connections +came and went, until a connection actually negotiated). But we +broke that in commit ee7d7aa when removing the return value to +nbd_client_new(), although that patch also introduced a bug causing +an assertion failure on a client that fails negotiation. We then +made it worse during refactoring in commit 1a6245a (a segfault +before we could even assert); the (masked) assertion was cleaned +up in d3780c2 (still in 2.6), and just recently we finally fixed +the segfault ("nbd: Fully intialize client in case of failed +negotiation"). But that still means that ever since we added +TLS support to qemu-nbd, we have been vulnerable to an ill-timed +port-scan being able to cause a denial of service by taking down +qemu-nbd before a real client has a chance to connect. + +Since negotiation is now handled asynchronously via coroutines, +we no longer have a synchronous point of return by re-adding a +return value to nbd_client_new(). So this patch instead wires +things up to pass the negotiation status through the close_fn +callback function. + +Simple test across two terminals: +$ qemu-nbd -f raw -p 30001 file +$ nmap 127.0.0.1 -p 30001 && \ + qemu-io -c 'r 0 512' -f raw nbd://localhost:30001 + +Note that this patch does not change what constitutes successful +negotiation (thus, a client must enter transmission phase before +that client can be considered as a reason to terminate the server +when the connection ends). Perhaps we may want to tweak things +in a later patch to also treat a client that uses NBD_OPT_ABORT +as being a 'successful' negotiation (the client correctly talked +the NBD protocol, and informed us it was not going to use our +export after all), but that's a discussion for another day. + +Fixes: https://bugzilla.redhat.com/show_bug.cgi?id=1451614 + +Signed-off-by: Eric Blake +Message-Id: <20170608222617.20376-1-eblake@redhat.com> +Signed-off-by: Paolo Bonzini +--- + blockdev-nbd.c | 6 +++++- + include/block/nbd.h | 2 +- + nbd/server.c | 24 +++++++++++++++--------- + qemu-nbd.c | 4 ++-- + 4 files changed, 23 insertions(+), 13 deletions(-) + +diff --git a/blockdev-nbd.c b/blockdev-nbd.c +index dd0860f..28f551a 100644 +--- a/blockdev-nbd.c ++++ b/blockdev-nbd.c +@@ -27,6 +27,10 @@ typedef struct NBDServerData { + + static NBDServerData *nbd_server; + ++static void nbd_blockdev_client_closed(NBDClient *client, bool ignored) ++{ ++ nbd_client_put(client); ++} + + static gboolean nbd_accept(QIOChannel *ioc, GIOCondition condition, + gpointer opaque) +@@ -46,7 +50,7 @@ static gboolean nbd_accept(QIOChannel *ioc, GIOCondition condition, + + nbd_client_new(NULL, cioc, + nbd_server->tlscreds, NULL, +- nbd_client_put); ++ nbd_blockdev_client_closed); + object_unref(OBJECT(cioc)); + return TRUE; + } +diff --git a/include/block/nbd.h b/include/block/nbd.h +index 416257a..8fa5ce5 100644 +--- a/include/block/nbd.h ++++ b/include/block/nbd.h +@@ -162,7 +162,7 @@ void nbd_client_new(NBDExport *exp, + QIOChannelSocket *sioc, + QCryptoTLSCreds *tlscreds, + const char *tlsaclname, +- void (*close)(NBDClient *)); ++ void (*close_fn)(NBDClient *, bool)); + void nbd_client_get(NBDClient *client); + void nbd_client_put(NBDClient *client); + +diff --git a/nbd/server.c b/nbd/server.c +index 49b55f6..f2b1aa4 100644 +--- a/nbd/server.c ++++ b/nbd/server.c +@@ -81,7 +81,7 @@ static QTAILQ_HEAD(, NBDExport) exports = QTAILQ_HEAD_INITIALIZER(exports); + + struct NBDClient { + int refcount; +- void (*close)(NBDClient *client); ++ void (*close_fn)(NBDClient *client, bool negotiated); + + NBDExport *exp; + QCryptoTLSCreds *tlscreds; +@@ -778,7 +778,7 @@ void nbd_client_put(NBDClient *client) + } + } + +-static void client_close(NBDClient *client) ++static void client_close(NBDClient *client, bool negotiated) + { + if (client->closing) { + return; +@@ -793,8 +793,8 @@ static void client_close(NBDClient *client) + NULL); + + /* Also tell the client, so that they release their reference. */ +- if (client->close) { +- client->close(client); ++ if (client->close_fn) { ++ client->close_fn(client, negotiated); + } + } + +@@ -975,7 +975,7 @@ void nbd_export_close(NBDExport *exp) + + nbd_export_get(exp); + QTAILQ_FOREACH_SAFE(client, &exp->clients, next, next) { +- client_close(client); ++ client_close(client, true); + } + nbd_export_set_name(exp, NULL); + nbd_export_put(exp); +@@ -1337,7 +1337,7 @@ done: + + out: + nbd_request_put(req); +- client_close(client); ++ client_close(client, true); + } + + static void nbd_read(void *opaque) +@@ -1363,7 +1363,7 @@ static coroutine_fn void nbd_co_client_start(void *opaque) + qemu_co_mutex_init(&client->send_lock); + + if (nbd_negotiate(data)) { +- client_close(client); ++ client_close(client, false); + goto out; + } + nbd_set_handlers(client); +@@ -1373,11 +1373,17 @@ out: + g_free(data); + } + ++/* ++ * Create a new client listener on the given export @exp, using the ++ * given channel @sioc. Begin servicing it in a coroutine. When the ++ * connection closes, call @close_fn with an indication of whether the ++ * client completed negotiation. ++ */ + void nbd_client_new(NBDExport *exp, + QIOChannelSocket *sioc, + QCryptoTLSCreds *tlscreds, + const char *tlsaclname, +- void (*close_fn)(NBDClient *)) ++ void (*close_fn)(NBDClient *, bool)) + { + NBDClient *client; + NBDClientNewData *data = g_new(NBDClientNewData, 1); +@@ -1394,7 +1400,7 @@ void nbd_client_new(NBDExport *exp, + client->ioc = QIO_CHANNEL(sioc); + object_ref(OBJECT(client->ioc)); + client->can_read = true; +- client->close = close_fn; ++ client->close_fn = close_fn; + + data->client = client; + data->co = qemu_coroutine_create(nbd_co_client_start, data); +diff --git a/qemu-nbd.c b/qemu-nbd.c +index 651f85e..9464a04 100644 +--- a/qemu-nbd.c ++++ b/qemu-nbd.c +@@ -336,10 +336,10 @@ static void nbd_export_closed(NBDExport *exp) + + static void nbd_update_server_watch(void); + +-static void nbd_client_closed(NBDClient *client) ++static void nbd_client_closed(NBDClient *client, bool negotiated) + { + nb_fds--; +- if (nb_fds == 0 && !persistent && state == RUNNING) { ++ if (negotiated && nb_fds == 0 && !persistent && state == RUNNING) { + state = TERMINATE; + } + nbd_update_server_watch(); +-- +1.8.3.1 + diff --git a/qemu.git-26f670a244982335cc08943fb1ec099a2c81e42d.patch b/qemu.git-26f670a244982335cc08943fb1ec099a2c81e42d.patch new file mode 100644 index 0000000..d8e71cc --- /dev/null +++ b/qemu.git-26f670a244982335cc08943fb1ec099a2c81e42d.patch @@ -0,0 +1,31 @@ +From 26f670a244982335cc08943fb1ec099a2c81e42d Mon Sep 17 00:00:00 2001 +From: Li Qiang +Date: Tue, 7 Feb 2017 03:15:03 -0800 +Subject: [PATCH] usb: ohci: fix error return code in servicing iso td + +It should return 1 if an error occurs when reading iso td. +This will avoid an infinite loop issue in ohci_service_ed_list. + +Signed-off-by: Li Qiang +Message-id: 5899ac3e.1033240a.944d5.9a2d@mx.google.com +Signed-off-by: Gerd Hoffmann +--- + hw/usb/hcd-ohci.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/hw/usb/hcd-ohci.c b/hw/usb/hcd-ohci.c +index c82a92f..2cba3e3 100644 +--- a/hw/usb/hcd-ohci.c ++++ b/hw/usb/hcd-ohci.c +@@ -725,7 +725,7 @@ static int ohci_service_iso_td(OHCIState *ohci, struct ohci_ed *ed, + if (ohci_read_iso_td(ohci, addr, &iso_td)) { + trace_usb_ohci_iso_td_read_failed(addr); + ohci_die(ohci); +- return 0; ++ return 1; + } + + starting_frame = OHCI_BM(iso_td.flags, TD_SF); +-- +1.8.3.1 + diff --git a/qemu.git-df8ad9f128c15aa0a0ebc7b24e9a22c9775b67af.patch b/qemu.git-df8ad9f128c15aa0a0ebc7b24e9a22c9775b67af.patch new file mode 100644 index 0000000..31c2df4 --- /dev/null +++ b/qemu.git-df8ad9f128c15aa0a0ebc7b24e9a22c9775b67af.patch @@ -0,0 +1,81 @@ +From df8ad9f128c15aa0a0ebc7b24e9a22c9775b67af Mon Sep 17 00:00:00 2001 +From: Eric Blake +Date: Fri, 26 May 2017 22:04:21 -0500 +Subject: [PATCH] nbd: Fully initialize client in case of failed negotiation + +If a non-NBD client connects to qemu-nbd, we would end up with +a SIGSEGV in nbd_client_put() because we were trying to +unregister the client's association to the export, even though +we skipped inserting the client into that list. Easy trigger +in two terminals: + +$ qemu-nbd -p 30001 --format=raw file +$ nmap 127.0.0.1 -p 30001 + +nmap claims that it thinks it connected to a pago-services1 +server (which probably means nmap could be updated to learn the +NBD protocol and give a more accurate diagnosis of the open +port - but that's not our problem), then terminates immediately, +so our call to nbd_negotiate() fails. The fix is to reorder +nbd_co_client_start() to ensure that all initialization occurs +before we ever try talking to a client in nbd_negotiate(), so +that the teardown sequence on negotiation failure doesn't fault +while dereferencing a half-initialized object. + +While debugging this, I also noticed that nbd_update_server_watch() +called by nbd_client_closed() was still adding a channel to accept +the next client, even when the state was no longer RUNNING. That +is fixed by making nbd_can_accept() pay attention to the current +state. + +Fixes: https://bugzilla.redhat.com/show_bug.cgi?id=1451614 + +Signed-off-by: Eric Blake +Message-Id: <20170527030421.28366-1-eblake@redhat.com> +Signed-off-by: Paolo Bonzini +--- + nbd/server.c | 8 +++----- + qemu-nbd.c | 2 +- + 2 files changed, 4 insertions(+), 6 deletions(-) + +diff --git a/nbd/server.c b/nbd/server.c +index ee59e5d..49b55f6 100644 +--- a/nbd/server.c ++++ b/nbd/server.c +@@ -1358,17 +1358,15 @@ static coroutine_fn void nbd_co_client_start(void *opaque) + + if (exp) { + nbd_export_get(exp); ++ QTAILQ_INSERT_TAIL(&exp->clients, client, next); + } ++ qemu_co_mutex_init(&client->send_lock); ++ + if (nbd_negotiate(data)) { + client_close(client); + goto out; + } +- qemu_co_mutex_init(&client->send_lock); + nbd_set_handlers(client); +- +- if (exp) { +- QTAILQ_INSERT_TAIL(&exp->clients, client, next); +- } + out: + g_free(data); + } +diff --git a/qemu-nbd.c b/qemu-nbd.c +index f60842f..651f85e 100644 +--- a/qemu-nbd.c ++++ b/qemu-nbd.c +@@ -325,7 +325,7 @@ out: + + static int nbd_can_accept(void) + { +- return nb_fds < shared; ++ return state == RUNNING && nb_fds < shared; + } + + static void nbd_export_closed(NBDExport *exp) +-- +1.8.3.1 + diff --git a/qemu.trad.CVE-2017-9330.patch b/qemu.trad.CVE-2017-9330.patch new file mode 100644 index 0000000..046e3e0 --- /dev/null +++ b/qemu.trad.CVE-2017-9330.patch @@ -0,0 +1,31 @@ +From 26f670a244982335cc08943fb1ec099a2c81e42d Mon Sep 17 00:00:00 2001 +From: Li Qiang +Date: Tue, 7 Feb 2017 03:15:03 -0800 +Subject: [PATCH] usb: ohci: fix error return code in servicing iso td + +It should return 1 if an error occurs when reading iso td. +This will avoid an infinite loop issue in ohci_service_ed_list. + +Signed-off-by: Li Qiang +Message-id: 5899ac3e.1033240a.944d5.9a2d@mx.google.com +Signed-off-by: Gerd Hoffmann +--- + hw/usb-ohci.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/hw/usb-ohci.c b/hw/usb-ohci.c +index c82a92f..2cba3e3 100644 +--- a/hw/usb-ohci.c ++++ b/hw/usb-ohci.c +@@ -725,7 +725,7 @@ static int ohci_service_iso_td(OHCIState *ohci, struct ohci_ed *ed, + + if (!ohci_read_iso_td(addr, &iso_td)) { + printf("usb-ohci: ISO_TD read error at %x\n", addr); +- return 0; ++ return 1; + } + + starting_frame = OHCI_BM(iso_td.flags, TD_SF); +-- +1.8.3.1 + diff --git a/xen.spec b/xen.spec index a4dbd14..5a63291 100644 --- a/xen.spec +++ b/xen.spec @@ -50,7 +50,7 @@ Summary: Xen is a virtual machine monitor Name: xen Version: 4.8.1 -Release: 7%{?dist} +Release: 8%{?dist} Group: Development/Libraries License: GPLv2+ and LGPLv2+ and BSD URL: http://xen.org/ @@ -154,6 +154,12 @@ Patch86: xsa235-4.9.patch Patch87: qemu.git-3268a845f41253fb55852a8429c32b50f36f349a.patch Patch88: qemu.trad.CVE-2017-8309.patch Patch89: qemu.git-fa18f36a461984eae50ab957e47ec78dae3c14fc.patch +Patch90: qemu.git-26f670a244982335cc08943fb1ec099a2c81e42d.patch +Patch91: qemu.trad.CVE-2017-9330.patch +Patch92: qemu.git-df8ad9f128c15aa0a0ebc7b24e9a22c9775b67af.patch +Patch93: qemu.git-0c9390d978cbf61e8f16c9f580fa96b305c43568.patch +Patch94: qemu.git-041e32b8d9d076980b4e35317c0339e57ab888f1.patch +Patch95: qemu.git-04bf2526ce87f21b32c9acba1c5518708c243ad0.patch BuildRoot: %{_tmppath}/%{name}-%{version}-%{release}-root @@ -390,6 +396,7 @@ pushd tools/qemu-xen-traditional %patch55 -p1 %patch78 -p1 %patch88 -p1 +%patch91 -p1 popd # qemu-xen patches @@ -420,6 +427,11 @@ pushd tools/qemu-xen %patch77 -p1 %patch87 -p1 %patch89 -p1 +%patch90 -p1 +%patch92 -p1 +%patch93 -p1 +%patch94 -p1 +%patch95 -p1 popd # stubdom sources @@ -922,6 +934,16 @@ rm -rf %{buildroot} %endif %changelog +* Wed Aug 30 2017 Michael Young - 4.8.1-8 +- Qemu: usb: ohci: infinite loop due to incorrect return value [CVE-2017-9330] + (#1457698) +- Qemu: nbd: segmentation fault due to client non-negotiation [CVE-2017-9524] + (#1460173) +- Qemu: qemu-nbd: server breaks with SIGPIPE upon client abort [CVE-2017-10664] + (#1466466) +- Qemu: exec: oob access during dma operation [CVE-2017-11334] (#1471640) +- revised full fix for XSA-226 (regressed 32-bit Dom0 or backend domains) + * Wed Aug 23 2017 Michael Young - 4.8.1-7 - full fix for XSA-226, replacing workaround - drop conflict of xendomain and libvirtd as can cause problems (#1398590) diff --git a/xsa226.0001-gnttab-dont-use-possibly-unbounded-tail-calls.patch b/xsa226.0001-gnttab-dont-use-possibly-unbounded-tail-calls.patch index 7711d3f..d60bbe2 100644 --- a/xsa226.0001-gnttab-dont-use-possibly-unbounded-tail-calls.patch +++ b/xsa226.0001-gnttab-dont-use-possibly-unbounded-tail-calls.patch @@ -16,6 +16,21 @@ This is part of CVE-2017-12135 / XSA-226. Signed-off-by: Jan Beulich +--- a/xen/common/compat/grant_table.c ++++ b/xen/common/compat/grant_table.c +@@ -258,9 +258,9 @@ int compat_grant_table_op(unsigned int cmd, + rc = gnttab_copy(guest_handle_cast(nat.uop, gnttab_copy_t), n); + if ( rc > 0 ) + { +- ASSERT(rc < n); +- i -= n - rc; +- n = rc; ++ ASSERT(rc <= n); ++ i -= rc; ++ n -= rc; + } + if ( rc >= 0 ) + { --- a/xen/common/grant_table.c +++ b/xen/common/grant_table.c @@ -2103,8 +2103,10 @@ __release_grant_for_copy(