[virt-manager/f19] Fix parsing rawhide .treeinfo (bz #989162) Fix spice with TLS (bz #904295) Reduce impact of memory l

Cole Robinson crobinso at fedoraproject.org
Tue Sep 24 15:42:28 UTC 2013


commit ff5bbfd309de657cb282e5d4fb9864c24d524b58
Author: Cole Robinson <crobinso at redhat.com>
Date:   Tue Sep 24 11:42:18 2013 -0400

    Fix parsing rawhide .treeinfo (bz #989162)
    Fix spice with TLS (bz #904295)
    Reduce impact of memory leak (bz #972371)

 0001-Fix-rawhide-URL-installs.patch                |   24 ++
 0002-console-Fix-spice-with-TLS-bz-904295.patch    |   94 ++++++
 ...able-graph-data-func-if-graph-isn-t-visib.patch |  165 ++++++++++
 ...Check-can_set_row_none-before-setting-ico.patch |   46 +++
 ...r-ignore-VIR_ERR_NO_DOMAIN-when-a-domain-.patch |  147 +++++++++
 ...ge-some-row-creation-drop-unneeded-row-ke.patch |  316 ++++++++++++++++++++
 ...Separate-stats-and-state-update-callbacks.patch |  204 +++++++++++++
 virt-manager.spec                                  |   29 ++-
 8 files changed, 1024 insertions(+), 1 deletions(-)
---
diff --git a/0001-Fix-rawhide-URL-installs.patch b/0001-Fix-rawhide-URL-installs.patch
new file mode 100644
index 0000000..71835c0
--- /dev/null
+++ b/0001-Fix-rawhide-URL-installs.patch
@@ -0,0 +1,24 @@
+From 17406905d786734e9d30b3a808314f7bb1e28891 Mon Sep 17 00:00:00 2001
+From: Lars Seipel <lars.seipel at gmail.com>
+Date: Mon, 29 Jul 2013 12:28:22 -0400
+Subject: [PATCH] Fix rawhide URL installs
+
+https://bugzilla.redhat.com/show_bug.cgi?id=989162
+(cherry picked from commit 72648c9185e3ccb27fb9896a4e7a48f1769c8a4e)
+---
+ virtinst/OSDistro.py | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/virtinst/OSDistro.py b/virtinst/OSDistro.py
+index 5ecfdf6..780823c 100644
+--- a/virtinst/OSDistro.py
++++ b/virtinst/OSDistro.py
+@@ -512,7 +512,7 @@ class FedoraDistro(RedHatDistro):
+             if ret:
+                 lateststr, latestnum = self._latestFedoraVariant()
+                 ver = self.treeinfo.get("general", "version")
+-                if ver == "development":
++                if ver == "development" or ver == "rawhide":
+                     self.os_variant = self._latestFedoraVariant()
+                 elif ver:
+                     vernum = int(str(ver).split("-")[0])
diff --git a/0002-console-Fix-spice-with-TLS-bz-904295.patch b/0002-console-Fix-spice-with-TLS-bz-904295.patch
new file mode 100644
index 0000000..3a12be1
--- /dev/null
+++ b/0002-console-Fix-spice-with-TLS-bz-904295.patch
@@ -0,0 +1,94 @@
+From 11eb5ff728413ca1b3c6404e4e42550add553355 Mon Sep 17 00:00:00 2001
+From: Cole Robinson <crobinso at redhat.com>
+Date: Sun, 1 Sep 2013 16:08:14 -0400
+Subject: [PATCH] console: Fix spice with TLS (bz #904295)
+
+We now use the same CA trust store as virt-viewer's default, which is:
+
+~/.spicec/spice_truststore.pem
+
+(cherry picked from commit cdc82e62a236d0e737851c693d6673f65ca278c1)
+
+Conflicts:
+	virtManager/console.py
+---
+ virtManager/console.py | 26 +++++++++++++++-----------
+ 1 file changed, 15 insertions(+), 11 deletions(-)
+
+diff --git a/virtManager/console.py b/virtManager/console.py
+index 001318e..90db31c 100644
+--- a/virtManager/console.py
++++ b/virtManager/console.py
+@@ -63,6 +63,7 @@ class ConnectionInfo(object):
+         self.gport      = gdev.port and str(gdev.port) or None
+         self.gsocket    = gdev.socket
+         self.gaddr      = gdev.listen or "127.0.0.1"
++        self.gtlsport   = gdev.tlsPort or None
+ 
+         self.transport, self.connuser = conn.get_transport()
+         self._connhost = conn.get_uri_hostname() or "127.0.0.1"
+@@ -80,19 +81,22 @@ class ConnectionInfo(object):
+     def get_conn_host(self):
+         host = self._connhost
+         port = self._connport
++        tlsport = None
+ 
+         if not self.need_tunnel():
+             port = self.gport
++            tlsport = self.gtlsport
+             if self.gaddr != "0.0.0.0":
+                 host = self.gaddr
+ 
+-        return host, port
++        return host, port, tlsport
+ 
+     def logstring(self):
+         return ("proto=%s trans=%s connhost=%s connuser=%s "
+-                "connport=%s gaddr=%s gport=%s gsocket=%s" %
++                "connport=%s gaddr=%s gport=%s gtlsport=%s gsocket=%s" %
+                 (self.gtype, self.transport, self._connhost, self.connuser,
+-                 self._connport, self.gaddr, self.gport, self.gsocket))
++                 self._connport, self.gaddr, self.gport, self.gtlsport,
++                 self.gsocket))
+     def console_active(self):
+         if self.gsocket:
+             return True
+@@ -111,7 +115,7 @@ class Tunnel(object):
+         if self.outfd is not None:
+             return -1
+ 
+-        host, port = ginfo.get_conn_host()
++        host, port, ignore = ginfo.get_conn_host()
+ 
+         # Build SSH cmd
+         argv = ["ssh", "ssh"]
+@@ -406,7 +410,7 @@ class VNCViewer(Viewer):
+         return self.display.is_open()
+ 
+     def open_host(self, ginfo, password=None):
+-        host, port = ginfo.get_conn_host()
++        host, port, ignore = ginfo.get_conn_host()
+ 
+         if not ginfo.gsocket:
+             logging.debug("VNC connection to %s:%s", host, port)
+@@ -553,14 +557,14 @@ class SpiceViewer(Viewer):
+         return self.display_channel.get_properties("width", "height")
+ 
+     def open_host(self, ginfo, password=None):
+-        host, port = ginfo.get_conn_host()
+-
+-        uri = "spice://"
+-        uri += str(host) + "?port=" + str(port)
+-        logging.debug("spice uri: %s", uri)
++        host, port, tlsport = ginfo.get_conn_host()
+ 
+         self.spice_session = SpiceClientGLib.Session()
+-        self.spice_session.set_property("uri", uri)
++        SpiceClientGLib.set_session_option(self.spice_session)
++        self.spice_session.set_property("host", str(host))
++        self.spice_session.set_property("port", str(port))
++        if tlsport:
++            self.spice_session.set_property("tls-port", str(tlsport))
+         if password:
+             self.spice_session.set_property("password", password)
+         GObject.GObject.connect(self.spice_session, "channel-new",
diff --git a/0003-manager-Disable-graph-data-func-if-graph-isn-t-visib.patch b/0003-manager-Disable-graph-data-func-if-graph-isn-t-visib.patch
new file mode 100644
index 0000000..e2fe994
--- /dev/null
+++ b/0003-manager-Disable-graph-data-func-if-graph-isn-t-visib.patch
@@ -0,0 +1,165 @@
+From 0c452553f19bcaf9cf5ebc52d1d18014ffe10160 Mon Sep 17 00:00:00 2001
+From: Cole Robinson <crobinso at redhat.com>
+Date: Sun, 1 Sep 2013 21:35:23 -0400
+Subject: [PATCH] manager: Disable graph data func if graph isn't visible
+
+Seems like pygobject is a bit leaky with tree row accesses, and
+the cell cb hammers on that quite a bit, even if the graph isn't showing.
+
+(cherry picked from commit db7db9ab47dd00d746cf8a3359c1c26dbfcfa50e)
+---
+ virtManager/manager.py | 82 ++++++++++++++++++++++----------------------------
+ 1 file changed, 36 insertions(+), 46 deletions(-)
+
+diff --git a/virtManager/manager.py b/virtManager/manager.py
+index bdc21cf..ca9d909 100644
+--- a/virtManager/manager.py
++++ b/virtManager/manager.py
+@@ -270,15 +270,11 @@ class vmmManager(vmmGObjectUI):
+             self.config.on_stats_enable_net_poll_changed(self.enable_polling,
+                                                     COL_NETWORK))
+ 
++        self.toggle_guest_cpu_usage_visible_widget()
++        self.toggle_host_cpu_usage_visible_widget()
++        self.toggle_disk_io_visible_widget()
++        self.toggle_network_traffic_visible_widget()
+ 
+-        self.widget("menu_view_stats_guest_cpu").set_active(
+-                            self.config.is_vmlist_guest_cpu_usage_visible())
+-        self.widget("menu_view_stats_host_cpu").set_active(
+-                            self.config.is_vmlist_host_cpu_usage_visible())
+-        self.widget("menu_view_stats_disk").set_active(
+-                            self.config.is_vmlist_disk_io_visible())
+-        self.widget("menu_view_stats_network").set_active(
+-                            self.config.is_vmlist_network_traffic_visible())
+ 
+     def init_toolbar(self):
+         self.widget("vm-new").set_icon_name("vm_new")
+@@ -428,7 +424,7 @@ class vmmManager(vmmGObjectUI):
+         nameCol.add_attribute(name_txt, 'foreground', ROW_COLOR)
+         nameCol.set_sort_column_id(COL_NAME)
+ 
+-        def make_stats_column(title, datafunc, is_visible, colnum):
++        def make_stats_column(title, colnum):
+             col = Gtk.TreeViewColumn(title)
+             col.set_min_width(140)
+ 
+@@ -443,29 +439,15 @@ class vmmManager(vmmGObjectUI):
+             img.set_property("reversed", True)
+             col.pack_start(img, True)
+             col.add_attribute(img, 'visible', ROW_IS_VM)
+-            col.set_cell_data_func(img, datafunc, None)
+ 
+-            col.set_visible(is_visible)
+             col.set_sort_column_id(colnum)
+             vmlist.append_column(col)
+             return col
+ 
+-        self.guestcpucol = make_stats_column(_("CPU usage"),
+-                            self.guest_cpu_usage_img,
+-                            self.config.is_vmlist_guest_cpu_usage_visible(),
+-                            COL_GUEST_CPU)
+-        self.hostcpucol = make_stats_column(_("Host CPU usage"),
+-                            self.host_cpu_usage_img,
+-                            self.config.is_vmlist_host_cpu_usage_visible(),
+-                            COL_HOST_CPU)
+-        self.diskcol = make_stats_column(_("Disk I/O"),
+-                            self.disk_io_img,
+-                            self.config.is_vmlist_disk_io_visible(),
+-                            COL_DISK)
+-        self.netcol = make_stats_column(_("Network I/O"),
+-                            self.network_traffic_img,
+-                            self.config.is_vmlist_network_traffic_visible(),
+-                            COL_NETWORK)
++        self.guestcpucol = make_stats_column(_("CPU usage"), COL_GUEST_CPU)
++        self.hostcpucol = make_stats_column(_("Host CPU usage"), COL_HOST_CPU)
++        self.diskcol = make_stats_column(_("Disk I/O"), COL_DISK)
++        self.netcol = make_stats_column(_("Network I/O"), COL_NETWORK)
+ 
+         model.set_sort_func(COL_NAME, self.vmlist_name_sorter)
+         model.set_sort_func(COL_GUEST_CPU, self.vmlist_guest_cpu_usage_sorter)
+@@ -1196,25 +1178,33 @@ class vmmManager(vmmGObjectUI):
+             current_text = current_text + disabled_text
+         widget.set_label(current_text)
+ 
+-    def toggle_network_traffic_visible_widget(self):
+-        val = self.config.is_vmlist_network_traffic_visible()
+-        self.netcol.set_visible(val)
+-        self.widget("menu_view_stats_network").set_active(val)
++    def _toggle_graph_helper(self, do_show, col, datafunc, menu):
++        img = -1
++        for child in col.get_cells():
++            if isinstance(child, CellRendererSparkline):
++                img = child
++        datafunc = do_show and datafunc or None
+ 
+-    def toggle_disk_io_visible_widget(self):
+-        val = self.config.is_vmlist_disk_io_visible()
+-        self.diskcol.set_visible(val)
+-        self.widget("menu_view_stats_disk").set_active(val)
++        col.set_cell_data_func(img, datafunc, None)
++        col.set_visible(do_show)
++        self.widget(menu).set_active(do_show)
+ 
++    def toggle_network_traffic_visible_widget(self):
++        self._toggle_graph_helper(
++            self.config.is_vmlist_network_traffic_visible(), self.netcol,
++            self.network_traffic_img, "menu_view_stats_network")
++    def toggle_disk_io_visible_widget(self):
++        self._toggle_graph_helper(
++            self.config.is_vmlist_disk_io_visible(), self.diskcol,
++            self.disk_io_img, "menu_view_stats_disk")
+     def toggle_guest_cpu_usage_visible_widget(self):
+-        val = self.config.is_vmlist_guest_cpu_usage_visible()
+-        self.guestcpucol.set_visible(val)
+-        self.widget("menu_view_stats_guest_cpu").set_active(val)
+-
++        self._toggle_graph_helper(
++            self.config.is_vmlist_guest_cpu_usage_visible(), self.guestcpucol,
++            self.guest_cpu_usage_img, "menu_view_stats_guest_cpu")
+     def toggle_host_cpu_usage_visible_widget(self):
+-        val = self.config.is_vmlist_host_cpu_usage_visible()
+-        self.hostcpucol.set_visible(val)
+-        self.widget("menu_view_stats_host_cpu").set_active(val)
++        self._toggle_graph_helper(
++            self.config.is_vmlist_host_cpu_usage_visible(), self.hostcpucol,
++            self.host_cpu_usage_img, "menu_view_stats_host_cpu")
+ 
+     def toggle_stats_visible(self, src, stats_id):
+         visible = src.get_active()
+@@ -1236,7 +1226,7 @@ class vmmManager(vmmGObjectUI):
+         self.toggle_stats_visible(src, COL_NETWORK)
+ 
+     def guest_cpu_usage_img(self, column_ignore, cell, model, _iter, data):
+-        obj = model.get_value(_iter, ROW_HANDLE)
++        obj = model[_iter][ROW_HANDLE]
+         if obj is None or not hasattr(obj, "conn"):
+             return
+ 
+@@ -1244,7 +1234,7 @@ class vmmManager(vmmGObjectUI):
+         cell.set_property('data_array', data)
+ 
+     def host_cpu_usage_img(self, column_ignore, cell, model, _iter, data):
+-        obj = model.get_value(_iter, ROW_HANDLE)
++        obj = model[_iter][ROW_HANDLE]
+         if obj is None or not hasattr(obj, "conn"):
+             return
+ 
+@@ -1252,7 +1242,7 @@ class vmmManager(vmmGObjectUI):
+         cell.set_property('data_array', data)
+ 
+     def disk_io_img(self, column_ignore, cell, model, _iter, data):
+-        obj = model.get_value(_iter, ROW_HANDLE)
++        obj = model[_iter][ROW_HANDLE]
+         if obj is None or not hasattr(obj, "conn"):
+             return
+ 
+@@ -1260,7 +1250,7 @@ class vmmManager(vmmGObjectUI):
+         cell.set_property('data_array', data)
+ 
+     def network_traffic_img(self, column_ignore, cell, model, _iter, data):
+-        obj = model.get_value(_iter, ROW_HANDLE)
++        obj = model[_iter][ROW_HANDLE]
+         if obj is None or not hasattr(obj, "conn"):
+             return
+ 
diff --git a/0004-inspection-Check-can_set_row_none-before-setting-ico.patch b/0004-inspection-Check-can_set_row_none-before-setting-ico.patch
new file mode 100644
index 0000000..b9dc4e4
--- /dev/null
+++ b/0004-inspection-Check-can_set_row_none-before-setting-ico.patch
@@ -0,0 +1,46 @@
+From 89d78c1af3f84113ea0d18b4229e98d16c12bfef Mon Sep 17 00:00:00 2001
+From: "Richard W.M. Jones" <rjones at redhat.com>
+Date: Fri, 28 Jun 2013 18:45:53 +0100
+Subject: [PATCH] inspection: Check can_set_row_none before setting icon to
+ None.
+
+Previously one could set the icon field of a tree model to None, but
+with Gtk3 and older versions of pygobject3 this would fail.
+
+Use can_set_row_none to test for this condition and work around it.
+
+The previous traceback was:
+
+Traceback (most recent call last):
+  File "/home/rjones/d/virt-manager/virtManager/manager.py", line 981, in vm_inspection_changed
+    self.get_inspection_icon_pixbuf(vm, 16, 16)
+  File "/usr/lib64/python2.7/site-packages/gi/overrides/Gtk.py", line 1152, in __setitem__
+    self.model.set_value(self.iter, key, value)
+  File "/usr/lib64/python2.7/site-packages/gi/overrides/Gtk.py", line 1298, in set_value
+    Gtk.TreeStore.set_value(self, treeiter, column, value)
+  File "/usr/lib64/python2.7/site-packages/gi/types.py", line 47, in function
+    return info.invoke(*args, **kwargs)
+TypeError: Argument 3 does not allow None as a value
+
+(cherry picked from commit 9d5c1cdb1c03a8c045ae94ab5324aa7dda68e695)
+---
+ virtManager/manager.py | 6 ++++--
+ 1 file changed, 4 insertions(+), 2 deletions(-)
+
+diff --git a/virtManager/manager.py b/virtManager/manager.py
+index ca9d909..3682429 100644
+--- a/virtManager/manager.py
++++ b/virtManager/manager.py
+@@ -959,8 +959,10 @@ class vmmManager(vmmGObjectUI):
+             return
+ 
+         row = self.rows[self.vm_row_key(vm)]
+-        row[ROW_INSPECTION_OS_ICON] = \
+-            self.get_inspection_icon_pixbuf(vm, 16, 16)
++        new_icon = self.get_inspection_icon_pixbuf(vm, 16, 16)
++        if not can_set_row_none:
++            new_icon = new_icon or ""
++        row[ROW_INSPECTION_OS_ICON] = new_icon
+         model.row_changed(row.path, row.iter)
+ 
+     def get_inspection_icon_pixbuf(self, vm, w, h):
diff --git a/0005-virt-manager-ignore-VIR_ERR_NO_DOMAIN-when-a-domain-.patch b/0005-virt-manager-ignore-VIR_ERR_NO_DOMAIN-when-a-domain-.patch
new file mode 100644
index 0000000..69d4be6
--- /dev/null
+++ b/0005-virt-manager-ignore-VIR_ERR_NO_DOMAIN-when-a-domain-.patch
@@ -0,0 +1,147 @@
+From 6df408590cf0c4c094bcc5e8700700118e2d71c6 Mon Sep 17 00:00:00 2001
+From: Giuseppe Scrivano <gscrivan at redhat.com>
+Date: Fri, 16 Aug 2013 15:59:33 +0200
+Subject: [PATCH] virt-manager: ignore VIR_ERR_NO_DOMAIN when a domain was just
+ deleted
+
+Some callbacks could try to access a domain that was just deleted and
+not accessible anymore.  Detect these cases and don't propagate the
+exception.
+
+Signed-off-by: Giuseppe Scrivano <gscrivan at redhat.com>
+(cherry picked from commit c1fa43ebb90c26c57f72faaf6c0b6a5c19221dd4)
+
+Conflicts:
+	virtManager/uihelpers.py
+---
+ virtManager/details.py   | 10 ++++++++--
+ virtManager/domain.py    | 14 +++++++++-----
+ virtManager/manager.py   | 29 ++++++++++++++++++-----------
+ virtManager/uihelpers.py |  5 +++++
+ 4 files changed, 40 insertions(+), 18 deletions(-)
+
+diff --git a/virtManager/details.py b/virtManager/details.py
+index b2d496e..79db2cf 100644
+--- a/virtManager/details.py
++++ b/virtManager/details.py
+@@ -2598,8 +2598,14 @@ class vmmDetails(vmmGObjectUI):
+ 
+         # If the dialog is visible, we want to make sure the XML is always
+         # up to date
+-        if self.is_visible():
+-            self.vm.refresh_xml()
++        try:
++            if self.is_visible():
++                self.vm.refresh_xml()
++        except libvirt.libvirtError, e:
++            if uihelpers.exception_is_libvirt_error(e, "VIR_ERR_NO_DOMAIN"):
++                self.close()
++                return
++            raise
+ 
+         # Stats page needs to be refreshed every tick
+         if (page == PAGE_DETAILS and
+diff --git a/virtManager/domain.py b/virtManager/domain.py
+index bd3d964..486664f 100644
+--- a/virtManager/domain.py
++++ b/virtManager/domain.py
+@@ -32,6 +32,7 @@ from virtinst.VirtualCharDevice import VirtualCharSpicevmcDevice
+ import virtinst.support as support
+ 
+ from virtManager import util
++from virtManager import uihelpers
+ from virtManager.libvirtobject import vmmLibvirtObject
+ 
+ 
+@@ -406,7 +407,12 @@ class vmmDomain(vmmLibvirtObject):
+                               caps=self.conn.get_capabilities())
+ 
+     def _reparse_xml(self, ignore=None):
+-        self._guest = self._build_guest(self._get_domain_xml())
++        try:
++            self._guest = self._build_guest(self._get_domain_xml())
++        except libvirt.libvirtError, e:
++            if uihelpers.exception_is_libvirt_error(e, "VIR_ERR_NO_DOMAIN"):
++                return
++            raise
+ 
+ 
+     ##############################
+@@ -1566,14 +1572,12 @@ class vmmDomain(vmmLibvirtObject):
+         """
+         try:
+             info = self._backend.info()
++            self._update_status(info[0])
+         except libvirt.libvirtError, e:
+-            if (hasattr(libvirt, "VIR_ERR_NO_DOMAIN") and
+-                e.get_error_code() == getattr(libvirt, "VIR_ERR_NO_DOMAIN")):
+-                # Possibly a transient domain that was removed on shutdown
++            if uihelpers.exception_is_libvirt_error(e, "VIR_ERR_NO_DOMAIN"):
+                 return
+             raise
+ 
+-        self._update_status(info[0])
+ 
+     def _update_status(self, status):
+         """
+diff --git a/virtManager/manager.py b/virtManager/manager.py
+index 3682429..97cb068 100644
+--- a/virtManager/manager.py
++++ b/virtManager/manager.py
+@@ -35,6 +35,7 @@ from virtManager.baseclass import vmmGObjectUI
+ from virtManager.graphwidgets import CellRendererSparkline
+ from virtManager import util as util
+ 
++import libvirt
+ 
+ # Number of data points for performance graphs
+ GRAPH_LEN = 40
+@@ -936,18 +937,24 @@ class vmmManager(vmmGObjectUI):
+         if self.vm_row_key(vm) not in self.rows:
+             return
+ 
+-        row = self.rows[self.vm_row_key(vm)]
+-        row[ROW_NAME] = vm.get_name()
+-        row[ROW_STATUS] = vm.run_status()
+-        row[ROW_STATUS_ICON] = vm.run_status_icon_name()
+-        row[ROW_IS_VM_RUNNING] = vm.is_active()
+-        row[ROW_MARKUP] = self._build_vm_markup(row)
+ 
+-        if config_changed:
+-            desc = vm.get_description()
+-            if not can_set_row_none:
+-                desc = desc or ""
+-            row[ROW_HINT] = util.xml_escape(desc)
++        try:
++            row = self.rows[self.vm_row_key(vm)]
++            row[ROW_NAME] = vm.get_name()
++            row[ROW_STATUS] = vm.run_status()
++            row[ROW_STATUS_ICON] = vm.run_status_icon_name()
++            row[ROW_IS_VM_RUNNING] = vm.is_active()
++            row[ROW_MARKUP] = self._build_vm_markup(row)
++
++            if config_changed:
++                desc = vm.get_description()
++                if not can_set_row_none:
++                    desc = desc or ""
++                    row[ROW_HINT] = util.xml_escape(desc)
++        except libvirt.libvirtError, e:
++            if uihelpers.exception_is_libvirt_error(e, "VIR_ERR_NO_DOMAIN"):
++                return
++            raise
+ 
+         model.row_changed(row.path, row.iter)
+ 
+diff --git a/virtManager/uihelpers.py b/virtManager/uihelpers.py
+index ba69ee9..ff254ab 100644
+--- a/virtManager/uihelpers.py
++++ b/virtManager/uihelpers.py
+@@ -1027,3 +1027,8 @@ def build_keycombo_menu(cb):
+ 
+     menu.show_all()
+     return menu
++
++def exception_is_libvirt_error(e, error):
++    import libvirt
++    return (hasattr(libvirt, error) and
++            e.get_error_code() == getattr(libvirt, error))
diff --git a/0006-manager-Merge-some-row-creation-drop-unneeded-row-ke.patch b/0006-manager-Merge-some-row-creation-drop-unneeded-row-ke.patch
new file mode 100644
index 0000000..c4cc0fd
--- /dev/null
+++ b/0006-manager-Merge-some-row-creation-drop-unneeded-row-ke.patch
@@ -0,0 +1,316 @@
+From c3e576155228cc3f3f05d3953edadbf589b74d8c Mon Sep 17 00:00:00 2001
+From: Cole Robinson <crobinso at redhat.com>
+Date: Sun, 1 Sep 2013 18:36:58 -0400
+Subject: [PATCH] manager: Merge some row creation, drop unneeded row keys
+
+(cherry picked from commit 1bd6026515324430adbdd7a8b666e1b6a64879c3)
+
+Conflicts:
+	virtManager/manager.py
+---
+ virtManager/manager.py | 174 ++++++++++++++++++++++---------------------------
+ 1 file changed, 79 insertions(+), 95 deletions(-)
+
+diff --git a/virtManager/manager.py b/virtManager/manager.py
+index 97cb068..2770b2f 100644
+--- a/virtManager/manager.py
++++ b/virtManager/manager.py
+@@ -42,18 +42,16 @@ GRAPH_LEN = 40
+ 
+ # fields in the tree model data set
+ (ROW_HANDLE,
+-ROW_NAME,
++ROW_SORT_KEY,
+ ROW_MARKUP,
+-ROW_STATUS,
+ ROW_STATUS_ICON,
+-ROW_KEY,
+ ROW_HINT,
+ ROW_IS_CONN,
+ ROW_IS_CONN_CONNECTED,
+ ROW_IS_VM,
+ ROW_IS_VM_RUNNING,
+ ROW_COLOR,
+-ROW_INSPECTION_OS_ICON) = range(13)
++ROW_INSPECTION_OS_ICON) = range(11)
+ 
+ # Columns in the tree view
+ COL_NAME = 0
+@@ -78,6 +76,24 @@ def _style_get_prop(widget, propname):
+     return value.get_int()
+ 
+ 
++def _get_inspection_icon_pixbuf(vm, w, h):
++    # libguestfs gives us the PNG data as a string.
++    png_data = vm.inspection.icon
++    if png_data is None:
++        return None
++
++    try:
++        pb = GdkPixbuf.PixbufLoader()
++        pb.set_size(w, h)
++        pb.write(png_data)
++        pb.close()
++        return pb.get_pixbuf()
++    except:
++        logging.exception("Error loading inspection icon data")
++        vm.inspection.icon = None
++        return None
++
++
+ class vmmManager(vmmGObjectUI):
+     __gsignals__ = {
+         "action-show-connect": (GObject.SignalFlags.RUN_FIRST, None, []),
+@@ -380,11 +396,9 @@ class vmmManager(vmmGObjectUI):
+ 
+         rowtypes = []
+         rowtypes.insert(ROW_HANDLE, object)  # backing object
+-        rowtypes.insert(ROW_NAME, str)  # object name
++        rowtypes.insert(ROW_SORT_KEY, str)  # object name
+         rowtypes.insert(ROW_MARKUP, str)  # row markup text
+-        rowtypes.insert(ROW_STATUS, str)  # object status string
+         rowtypes.insert(ROW_STATUS_ICON, str)  # status icon name
+-        rowtypes.insert(ROW_KEY, str)  # key/uuid
+         rowtypes.insert(ROW_HINT, str)  # row tooltip
+         rowtypes.insert(ROW_IS_CONN, bool)  # if object is a connection
+         rowtypes.insert(ROW_IS_CONN_CONNECTED, bool)  # if conn is connected
+@@ -764,8 +778,8 @@ class vmmManager(vmmGObjectUI):
+             hint += " (%s)" % _("Double click to connect")
+         return hint
+ 
+-    def _build_conn_markup(self, conn, row):
+-        name = util.xml_escape(row[ROW_NAME])
++    def _build_conn_markup(self, conn, name):
++        name = util.xml_escape(name)
+         text = name
+         if conn.state == conn.STATE_DISCONNECTED:
+             text += " - " + _("Not Connected")
+@@ -781,31 +795,44 @@ class vmmManager(vmmGObjectUI):
+             color = "#5b5b5b"
+         return color
+ 
+-    def _build_vm_markup(self, row):
++    def _build_vm_markup(self, name, status):
+         domtext     = ("<span size='smaller' weight='bold'>%s</span>" %
+-                       util.xml_escape(row[ROW_NAME]))
+-        statetext   = "<span size='smaller'>%s</span>" % row[ROW_STATUS]
++                       util.xml_escape(name))
++        statetext   = "<span size='smaller'>%s</span>" % status
+         return domtext + "\n" + statetext
+ 
+-    def _build_vm_row(self, vm):
+-        row = []
++    def _build_row(self, conn, vm):
++        if conn:
++            name = conn.get_pretty_desc_inactive(False)
++            markup = self._build_conn_markup(conn, name)
++            status = ("<span size='smaller'>%s</span>" %
++                      conn.get_state_text())
++            status_icon = None
++            hint = self._build_conn_hint(conn)
++            color = self._build_conn_color(conn)
++            os_icon = None
++        else:
++            name = vm.get_name()
++            status = vm.run_status()
++            markup = self._build_vm_markup(name, status)
++            status_icon = vm.run_status_icon_name()
++            hint = vm.get_description()
++            color = None
++            os_icon = _get_inspection_icon_pixbuf(vm, 16, 16)
+ 
+-        row.insert(ROW_HANDLE, vm)
+-        row.insert(ROW_NAME, vm.get_name())
+-        row.insert(ROW_MARKUP, "")
+-        row.insert(ROW_STATUS, vm.run_status())
+-        row.insert(ROW_STATUS_ICON, vm.run_status_icon_name())
+-        row.insert(ROW_KEY, vm.get_uuid())
+-        row.insert(ROW_HINT, util.xml_escape(vm.get_description()))
+-        row.insert(ROW_IS_CONN, False)
+-        row.insert(ROW_IS_CONN_CONNECTED, True)
+-        row.insert(ROW_IS_VM, True)
+-        row.insert(ROW_IS_VM_RUNNING, vm.is_active())
+-        row.insert(ROW_COLOR, None)
+-        row.insert(ROW_INSPECTION_OS_ICON,
+-                   self.get_inspection_icon_pixbuf(vm, 16, 16))
+-
+-        row[ROW_MARKUP] = self._build_vm_markup(row)
++        row = []
++        row.insert(ROW_HANDLE, conn or vm)
++        row.insert(ROW_SORT_KEY, name)
++        row.insert(ROW_MARKUP, markup)
++        row.insert(ROW_STATUS_ICON, status_icon)
++        row.insert(ROW_HINT, util.xml_escape(hint))
++        row.insert(ROW_IS_CONN, bool(conn))
++        row.insert(ROW_IS_CONN_CONNECTED,
++                   bool(conn) and conn.state != conn.STATE_DISCONNECTED)
++        row.insert(ROW_IS_VM, bool(vm))
++        row.insert(ROW_IS_VM_RUNNING, bool(vm) and vm.is_active())
++        row.insert(ROW_COLOR, color)
++        row.insert(ROW_INSPECTION_OS_ICON, os_icon)
+ 
+         return row
+ 
+@@ -814,7 +841,7 @@ class vmmManager(vmmGObjectUI):
+         if row_key in self.rows:
+             return
+ 
+-        row = self._build_vm_row(vm)
++        row = self._build_row(None, vm)
+         parent = self.rows[conn.get_uri()].iter
+ 
+         _iter = model.append(parent, row)
+@@ -824,28 +851,8 @@ class vmmManager(vmmGObjectUI):
+         # Expand a connection when adding a vm to it
+         self.widget("vm-list").expand_row(model.get_path(parent), False)
+ 
+-    def _build_conn_row(self, conn):
+-        row = []
+-        row.insert(ROW_HANDLE, conn)
+-        row.insert(ROW_NAME, conn.get_pretty_desc_inactive(False))
+-        row.insert(ROW_MARKUP, self._build_conn_markup(conn, row))
+-        row.insert(ROW_STATUS, ("<span size='smaller'>%s</span>" %
+-                                conn.get_state_text()))
+-        row.insert(ROW_STATUS_ICON, None)
+-        row.insert(ROW_KEY, conn.get_uri())
+-        row.insert(ROW_HINT, self._build_conn_hint(conn))
+-        row.insert(ROW_IS_CONN, True)
+-        row.insert(ROW_IS_CONN_CONNECTED,
+-                   conn.state != conn.STATE_DISCONNECTED)
+-        row.insert(ROW_IS_VM, False)
+-        row.insert(ROW_IS_VM_RUNNING, False)
+-        row.insert(ROW_COLOR, self._build_conn_color(conn))
+-        row.insert(ROW_INSPECTION_OS_ICON, None)
+-
+-        return row
+-
+     def _append_conn(self, model, conn):
+-        row = self._build_conn_row(conn)
++        row = self._build_row(conn, None)
+ 
+         _iter = model.append(None, row)
+         path = model.get_path(_iter)
+@@ -877,11 +884,11 @@ class vmmManager(vmmGObjectUI):
+             if row[ROW_IS_CONN]:
+                 connrows.append(row)
+         for row in connrows:
+-            descs.append(row[ROW_NAME])
++            descs.append(row[ROW_SORT_KEY])
+ 
+         for row in connrows:
+             conn = row[ROW_HANDLE]
+-            name = row[ROW_NAME]
++            name = row[ROW_SORT_KEY]
+             if descs.count(name) <= 1:
+                 continue
+ 
+@@ -919,7 +926,7 @@ class vmmManager(vmmGObjectUI):
+         missing = True
+         for row in range(model.iter_n_children(parent)):
+             _iter = model.iter_nth_child(parent, row)
+-            if model.get_value(_iter, ROW_KEY) == vm.get_uuid():
++            if model.get_value(_iter, ROW_HANDLE) == vm:
+                 missing = False
+                 break
+ 
+@@ -931,20 +938,18 @@ class vmmManager(vmmGObjectUI):
+         self.vm_resources_sampled(vm)
+ 
+     def vm_resources_sampled(self, vm, config_changed=False):
+-        vmlist = self.widget("vm-list")
+-        model = vmlist.get_model()
+-
+-        if self.vm_row_key(vm) not in self.rows:
++        row = self.rows.get(self.vm_row_key(vm), None)
++        if row is None:
+             return
+ 
+-
+         try:
+-            row = self.rows[self.vm_row_key(vm)]
+-            row[ROW_NAME] = vm.get_name()
+-            row[ROW_STATUS] = vm.run_status()
++            name = vm.get_name()
++            status = vm.run_status()
++
++            row[ROW_SORT_KEY] = name
+             row[ROW_STATUS_ICON] = vm.run_status_icon_name()
+             row[ROW_IS_VM_RUNNING] = vm.is_active()
+-            row[ROW_MARKUP] = self._build_vm_markup(row)
++            row[ROW_MARKUP] = self._build_vm_markup(name, status)
+ 
+             if config_changed:
+                 desc = vm.get_description()
+@@ -956,53 +961,32 @@ class vmmManager(vmmGObjectUI):
+                 return
+             raise
+ 
+-        model.row_changed(row.path, row.iter)
++        self.widget("vm-list").get_model().row_changed(row.path, row.iter)
+ 
+     def vm_inspection_changed(self, vm):
+-        vmlist = self.widget("vm-list")
+-        model = vmlist.get_model()
+-
+-        if self.vm_row_key(vm) not in self.rows:
++        row = self.rows.get(self.vm_row_key(vm), None)
++        if row is None:
+             return
+ 
+         row = self.rows[self.vm_row_key(vm)]
+-        new_icon = self.get_inspection_icon_pixbuf(vm, 16, 16)
++        new_icon = _get_inspection_icon_pixbuf(vm, 16, 16)
+         if not can_set_row_none:
+             new_icon = new_icon or ""
+         row[ROW_INSPECTION_OS_ICON] = new_icon
+-        model.row_changed(row.path, row.iter)
+-
+-    def get_inspection_icon_pixbuf(self, vm, w, h):
+-        # libguestfs gives us the PNG data as a string.
+-        png_data = vm.inspection.icon
+-        if png_data is None:
+-            return None
+ 
+-        try:
+-            pb = GdkPixbuf.PixbufLoader()
+-            pb.set_size(w, h)
+-            pb.write(png_data)
+-            pb.close()
+-            return pb.get_pixbuf()
+-        except:
+-            logging.exception("Error loading inspection icon data")
+-            vm.inspection.icon = None
+-            return None
++        self.widget("vm-list").get_model().row_changed(row.path, row.iter)
+ 
+     def conn_state_changed(self, conn):
+         self.conn_resources_sampled(conn)
+         self.vm_selected()
+ 
+     def conn_resources_sampled(self, conn, newname=None):
+-        vmlist = self.widget("vm-list")
+-        model = vmlist.get_model()
++        model = self.widget("vm-list").get_model()
+         row = self.rows[conn.get_uri()]
+ 
+         if newname:
+-            row[ROW_NAME] = newname
+-        row[ROW_MARKUP] = self._build_conn_markup(conn, row)
+-        row[ROW_STATUS] = ("<span size='smaller'>%s</span>" %
+-                           conn.get_state_text())
++            row[ROW_SORT_KEY] = newname
++        row[ROW_MARKUP] = self._build_conn_markup(conn, row[ROW_SORT_KEY])
+         row[ROW_IS_CONN_CONNECTED] = conn.state != conn.STATE_DISCONNECTED
+         row[ROW_COLOR] = self._build_conn_color(conn)
+         row[ROW_HINT] = self._build_conn_hint(conn)
+@@ -1131,8 +1115,8 @@ class vmmManager(vmmGObjectUI):
+     #################
+ 
+     def vmlist_name_sorter(self, model, iter1, iter2, ignore):
+-        return cmp(model.get_value(iter1, ROW_NAME),
+-                   model.get_value(iter2, ROW_NAME))
++        return cmp(model.get_value(iter1, ROW_SORT_KEY),
++                   model.get_value(iter2, ROW_SORT_KEY))
+ 
+     def vmlist_guest_cpu_usage_sorter(self, model, iter1, iter2, ignore):
+         obj1 = model.get_value(iter1, ROW_HANDLE)
diff --git a/0007-manager-Separate-stats-and-state-update-callbacks.patch b/0007-manager-Separate-stats-and-state-update-callbacks.patch
new file mode 100644
index 0000000..2a762e0
--- /dev/null
+++ b/0007-manager-Separate-stats-and-state-update-callbacks.patch
@@ -0,0 +1,204 @@
+From ed5dc524c54e72ee7f75749f11eb0606dddee8ea Mon Sep 17 00:00:00 2001
+From: Cole Robinson <crobinso at redhat.com>
+Date: Mon, 2 Sep 2013 09:09:31 -0400
+Subject: [PATCH] manager: Separate stats and state update callbacks
+
+There's no need to be resetting row keys like VM name, state, on every
+'resources-sampled' signals, since we have had finer grained status-changed
+and config-changed signals for a while. This seems to reduce the memory
+leak on F19 as well.
+
+(cherry picked from commit f141c77c452d4807b516bdc40a0e86235bf5243a)
+
+Conflicts:
+	virtManager/manager.py
+---
+ virtManager/manager.py | 100 ++++++++++++++++++++++++++-----------------------
+ 1 file changed, 53 insertions(+), 47 deletions(-)
+
+diff --git a/virtManager/manager.py b/virtManager/manager.py
+index 2770b2f..6773ff3 100644
+--- a/virtManager/manager.py
++++ b/virtManager/manager.py
+@@ -185,9 +185,9 @@ class vmmManager(vmmGObjectUI):
+         self.init_toolbar()
+         self.init_context_menus()
+ 
+-        self.vm_selected()
+-        self.widget("vm-list").get_selection().connect("changed",
+-                                                       self.vm_selected)
++        self.update_current_selection()
++        self.widget("vm-list").get_selection().connect(
++            "changed", self.update_current_selection)
+ 
+         self.max_disk_rate = 10.0
+         self.max_net_rate = 10.0
+@@ -750,9 +750,9 @@ class vmmManager(vmmGObjectUI):
+ 
+     def vm_added(self, conn, vmuuid):
+         vm = conn.get_vm(vmuuid)
++        vm.connect("config-changed", self.vm_config_changed)
+         vm.connect("status-changed", self.vm_status_changed)
+-        vm.connect("resources-sampled", self.vm_resources_sampled)
+-        vm.connect("config-changed", self.vm_resources_sampled, True)
++        vm.connect("resources-sampled", self.vm_row_updated)
+         vm.connect("inspection-changed", self.vm_inspection_changed)
+ 
+         vmlist = self.widget("vm-list")
+@@ -868,7 +868,7 @@ class vmmManager(vmmGObjectUI):
+ 
+         conn.connect("vm-added", self.vm_added)
+         conn.connect("vm-removed", self.vm_removed)
+-        conn.connect("resources-sampled", self.conn_resources_sampled)
++        conn.connect("resources-sampled", self.conn_row_updated)
+         conn.connect("state-changed", self.conn_state_changed)
+         conn.connect("connect-error", self._connect_error)
+ 
+@@ -893,7 +893,7 @@ class vmmManager(vmmGObjectUI):
+                 continue
+ 
+             newname = conn.get_pretty_desc_inactive(False, True)
+-            self.conn_resources_sampled(conn, newname)
++            self.conn_state_changed(conn, newname=newname)
+ 
+     def remove_conn(self, engine_ignore, uri):
+         model = self.widget("vm-list").get_model()
+@@ -916,28 +916,13 @@ class vmmManager(vmmGObjectUI):
+     # State/UI updating methods #
+     #############################
+ 
+-    def vm_status_changed(self, vm, oldstatus, newstatus):
+-        ignore = newstatus
+-        ignore = oldstatus
+-        parent = self.rows[vm.conn.get_uri()].iter
+-        vmlist = self.widget("vm-list")
+-        model = vmlist.get_model()
+-
+-        missing = True
+-        for row in range(model.iter_n_children(parent)):
+-            _iter = model.iter_nth_child(parent, row)
+-            if model.get_value(_iter, ROW_HANDLE) == vm:
+-                missing = False
+-                break
+-
+-        if missing:
+-            self._append_vm(model, vm, vm.conn)
+-
+-        # Update run/shutdown/pause button states
+-        self.vm_selected()
+-        self.vm_resources_sampled(vm)
++    def vm_row_updated(self, vm):
++        row = self.rows.get(self.vm_row_key(vm), None)
++        if row is None:
++            return
++        self.widget("vm-list").get_model().row_changed(row.path, row.iter)
+ 
+-    def vm_resources_sampled(self, vm, config_changed=False):
++    def vm_config_changed(self, vm):
+         row = self.rows.get(self.vm_row_key(vm), None)
+         if row is None:
+             return
+@@ -951,17 +936,37 @@ class vmmManager(vmmGObjectUI):
+             row[ROW_IS_VM_RUNNING] = vm.is_active()
+             row[ROW_MARKUP] = self._build_vm_markup(name, status)
+ 
+-            if config_changed:
+-                desc = vm.get_description()
+-                if not can_set_row_none:
+-                    desc = desc or ""
+-                    row[ROW_HINT] = util.xml_escape(desc)
++            desc = vm.get_description()
++            if not can_set_row_none:
++                desc = desc or ""
++            row[ROW_HINT] = util.xml_escape(desc)
+         except libvirt.libvirtError, e:
+             if uihelpers.exception_is_libvirt_error(e, "VIR_ERR_NO_DOMAIN"):
+                 return
+             raise
+ 
+-        self.widget("vm-list").get_model().row_changed(row.path, row.iter)
++        self.vm_row_updated(vm)
++
++    def vm_status_changed(self, vm, oldstatus, newstatus):
++        ignore = newstatus
++        ignore = oldstatus
++        parent = self.rows[vm.conn.get_uri()].iter
++        vmlist = self.widget("vm-list")
++        model = vmlist.get_model()
++
++        missing = True
++        for row in range(model.iter_n_children(parent)):
++            _iter = model.iter_nth_child(parent, row)
++            if model.get_value(_iter, ROW_HANDLE) == vm:
++                missing = False
++                break
++
++        if missing:
++            self._append_vm(model, vm, vm.conn)
++
++        # Update run/shutdown/pause button states
++        self.update_current_selection()
++        self.vm_config_changed(vm)
+ 
+     def vm_inspection_changed(self, vm):
+         row = self.rows.get(self.vm_row_key(vm), None)
+@@ -974,16 +979,10 @@ class vmmManager(vmmGObjectUI):
+             new_icon = new_icon or ""
+         row[ROW_INSPECTION_OS_ICON] = new_icon
+ 
+-        self.widget("vm-list").get_model().row_changed(row.path, row.iter)
+-
+-    def conn_state_changed(self, conn):
+-        self.conn_resources_sampled(conn)
+-        self.vm_selected()
++        self.vm_row_updated(vm)
+ 
+-    def conn_resources_sampled(self, conn, newname=None):
+-        model = self.widget("vm-list").get_model()
++    def conn_state_changed(self, conn, newname=None):
+         row = self.rows[conn.get_uri()]
+-
+         if newname:
+             row[ROW_SORT_KEY] = newname
+         row[ROW_MARKUP] = self._build_conn_markup(conn, row[ROW_SORT_KEY])
+@@ -994,20 +993,27 @@ class vmmManager(vmmGObjectUI):
+         if conn.get_state() in [vmmConnection.STATE_DISCONNECTED,
+                                 vmmConnection.STATE_CONNECTING]:
+             # Connection went inactive, delete any VM child nodes
+-            parent = self.rows[conn.get_uri()].iter
++            parent = row.iter
+             if parent is not None:
++                model = self.widget("vm-list").get_model()
+                 child = model.iter_children(parent)
+                 while child is not None:
+-                    del self.rows[self.vm_row_key(model.get_value(child,
+-                                                                  ROW_HANDLE))]
++                    vm = model[child][ROW_HANDLE]
++                    del self.rows[self.vm_row_key(vm)]
+                     model.remove(child)
+                     child = model.iter_children(parent)
+ 
++        self.conn_row_updated(conn)
++        self.update_current_selection()
++
++    def conn_row_updated(self, conn):
++        row = self.rows[conn.get_uri()]
++
+         self.max_disk_rate = max(self.max_disk_rate, conn.disk_io_max_rate())
+         self.max_net_rate = max(self.max_net_rate,
+                                 conn.network_traffic_max_rate())
+ 
+-        model.row_changed(row.path, row.iter)
++        self.widget("vm-list").get_model().row_changed(row.path, row.iter)
+ 
+     def change_run_text(self, can_restore):
+         if can_restore:
+@@ -1019,7 +1025,7 @@ class vmmManager(vmmGObjectUI):
+         self.vmmenu_items["run"].get_child().set_label(text)
+         self.widget("vm-run").set_label(strip_text)
+ 
+-    def vm_selected(self, ignore=None):
++    def update_current_selection(self, ignore=None):
+         vm = self.current_vm()
+ 
+         show_open = bool(vm)
diff --git a/virt-manager.spec b/virt-manager.spec
index f0aedb8..1b5f9f7 100644
--- a/virt-manager.spec
+++ b/virt-manager.spec
@@ -21,7 +21,7 @@
 
 
 %define _version 0.10.0
-%define _release 1
+%define _release 2
 
 
 # This macro is used for the continuous automated builds. It just
@@ -40,6 +40,17 @@ Group: Applications/Emulators
 License: GPLv2+
 URL: http://virt-manager.org/
 Source0: http://virt-manager.org/download/sources/%{name}/%{name}-%{version}.tar.gz
+
+# Fix parsing rawhide .treeinfo (bz #989162)
+Patch0001: 0001-Fix-rawhide-URL-installs.patch
+# Fix spice with TLS (bz #904295)
+Patch0002: 0002-console-Fix-spice-with-TLS-bz-904295.patch
+# Reduce impact of memory leak (bz #972371)
+Patch0003: 0003-manager-Disable-graph-data-func-if-graph-isn-t-visib.patch
+Patch0004: 0004-inspection-Check-can_set_row_none-before-setting-ico.patch
+Patch0005: 0005-virt-manager-ignore-VIR_ERR_NO_DOMAIN-when-a-domain-.patch
+Patch0006: 0006-manager-Merge-some-row-creation-drop-unneeded-row-ke.patch
+Patch0007: 0007-manager-Separate-stats-and-state-update-callbacks.patch
 BuildArch: noarch
 
 
@@ -104,6 +115,17 @@ machine).
 %prep
 %setup -q
 
+# Fix parsing rawhide .treeinfo (bz #989162)
+%patch0001 -p1
+# Fix spice with TLS (bz #904295)
+%patch0002 -p1
+# Reduce impact of memory leak (bz #972371)
+%patch0003 -p1
+%patch0004 -p1
+%patch0005 -p1
+%patch0006 -p1
+%patch0007 -p1
+
 %build
 %if %{qemu_user}
 %define _qemu_user --qemu-user=%{qemu_user}
@@ -213,6 +235,11 @@ fi
 
 
 %changelog
+* Tue Sep 24 2013 Cole Robinson <crobinso at redhat.com> - 0.10.0-2
+- Fix parsing rawhide .treeinfo (bz #989162)
+- Fix spice with TLS (bz #904295)
+- Reduce impact of memory leak (bz #972371)
+
 * Wed Jun 19 2013 Cole Robinson <crobinso at redhat.com> - 0.10.0-1
 - Rebased to version 0.10.0
 - Fix screenshots (bz #969410)


More information about the scm-commits mailing list