[openstack-nova/f17] Update from latest stable/essex

Pádraig Brady pbrady at fedoraproject.org
Mon Jul 30 02:44:07 UTC 2012


commit 6f3f951a2c698ece5aaf9c18ee079ce6729ce9dd
Author: Pádraig Brady <P at draigBrady.com>
Date:   Mon Jul 30 02:44:36 2012 +0100

    Update from latest stable/essex

 ...bvirt_volume_driver-with-right-mountpoint.patch |    0
 ...e_libvirt_utils-for-libvirt-console-tests.patch |    0
 ..._allocation_ratio-based-over-subscription.patch |    0
 ...pam_lib-from-changing-the-timeout-setting.patch |    0
 ...file-injection-writing-to-host-filesystem.patch |    0
 ...ish-over-quota-for-volume-size-and-number.patch |    0
 ...pose-over-quota-exceptions-via-native-API.patch |    0
 ...0011-Fix-call-to-network_get_all_by_uuids.patch |    0
 ...-fix-libvirt-get_memory_mb_total-with-xen.patch |    0
 ...ibguestfs-has-completed-before-proceeding.patch |    2 +-
 ...e-compute_api.get_all-in-affinity-filters.patch |    0
 0015-fix-metadata-file-injection-with-xen.patch    |   27 +++
 ...Fixes-affinity-filters-when-hints-is-None.patch |  108 ++++++++++++
 ...al-CommandFilters-to-fix-rootwrap-on-SLES.patch |   94 ++++++++++
 0018-Fix-marker-behavior-for-flavors.patch         |  108 ++++++++++++
 ...-qemu-img-cluster-size-in-libvirt-connect.patch |    0
 ...13-status-on-over-quota-in-the-native-API.patch |    0
 ...ndle-local-remote-exceptions-consistently.patch |  147 ++++++++++++++++
 ...rt-fix-qcow2-size-on-live-block-migration.patch |   30 +++
 ...-Backport-fix-for-API-listing-of-os-hosts.patch |   73 ++++++++
 ...void-lazy-loading-errors-on-instance_type.patch |   40 +++++
 ...casts-in-network-manager-to-prevent-races.patch |   82 +++++++++
 ...onally-allow-queries-for-deleted-flavours.patch |  141 +++++++++++++++
 0027-Fix-wrong-regex-in-cleanup_file_locks.patch   |   58 ++++++
 ...tomic-manipulation-of-libvirt-disk-images.patch |    6 +-
 ...e-don-t-access-the-net-when-building-docs.patch |    2 +-
 ...0030-fix-useexisting-deprecation-warnings.patch |    2 +-
 ...-configurable-libvirt-injection-partition.patch |    4 +-
 ...unt-guest-image-once-when-injecting-files.patch |    4 +-
 ...ect-SELinux-context-for-injected-ssh-keys.patch |    6 +-
 ...4-ensure-libguestfs-mounts-are-cleaned-up.patch |    2 +-
 ...orking-rules-to-vm-s-on-compute-service-s.patch |   45 +++++
 ...-when-parsing-null-connection-info-in-BDM.patch |   41 +++++
 ...-EC2-CreateImage-API-for-boot-from-volume.patch |  185 ++++++++++++++++++++
 ...ribeImages-reports-correct-rootDeviceType.patch |   66 +++++++
 ...Reject-EC2-CreateImage-for-instance-store.patch |  158 +++++++++++++++++
 0040-Fix-EC2-CreateImage-no_reboot-logic.patch     |   94 ++++++++++
 ...HTTPResponse-class-for-versions-of-boto-2.patch |   66 +++++++
 ...vert-remaining-network-API-casts-to-calls.patch |   97 ++++++++++
 ...g-where-the-fixed-ip-deallocation-happens.patch |  106 +++++++++++
 ...d_heartbeat-option-so-that-it-s-effective.patch |   27 +++
 openstack-nova.spec                                |  108 +++++++++---
 42 files changed, 1893 insertions(+), 36 deletions(-)
---
diff --git a/0003-Call-libvirt_volume_driver-with-right-mountpoint.patch b/0004-Call-libvirt_volume_driver-with-right-mountpoint.patch
similarity index 100%
rename from 0003-Call-libvirt_volume_driver-with-right-mountpoint.patch
rename to 0004-Call-libvirt_volume_driver-with-right-mountpoint.patch
diff --git a/0004-Use-fake_libvirt_utils-for-libvirt-console-tests.patch b/0005-Use-fake_libvirt_utils-for-libvirt-console-tests.patch
similarity index 100%
rename from 0004-Use-fake_libvirt_utils-for-libvirt-console-tests.patch
rename to 0005-Use-fake_libvirt_utils-for-libvirt-console-tests.patch
diff --git a/0005-Fixes-ram_allocation_ratio-based-over-subscription.patch b/0006-Fixes-ram_allocation_ratio-based-over-subscription.patch
similarity index 100%
rename from 0005-Fixes-ram_allocation_ratio-based-over-subscription.patch
rename to 0006-Fixes-ram_allocation_ratio-based-over-subscription.patch
diff --git a/0006-Stop-nova_ipam_lib-from-changing-the-timeout-setting.patch b/0007-Stop-nova_ipam_lib-from-changing-the-timeout-setting.patch
similarity index 100%
rename from 0006-Stop-nova_ipam_lib-from-changing-the-timeout-setting.patch
rename to 0007-Stop-nova_ipam_lib-from-changing-the-timeout-setting.patch
diff --git a/0007-Prevent-file-injection-writing-to-host-filesystem.patch b/0008-Prevent-file-injection-writing-to-host-filesystem.patch
similarity index 100%
rename from 0007-Prevent-file-injection-writing-to-host-filesystem.patch
rename to 0008-Prevent-file-injection-writing-to-host-filesystem.patch
diff --git a/0008-Distinguish-over-quota-for-volume-size-and-number.patch b/0009-Distinguish-over-quota-for-volume-size-and-number.patch
similarity index 100%
rename from 0008-Distinguish-over-quota-for-volume-size-and-number.patch
rename to 0009-Distinguish-over-quota-for-volume-size-and-number.patch
diff --git a/0009-Expose-over-quota-exceptions-via-native-API.patch b/0010-Expose-over-quota-exceptions-via-native-API.patch
similarity index 100%
rename from 0009-Expose-over-quota-exceptions-via-native-API.patch
rename to 0010-Expose-over-quota-exceptions-via-native-API.patch
diff --git a/0010-Fix-call-to-network_get_all_by_uuids.patch b/0011-Fix-call-to-network_get_all_by_uuids.patch
similarity index 100%
rename from 0010-Fix-call-to-network_get_all_by_uuids.patch
rename to 0011-Fix-call-to-network_get_all_by_uuids.patch
diff --git a/0011-fix-libvirt-get_memory_mb_total-with-xen.patch b/0012-fix-libvirt-get_memory_mb_total-with-xen.patch
similarity index 100%
rename from 0011-fix-libvirt-get_memory_mb_total-with-xen.patch
rename to 0012-fix-libvirt-get_memory_mb_total-with-xen.patch
diff --git a/0021-ensure-libguestfs-has-completed-before-proceeding.patch b/0013-ensure-libguestfs-has-completed-before-proceeding.patch
similarity index 96%
rename from 0021-ensure-libguestfs-has-completed-before-proceeding.patch
rename to 0013-ensure-libguestfs-has-completed-before-proceeding.patch
index e975238..796c7ee 100644
--- a/0021-ensure-libguestfs-has-completed-before-proceeding.patch
+++ b/0013-ensure-libguestfs-has-completed-before-proceeding.patch
@@ -1,4 +1,4 @@
-From 7656d036b559b5337bf36f3a6676d75edb52d8ab Mon Sep 17 00:00:00 2001
+From 1c1b858e919248d6e3fb11c1022532ba40e75844 Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Tue, 10 Jul 2012 15:22:39 +0100
 Subject: [PATCH] ensure libguestfs has completed before proceeding
diff --git a/0012-Use-compute_api.get_all-in-affinity-filters.patch b/0014-Use-compute_api.get_all-in-affinity-filters.patch
similarity index 100%
rename from 0012-Use-compute_api.get_all-in-affinity-filters.patch
rename to 0014-Use-compute_api.get_all-in-affinity-filters.patch
diff --git a/0015-fix-metadata-file-injection-with-xen.patch b/0015-fix-metadata-file-injection-with-xen.patch
new file mode 100644
index 0000000..f642aa7
--- /dev/null
+++ b/0015-fix-metadata-file-injection-with-xen.patch
@@ -0,0 +1,27 @@
+From 48e5f46f799ea5832f8d18cb2f34e98df9cda15a Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
+Date: Sat, 7 Jul 2012 10:37:46 +0100
+Subject: [PATCH] fix metadata file injection with xen
+
+The metadata parameter was misordered in commit 1463839f
+
+Cherry picked from commit a2032924
+Fixes Bug: 1022036
+Change-Id: Ica0e2f51b6852c8572bdc3c995cc8c2588b9a25c
+---
+ nova/virt/xenapi/vm_utils.py |    2 +-
+ 1 files changed, 1 insertions(+), 1 deletions(-)
+
+diff --git a/nova/virt/xenapi/vm_utils.py b/nova/virt/xenapi/vm_utils.py
+index 012b6fb..a9a2670 100644
+--- a/nova/virt/xenapi/vm_utils.py
++++ b/nova/virt/xenapi/vm_utils.py
+@@ -1756,7 +1756,7 @@ def _mounted_processing(device, key, net, metadata):
+                     # for xenapi, we don't 'inject' admin_password here,
+                     # it's handled at instance startup time
+                     disk.inject_data_into_fs(tmpdir,
+-                                             key, net, None, metadata,
++                                             key, net, metadata, None,
+                                              utils.execute)
+             finally:
+                 utils.execute('umount', dev_path, run_as_root=True)
diff --git a/0016-Fixes-affinity-filters-when-hints-is-None.patch b/0016-Fixes-affinity-filters-when-hints-is-None.patch
new file mode 100644
index 0000000..2714500
--- /dev/null
+++ b/0016-Fixes-affinity-filters-when-hints-is-None.patch
@@ -0,0 +1,108 @@
+From 2efc87cc08e227d5623ff58c5c6fdfd02c8578df Mon Sep 17 00:00:00 2001
+From: Vishvananda Ishaya <vishvananda at gmail.com>
+Date: Fri, 1 Jun 2012 12:29:24 -0700
+Subject: [PATCH] Fixes affinity filters when hints is None
+
+ * Fixes bug 1007573
+ * Includes failing tests
+
+Change-Id: I827588f0694c5dd7b5e8ff3173d4794a55946d81
+(cherry picked from commit 4803074f2c02c87310c486f66fb66be98533805f)
+---
+ nova/scheduler/filters/affinity_filter.py |    6 ++--
+ nova/tests/scheduler/test_host_filters.py |   37 +++++++++++++++++++++++++++++
+ 2 files changed, 40 insertions(+), 3 deletions(-)
+
+diff --git a/nova/scheduler/filters/affinity_filter.py b/nova/scheduler/filters/affinity_filter.py
+index 81d9442..c2812ef 100644
+--- a/nova/scheduler/filters/affinity_filter.py
++++ b/nova/scheduler/filters/affinity_filter.py
+@@ -38,7 +38,7 @@ class DifferentHostFilter(AffinityFilter):
+ 
+     def host_passes(self, host_state, filter_properties):
+         context = filter_properties['context']
+-        scheduler_hints = filter_properties['scheduler_hints']
++        scheduler_hints = filter_properties.get('scheduler_hints') or {}
+         me = host_state.host
+ 
+         affinity_uuids = scheduler_hints.get('different_host', [])
+@@ -57,7 +57,7 @@ class SameHostFilter(AffinityFilter):
+ 
+     def host_passes(self, host_state, filter_properties):
+         context = filter_properties['context']
+-        scheduler_hints = filter_properties['scheduler_hints']
++        scheduler_hints = filter_properties.get('scheduler_hints') or {}
+         me = host_state.host
+ 
+         affinity_uuids = scheduler_hints.get('same_host', [])
+@@ -71,7 +71,7 @@ class SameHostFilter(AffinityFilter):
+ 
+ class SimpleCIDRAffinityFilter(AffinityFilter):
+     def host_passes(self, host_state, filter_properties):
+-        scheduler_hints = filter_properties['scheduler_hints']
++        scheduler_hints = filter_properties.get('scheduler_hints') or {}
+ 
+         affinity_cidr = scheduler_hints.get('cidr', '/24')
+         affinity_host_addr = scheduler_hints.get('build_near_host_ip')
+diff --git a/nova/tests/scheduler/test_host_filters.py b/nova/tests/scheduler/test_host_filters.py
+index f56a145..1648c58 100644
+--- a/nova/tests/scheduler/test_host_filters.py
++++ b/nova/tests/scheduler/test_host_filters.py
+@@ -107,6 +107,18 @@ class HostFiltersTestCase(test.TestCase):
+ 
+         self.assertFalse(filt_cls.host_passes(host, filter_properties))
+ 
++    def test_affinity_different_filter_handles_none(self):
++        filt_cls = self.class_map['DifferentHostFilter']()
++        host = fakes.FakeHostState('host1', 'compute', {})
++        instance = fakes.FakeInstance(context=self.context,
++                                         params={'host': 'host2'})
++        instance_uuid = instance.uuid
++
++        filter_properties = {'context': self.context.elevated(),
++                             'scheduler_hints': None}
++
++        self.assertTrue(filt_cls.host_passes(host, filter_properties))
++
+     def test_affinity_same_filter_passes(self):
+         filt_cls = self.class_map['SameHostFilter']()
+         host = fakes.FakeHostState('host1', 'compute', {})
+@@ -133,6 +145,18 @@ class HostFiltersTestCase(test.TestCase):
+ 
+         self.assertFalse(filt_cls.host_passes(host, filter_properties))
+ 
++    def test_affinity_same_filter_handles_none(self):
++        filt_cls = self.class_map['SameHostFilter']()
++        host = fakes.FakeHostState('host1', 'compute', {})
++        instance = fakes.FakeInstance(context=self.context,
++                                         params={'host': 'host2'})
++        instance_uuid = instance.uuid
++
++        filter_properties = {'context': self.context.elevated(),
++                             'scheduler_hints': None}
++
++        self.assertTrue(filt_cls.host_passes(host, filter_properties))
++
+     def test_affinity_simple_cidr_filter_passes(self):
+         filt_cls = self.class_map['SimpleCIDRAffinityFilter']()
+         host = fakes.FakeHostState('host1', 'compute', {})
+@@ -163,6 +187,19 @@ class HostFiltersTestCase(test.TestCase):
+ 
+         self.assertFalse(filt_cls.host_passes(host, filter_properties))
+ 
++    def test_affinity_simple_cidr_filter_handles_none(self):
++        filt_cls = self.class_map['SimpleCIDRAffinityFilter']()
++        host = fakes.FakeHostState('host1', 'compute', {})
++
++        affinity_ip = flags.FLAGS.my_ip.split('.')[0:3]
++        affinity_ip.append('100')
++        affinity_ip = str.join('.', affinity_ip)
++
++        filter_properties = {'context': self.context.elevated(),
++                             'scheduler_hints': None}
++
++        self.assertTrue(filt_cls.host_passes(host, filter_properties))
++
+     def test_compute_filter_passes(self):
+         self._stub_service_is_up(True)
+         filt_cls = self.class_map['ComputeFilter']()
diff --git a/0017-Addtional-CommandFilters-to-fix-rootwrap-on-SLES.patch b/0017-Addtional-CommandFilters-to-fix-rootwrap-on-SLES.patch
new file mode 100644
index 0000000..4059b3f
--- /dev/null
+++ b/0017-Addtional-CommandFilters-to-fix-rootwrap-on-SLES.patch
@@ -0,0 +1,94 @@
+From cf6a85a6d4ac982875c1cfab44acdea1e1962930 Mon Sep 17 00:00:00 2001
+From: Ralf Haferkamp <rhafer at suse.de>
+Date: Wed, 20 Jun 2012 11:28:22 +0200
+Subject: [PATCH] Addtional CommandFilters to fix rootwrap on SLES
+
+Fixes bug 1013147 (for SLES)
+
+(cherry picked from commit a519752eef157aaa03c9f6169eba1ff1b5a9f1bd)
+
+Change-Id: Ib362c913b809f7601a9a4faedede89b22794dfb7
+---
+ Authors                  |    1 +
+ nova/rootwrap/compute.py |    7 +++++++
+ nova/rootwrap/network.py |    5 +++++
+ 3 files changed, 13 insertions(+), 0 deletions(-)
+
+diff --git a/Authors b/Authors
+index 2a7a82a..65ba31c 100644
+--- a/Authors
++++ b/Authors
+@@ -157,6 +157,7 @@ Pádraig Brady <pbrady at redhat.com>
+ Paul Voccio <paul at openstack.org>
+ Peng Yong <ppyy at pubyun.com>
+ Philip Knouff <philip.knouff at mailtrust.com>
++Ralf Haferkamp <rhafer at suse.de>
+ Renuka Apte <renuka.apte at citrix.com>
+ Ricardo Carrillo Cruz <emaildericky at gmail.com>
+ Rick Clark <rick at openstack.org>
+diff --git a/nova/rootwrap/compute.py b/nova/rootwrap/compute.py
+index bb53abc..a3d7ec0 100755
+--- a/nova/rootwrap/compute.py
++++ b/nova/rootwrap/compute.py
+@@ -100,6 +100,7 @@ filterlist = [
+     # nova/virt/libvirt/vif.py: 'tunctl', '-b', '-t', dev
+     # nova/network/linux_net.py: 'tunctl', '-b', '-t', dev
+     filters.CommandFilter("/usr/sbin/tunctl", "root"),
++    filters.CommandFilter("/bin/tunctl", "root"),
+ 
+     # nova/virt/libvirt/vif.py: 'ovs-vsctl', ...
+     # nova/virt/libvirt/vif.py: 'ovs-vsctl', 'del-port', ...
+@@ -118,6 +119,7 @@ filterlist = [
+     # nova/virt/xenapi/vm_utils.py: "parted", "--script", ...
+     # nova/virt/xenapi/vm_utils.py: 'parted', '--script', dev_path, ..*.
+     filters.CommandFilter("/sbin/parted", "root"),
++    filters.CommandFilter("/usr/sbin/parted", "root"),
+ 
+     # nova/virt/xenapi/vm_utils.py: fdisk %(dev_path)s
+     filters.CommandFilter("/sbin/fdisk", "root"),
+@@ -130,15 +132,20 @@ filterlist = [
+ 
+     # nova/network/linux_net.py: 'ip[6]tables-save' % (cmd,), '-t', ...
+     filters.CommandFilter("/sbin/iptables-save", "root"),
++    filters.CommandFilter("/usr/sbin/iptables-save", "root"),
+     filters.CommandFilter("/sbin/ip6tables-save", "root"),
++    filters.CommandFilter("/usr/sbin/ip6tables-save", "root"),
+ 
+     # nova/network/linux_net.py: 'ip[6]tables-restore' % (cmd,)
+     filters.CommandFilter("/sbin/iptables-restore", "root"),
++    filters.CommandFilter("/usr/sbin/iptables-restore", "root"),
+     filters.CommandFilter("/sbin/ip6tables-restore", "root"),
++    filters.CommandFilter("/usr/sbin/ip6tables-restore", "root"),
+ 
+     # nova/network/linux_net.py: 'arping', '-U', floating_ip, '-A', '-I', ...
+     # nova/network/linux_net.py: 'arping', '-U', network_ref['dhcp_server'],..
+     filters.CommandFilter("/usr/bin/arping", "root"),
++    filters.CommandFilter("/sbin/arping", "root"),
+ 
+     # nova/network/linux_net.py: 'route', '-n'
+     # nova/network/linux_net.py: 'route', 'del', 'default', 'gw'
+diff --git a/nova/rootwrap/network.py b/nova/rootwrap/network.py
+index 0a93a63..fbac613 100755
+--- a/nova/rootwrap/network.py
++++ b/nova/rootwrap/network.py
+@@ -40,15 +40,20 @@ filterlist = [
+ 
+     # nova/network/linux_net.py: 'ip[6]tables-save' % (cmd,), '-t', ...
+     filters.CommandFilter("/sbin/iptables-save", "root"),
++    filters.CommandFilter("/usr/sbin/iptables-save", "root"),
+     filters.CommandFilter("/sbin/ip6tables-save", "root"),
++    filters.CommandFilter("/usr/sbin/ip6tables-save", "root"),
+ 
+     # nova/network/linux_net.py: 'ip[6]tables-restore' % (cmd,)
+     filters.CommandFilter("/sbin/iptables-restore", "root"),
++    filters.CommandFilter("/usr/sbin/iptables-restore", "root"),
+     filters.CommandFilter("/sbin/ip6tables-restore", "root"),
++    filters.CommandFilter("/usr/sbin/ip6tables-restore", "root"),
+ 
+     # nova/network/linux_net.py: 'arping', '-U', floating_ip, '-A', '-I', ...
+     # nova/network/linux_net.py: 'arping', '-U', network_ref['dhcp_server'],..
+     filters.CommandFilter("/usr/bin/arping", "root"),
++    filters.CommandFilter("/sbin/arping", "root"),
+ 
+     # nova/network/linux_net.py: 'route', '-n'
+     # nova/network/linux_net.py: 'route', 'del', 'default', 'gw'
diff --git a/0018-Fix-marker-behavior-for-flavors.patch b/0018-Fix-marker-behavior-for-flavors.patch
new file mode 100644
index 0000000..3257755
--- /dev/null
+++ b/0018-Fix-marker-behavior-for-flavors.patch
@@ -0,0 +1,108 @@
+From d3a87a247e1c4a9dc9aa7b432d23b9c3c27d469a Mon Sep 17 00:00:00 2001
+From: Phlip Knouff <philip.knouff at mailtrust.com>
+Date: Mon, 26 Mar 2012 22:16:27 +0000
+Subject: [PATCH] Fix marker behavior for flavors
+
+Fixes Bug #956096
+
+(cherry-picked from commit 497502cbf833d063c964975448dfacd0e1db2ef4)
+
+Change-Id: I700770b17d0a38f120fce002167c8b6a8bbecbb2
+---
+ nova/api/openstack/common.py                     |    6 ++++-
+ nova/api/openstack/compute/flavors.py            |   13 ++++++----
+ nova/tests/api/openstack/compute/test_flavors.py |   28 ++++++++++++++++++++++
+ 3 files changed, 41 insertions(+), 6 deletions(-)
+
+diff --git a/nova/api/openstack/common.py b/nova/api/openstack/common.py
+index 38f3821..8e3daaa 100644
+--- a/nova/api/openstack/common.py
++++ b/nova/api/openstack/common.py
+@@ -192,7 +192,11 @@ def limited_by_marker(items, request, max_limit=FLAGS.osapi_max_limit):
+     if marker:
+         start_index = -1
+         for i, item in enumerate(items):
+-            if item['id'] == marker or item.get('uuid') == marker:
++            if 'flavorid' in item:
++                if item['flavorid'] == marker:
++                    start_index = i + 1
++                    break
++            elif item['id'] == marker or item.get('uuid') == marker:
+                 start_index = i + 1
+                 break
+         if start_index < 0:
+diff --git a/nova/api/openstack/compute/flavors.py b/nova/api/openstack/compute/flavors.py
+index 99f6f44..8c159c5 100644
+--- a/nova/api/openstack/compute/flavors.py
++++ b/nova/api/openstack/compute/flavors.py
+@@ -73,15 +73,13 @@ class Controller(wsgi.Controller):
+     def index(self, req):
+         """Return all flavors in brief."""
+         flavors = self._get_flavors(req)
+-        limited_flavors = common.limited_by_marker(flavors.values(), req)
+-        return self._view_builder.index(req, limited_flavors)
++        return self._view_builder.index(req, flavors)
+ 
+     @wsgi.serializers(xml=FlavorsTemplate)
+     def detail(self, req):
+         """Return all flavors in detail."""
+         flavors = self._get_flavors(req)
+-        limited_flavors = common.limited_by_marker(flavors.values(), req)
+-        return self._view_builder.detail(req, limited_flavors)
++        return self._view_builder.detail(req, flavors)
+ 
+     @wsgi.serializers(xml=FlavorTemplate)
+     def show(self, req, id):
+@@ -108,7 +106,12 @@ class Controller(wsgi.Controller):
+             except ValueError:
+                 pass  # ignore bogus values per spec
+ 
+-        return instance_types.get_all_types(filters=filters)
++        flavors = instance_types.get_all_types(filters=filters)
++        flavors_list = flavors.values()
++        sorted_flavors = sorted(flavors_list,
++                                key=lambda item: item['flavorid'])
++        limited_flavors = common.limited_by_marker(sorted_flavors, req)
++        return limited_flavors
+ 
+ 
+ def create_resource():
+diff --git a/nova/tests/api/openstack/compute/test_flavors.py b/nova/tests/api/openstack/compute/test_flavors.py
+index 7d03a62..599e86b 100644
+--- a/nova/tests/api/openstack/compute/test_flavors.py
++++ b/nova/tests/api/openstack/compute/test_flavors.py
+@@ -195,6 +195,34 @@ class FlavorsTest(test.TestCase):
+         }
+         self.assertEqual(flavor, expected)
+ 
++    def test_get_flavor_list_with_marker(self):
++        self.maxDiff = None
++        req = fakes.HTTPRequest.blank('/v2/fake/flavors?limit=1&marker=1')
++        flavor = self.controller.index(req)
++        expected = {
++            "flavors": [
++                {
++                    "id": "2",
++                    "name": "flavor 2",
++                    "links": [
++                        {
++                            "rel": "self",
++                            "href": "http://localhost/v2/fake/flavors/2",
++                        },
++                        {
++                            "rel": "bookmark",
++                            "href": "http://localhost/fake/flavors/2",
++                        },
++                    ],
++                },
++            ],
++            'flavors_links': [
++                {'href': 'http://localhost/v2/fake/flavors?limit=1&marker=2',
++               'rel': 'next'}
++            ]
++        }
++        self.assertDictMatch(flavor, expected)
++
+     def test_get_flavor_detail_with_limit(self):
+         req = fakes.HTTPRequest.blank('/v2/fake/flavors/detail?limit=1')
+         response = self.controller.index(req)
diff --git a/0013-Use-default-qemu-img-cluster-size-in-libvirt-connect.patch b/0019-Use-default-qemu-img-cluster-size-in-libvirt-connect.patch
similarity index 100%
rename from 0013-Use-default-qemu-img-cluster-size-in-libvirt-connect.patch
rename to 0019-Use-default-qemu-img-cluster-size-in-libvirt-connect.patch
diff --git a/0014-Return-413-status-on-over-quota-in-the-native-API.patch b/0020-Return-413-status-on-over-quota-in-the-native-API.patch
similarity index 100%
rename from 0014-Return-413-status-on-over-quota-in-the-native-API.patch
rename to 0020-Return-413-status-on-over-quota-in-the-native-API.patch
diff --git a/0021-Handle-local-remote-exceptions-consistently.patch b/0021-Handle-local-remote-exceptions-consistently.patch
new file mode 100644
index 0000000..9488b6f
--- /dev/null
+++ b/0021-Handle-local-remote-exceptions-consistently.patch
@@ -0,0 +1,147 @@
+From 4b89b4fd3665a6eaaa63911102070fd93f20f8bc Mon Sep 17 00:00:00 2001
+From: Eoghan Glynn <eglynn at redhat.com>
+Date: Tue, 10 Jul 2012 12:11:28 +0100
+Subject: [PATCH] Handle local & remote exceptions consistently.
+
+Related to LP 1021373.
+
+When the floating_ips quota threshold is exceeded, this occurs remotely
+in the networking service and hence is reported back to the API service
+over RPC, via a RemoteError wrapping the original QuotaError exception.
+
+Previously the handling of such RemoteErrors in the native API was
+inconsistent with exceptions raised locally within the API service.
+
+Now in both cases, we expose the exception explantion, status etc. in the
+response, if the exception type is declared as safe.
+
+This fix is not required on master, as the Folsom RPC failure deserialization
+logic renders it unnecessary.
+
+Change-Id: Icf7dcafd1f942f5d81d12587775d6ade4a176932
+---
+ nova/api/openstack/__init__.py               |   38 ++++++++++++++++++++-----
+ nova/tests/api/openstack/compute/test_api.py |   25 ++++++++++++++---
+ 2 files changed, 51 insertions(+), 12 deletions(-)
+
+diff --git a/nova/api/openstack/__init__.py b/nova/api/openstack/__init__.py
+index 00b3f3e..b771afa 100644
+--- a/nova/api/openstack/__init__.py
++++ b/nova/api/openstack/__init__.py
+@@ -25,6 +25,7 @@ import webob.dec
+ import webob.exc
+ 
+ from nova.api.openstack import wsgi
++from nova.rpc import common as rpc_common
+ from nova import exception
+ from nova import log as logging
+ from nova import utils
+@@ -47,8 +48,18 @@ class FaultWrapper(base_wsgi.Middleware):
+         return FaultWrapper._status_to_type.get(
+                                   status, webob.exc.HTTPInternalServerError)()
+ 
+-    def _error(self, inner, req, headers=None, status=500, safe=False):
+-        LOG.exception(_("Caught error: %s"), unicode(inner))
++    _name_to_type = {}
++
++    @staticmethod
++    def name_to_type(name):
++        if not FaultWrapper._name_to_type:
++            for clazz in utils.walk_class_hierarchy(exception.NovaException):
++                FaultWrapper._name_to_type[clazz.__name__] = clazz
++        return FaultWrapper._name_to_type.get(name)
++
++    def _error(self, req, class_name, explanation,
++               headers=None, status=500, safe=False):
++        LOG.exception(_("Caught error: %s"), explanation)
+         msg_dict = dict(url=req.url, status=status)
+         LOG.info(_("%(url)s returned with HTTP %(status)d") % msg_dict)
+         outer = self.status_to_type(status)
+@@ -62,18 +73,29 @@ class FaultWrapper(base_wsgi.Middleware):
+         # inconsistent with the EC2 API to hide every exception,
+         # including those that are safe to expose, see bug 1021373
+         if safe:
+-            outer.explanation = '%s: %s' % (inner.__class__.__name__,
+-                                            unicode(inner))
++            outer.explanation = '%s: %s' % (class_name, explanation)
+         return wsgi.Fault(outer)
+ 
+     @webob.dec.wsgify(RequestClass=wsgi.Request)
+     def __call__(self, req):
+         try:
+             return req.get_response(self.application)
+-        except exception.NovaException as ex:
+-            return self._error(ex, req, ex.headers, ex.code, ex.safe)
+-        except Exception as ex:
+-            return self._error(ex, req)
++        except rpc_common.RemoteError as e:
++            remote_exception_type = self.name_to_type(e.exc_type)
++            if remote_exception_type:
++                headers = remote_exception_type.headers
++                code = remote_exception_type.code
++                safe = remote_exception_type.safe
++            else:
++                headers = {}
++                code = 500
++                safe = False
++            return self._error(req, e.exc_type, e.value, headers, code, safe)
++        except exception.NovaException as e:
++            return self._error(req, e.__class__.__name__, unicode(e),
++                               e.headers, e.code, e.safe)
++        except Exception as e:
++            return self._error(req, e.__class__.__name__, unicode(e))
+ 
+ 
+ class APIMapper(routes.Mapper):
+diff --git a/nova/tests/api/openstack/compute/test_api.py b/nova/tests/api/openstack/compute/test_api.py
+index a9e186a..e8932f2 100644
+--- a/nova/tests/api/openstack/compute/test_api.py
++++ b/nova/tests/api/openstack/compute/test_api.py
+@@ -27,6 +27,7 @@ from nova import exception
+ from nova import test
+ from nova.api import openstack as openstack_api
+ from nova.api.openstack import wsgi
++from nova.rpc import common as rpc_common
+ from nova.tests.api.openstack import fakes
+ 
+ 
+@@ -145,10 +146,10 @@ class APITest(test.TestCase):
+     def test_unsafe_exceptions_are_not_described_in_faults(self):
+         self._do_test_exception_safety_reflected_in_faults(False)
+ 
+-    def _do_test_exception_mapping(self, exception_type):
++    def _do_test_exception_mapping(self, exception_value, exception_type):
+         @webob.dec.wsgify
+         def fail(req):
+-            raise exception_type('too many used')
++            raise exception_value
+ 
+         api = self._wsgi_app(fail)
+         resp = webob.Request.blank('/').get_response(api)
+@@ -158,8 +159,24 @@ class APITest(test.TestCase):
+             self.assertTrue(key in resp.headers)
+             self.assertEquals(resp.headers[key], value)
+ 
+-    def test_quota_error_mapping(self):
+-        self._do_test_exception_mapping(exception.QuotaError)
++    def test_local_quota_error_mapping(self):
++        exception_value = exception.QuotaError('too many used')
++        self._do_test_exception_mapping(exception_value, exception.QuotaError)
++
++    def test_remote_quota_error_mapping(self):
++        exception_value = rpc_common.RemoteError('QuotaError',
++                                                 'too many used')
++        self._do_test_exception_mapping(exception_value, exception.QuotaError)
++
++    def test_remote_unknown_error_mapping(self):
++        @webob.dec.wsgify
++        def fail(req):
++            raise rpc_common.RemoteError('UnknownError', 'whatevs')
++
++        api = self._wsgi_app(fail)
++        resp = webob.Request.blank('/').get_response(api)
++        self.assertFalse('whatevs' in resp.body, resp.body)
++        self.assertEqual(resp.status_int, 500, resp.body)
+ 
+     def test_request_id_in_response(self):
+         req = webob.Request.blank('/')
diff --git a/0022-libvirt-fix-qcow2-size-on-live-block-migration.patch b/0022-libvirt-fix-qcow2-size-on-live-block-migration.patch
new file mode 100644
index 0000000..68ed979
--- /dev/null
+++ b/0022-libvirt-fix-qcow2-size-on-live-block-migration.patch
@@ -0,0 +1,30 @@
+From f6d1f552875a918084907c53085d140d58fb1c37 Mon Sep 17 00:00:00 2001
+From: Yaguang Tang <heut2008 at gmail.com>
+Date: Wed, 9 May 2012 17:45:58 +0800
+Subject: [PATCH] libvirt: fix qcow2 size on live block migration
+
+When using live block migration, ephemeral disks with qcow2 format
+should be created in the destination with the same virtual size as
+before.
+
+bug 977007
+
+Change-Id: I5c5b1295bdb3e4dc281698eba38c5ce697aa9bc2
+(cherry picked from commit ee705d048418d63667136cad3951655178861d46)
+---
+ nova/virt/libvirt/connection.py |    2 +-
+ 1 files changed, 1 insertions(+), 1 deletions(-)
+
+diff --git a/nova/virt/libvirt/connection.py b/nova/virt/libvirt/connection.py
+index da44ac4..ed94f15 100644
+--- a/nova/virt/libvirt/connection.py
++++ b/nova/virt/libvirt/connection.py
+@@ -2160,7 +2160,7 @@ class LibvirtConnection(driver.ComputeDriver):
+                     image_id=instance_ref['image_ref'],
+                     user_id=instance_ref['user_id'],
+                     project_id=instance_ref['project_id'],
+-                    size=info['disk_size'])
++                    size=info['virt_disk_size'])
+ 
+         # if image has kernel and ramdisk, just download
+         # following normal way.
diff --git a/0023-Backport-fix-for-API-listing-of-os-hosts.patch b/0023-Backport-fix-for-API-listing-of-os-hosts.patch
new file mode 100644
index 0000000..dc8c921
--- /dev/null
+++ b/0023-Backport-fix-for-API-listing-of-os-hosts.patch
@@ -0,0 +1,73 @@
+From 08e5128ffd63acd14249db3930f05753abb8f848 Mon Sep 17 00:00:00 2001
+From: Adam Gandelman <adamg at canonical.com>
+Date: Mon, 23 Jul 2012 13:16:46 -0700
+Subject: [PATCH] Backport fix for API listing of os-hosts.
+
+Backports fix for bug 1014925 to stable/essex, which resolves issue
+where querying /v1.1/$tenant/os-hosts returns an empty list.
+
+Original fix by Joe Gordon reviewed into Folsom at:
+
+    https://review.openstack.org/#/c/8682/2
+
+Change-Id: I44ac2e519b7af9b8f3b37a42280ac6fe71c31a1c
+---
+ nova/api/openstack/compute/contrib/hosts.py        |    6 ++++--
+ .../api/openstack/compute/contrib/test_hosts.py    |   11 ++++++++---
+ 2 files changed, 12 insertions(+), 5 deletions(-)
+
+diff --git a/nova/api/openstack/compute/contrib/hosts.py b/nova/api/openstack/compute/contrib/hosts.py
+index a93da9e..202c8ca 100644
+--- a/nova/api/openstack/compute/contrib/hosts.py
++++ b/nova/api/openstack/compute/contrib/hosts.py
+@@ -27,7 +27,6 @@ from nova import db
+ from nova import exception
+ from nova import flags
+ from nova import log as logging
+-from nova.scheduler import api as scheduler_api
+ 
+ 
+ LOG = logging.getLogger(__name__)
+@@ -98,7 +97,10 @@ def _list_hosts(req, service=None):
+     by service type.
+     """
+     context = req.environ['nova.context']
+-    hosts = scheduler_api.get_host_list(context)
++    services = db.service_get_all(context, False)
++    hosts = []
++    for host in services:
++        hosts.append({"host_name": host['host'], 'service': host['topic']})
+     if service:
+         hosts = [host for host in hosts
+                 if host["service"] == service]
+diff --git a/nova/tests/api/openstack/compute/contrib/test_hosts.py b/nova/tests/api/openstack/compute/contrib/test_hosts.py
+index 77beeae..0482eb5 100644
+--- a/nova/tests/api/openstack/compute/contrib/test_hosts.py
++++ b/nova/tests/api/openstack/compute/contrib/test_hosts.py
+@@ -36,10 +36,15 @@ HOST_LIST = [
+         {"host_name": "host_c2", "service": "compute"},
+         {"host_name": "host_v1", "service": "volume"},
+         {"host_name": "host_v2", "service": "volume"}]
++SERVICES_LIST = [
++        {"host": "host_c1", "topic": "compute"},
++        {"host": "host_c2", "topic": "compute"},
++        {"host": "host_v1", "topic": "volume"},
++        {"host": "host_v2", "topic": "volume"}]
+ 
+ 
+-def stub_get_host_list(req):
+-    return HOST_LIST
++def stub_service_get_all(self, req):
++    return SERVICES_LIST
+ 
+ 
+ def stub_set_host_enabled(context, host, enabled):
+@@ -104,7 +109,7 @@ class HostTestCase(test.TestCase):
+         super(HostTestCase, self).setUp()
+         self.controller = os_hosts.HostController()
+         self.req = FakeRequest()
+-        self.stubs.Set(scheduler_api, 'get_host_list', stub_get_host_list)
++        self.stubs.Set(db, 'service_get_all', stub_service_get_all)
+         self.stubs.Set(self.controller.api, 'set_host_enabled',
+                        stub_set_host_enabled)
+         self.stubs.Set(self.controller.api, 'set_host_maintenance',
diff --git a/0024-Avoid-lazy-loading-errors-on-instance_type.patch b/0024-Avoid-lazy-loading-errors-on-instance_type.patch
new file mode 100644
index 0000000..d3e5b0a
--- /dev/null
+++ b/0024-Avoid-lazy-loading-errors-on-instance_type.patch
@@ -0,0 +1,40 @@
+From 4d74631659b1b6e5b29b763cd808528946cb3721 Mon Sep 17 00:00:00 2001
+From: Vishvananda Ishaya <vishvananda at gmail.com>
+Date: Tue, 3 Jul 2012 14:50:11 -0700
+Subject: [PATCH] Avoid lazy-loading errors on instance_type
+
+When instances are launched with a source group, the instance_type
+is not lazy_loaded in properly.
+
+The issue is intermittent because if another query has already loaded
+the instance with a joined instance_type or the instance has not
+yet been expunged from the session, then the load succeeds.
+
+Therefore this failure only appears under heavy load. Adding an
+explicit joindload fixes the issue.
+
+fixes bug 1018721
+
+Change-Id: I450c598c31c416c7be341cbb8cd14e33c6bb2aec
+(cherry picked from commit 2ef0dcfac78468551aac8492269ad856c312dcb5)
+---
+ nova/db/sqlalchemy/api.py |    6 +++---
+ 1 files changed, 3 insertions(+), 3 deletions(-)
+
+diff --git a/nova/db/sqlalchemy/api.py b/nova/db/sqlalchemy/api.py
+index 03ac987..ca07565 100644
+--- a/nova/db/sqlalchemy/api.py
++++ b/nova/db/sqlalchemy/api.py
+@@ -2858,9 +2858,9 @@ def security_group_rule_get(context, security_group_rule_id, session=None):
+ def security_group_rule_get_by_security_group(context, security_group_id,
+                                               session=None):
+     return _security_group_rule_get_query(context, session=session).\
+-                         filter_by(parent_group_id=security_group_id).\
+-                         options(joinedload_all('grantee_group.instances')).\
+-                         all()
++            filter_by(parent_group_id=security_group_id).\
++            options(joinedload_all('grantee_group.instances.instance_type')).\
++            all()
+ 
+ 
+ @require_context
diff --git a/0025-Avoid-casts-in-network-manager-to-prevent-races.patch b/0025-Avoid-casts-in-network-manager-to-prevent-races.patch
new file mode 100644
index 0000000..1a7fa27
--- /dev/null
+++ b/0025-Avoid-casts-in-network-manager-to-prevent-races.patch
@@ -0,0 +1,82 @@
+From 80d302670f8db37b297ea0618cc14851aab6fff5 Mon Sep 17 00:00:00 2001
+From: Vishvananda Ishaya <vishvananda at gmail.com>
+Date: Tue, 26 Jun 2012 17:56:21 -0700
+Subject: [PATCH] Avoid casts in network manager to prevent races
+
+ * Fixes bug 1017418
+ * Includes a change to turn the floating ip casts
+   into calls which is part of commit
+   82599c77346bbefd550ea4ee6c0b13a3df4950af
+ * These calls are to prevent race conditions that
+   were preventing floating ips from being deallocated
+   properly
+
+Change-Id: I3251f02fc5fcb8305f12b6b8a9644232b9146db2
+(cherry picked from commit c689891226baa8877f6fb7b3c468b06972068847)
+---
+ nova/network/manager.py            |    8 ++++----
+ nova/tests/network/test_manager.py |    4 ++--
+ 2 files changed, 6 insertions(+), 6 deletions(-)
+
+diff --git a/nova/network/manager.py b/nova/network/manager.py
+index 73ac52b..2354879 100644
+--- a/nova/network/manager.py
++++ b/nova/network/manager.py
+@@ -225,7 +225,7 @@ class RPCAllocateFixedIP(object):
+ 
+     def deallocate_fixed_ip(self, context, address, host, **kwargs):
+         """Call the superclass deallocate_fixed_ip if i'm the correct host
+-        otherwise cast to the correct host"""
++        otherwise call to the correct host"""
+         fixed_ip = self.db.fixed_ip_get_by_address(context, address)
+         network = self._get_network_by_id(context, fixed_ip['network_id'])
+ 
+@@ -238,7 +238,7 @@ class RPCAllocateFixedIP(object):
+             topic = self.db.queue_get_for(context, FLAGS.network_topic, host)
+             args = {'address': address,
+                     'host': host}
+-            rpc.cast(context, topic,
++            rpc.call(context, topic,
+                      {'method': 'deallocate_fixed_ip',
+                       'args': args})
+         else:
+@@ -469,7 +469,7 @@ class FloatingIP(object):
+                                         fixed_address, interface)
+         else:
+             # send to correct host
+-            rpc.cast(context,
++            rpc.call(context,
+                      self.db.queue_get_for(context, FLAGS.network_topic, host),
+                      {'method': '_associate_floating_ip',
+                       'args': {'floating_address': floating_address,
+@@ -534,7 +534,7 @@ class FloatingIP(object):
+             self._disassociate_floating_ip(context, address, interface)
+         else:
+             # send to correct host
+-            rpc.cast(context,
++            rpc.call(context,
+                      self.db.queue_get_for(context, FLAGS.network_topic, host),
+                      {'method': '_disassociate_floating_ip',
+                       'args': {'address': address,
+diff --git a/nova/tests/network/test_manager.py b/nova/tests/network/test_manager.py
+index 3b33296..a4b6c30 100644
+--- a/nova/tests/network/test_manager.py
++++ b/nova/tests/network/test_manager.py
+@@ -679,7 +679,7 @@ class VlanNetworkTestCase(test.TestCase):
+         self.local = True
+         self.stubs.Set(self.network.db, 'fixed_ip_get_by_address', fake4)
+         self.stubs.Set(self.network.db, 'network_get', fake4_network)
+-        self.stubs.Set(rpc, 'cast', fake6)
++        self.stubs.Set(rpc, 'call', fake6)
+         self.network.associate_floating_ip(ctxt, mox.IgnoreArg(),
+                                                  mox.IgnoreArg())
+         self.assertFalse(self.local)
+@@ -783,7 +783,7 @@ class VlanNetworkTestCase(test.TestCase):
+         self.local = True
+         self.stubs.Set(self.network.db, 'fixed_ip_get', fake4)
+         self.stubs.Set(self.network.db, 'network_get', fake4_network)
+-        self.stubs.Set(rpc, 'cast', fake6)
++        self.stubs.Set(rpc, 'call', fake6)
+         self.network.disassociate_floating_ip(ctxt, mox.IgnoreArg())
+         self.assertFalse(self.local)
+ 
diff --git a/0026-Conditionally-allow-queries-for-deleted-flavours.patch b/0026-Conditionally-allow-queries-for-deleted-flavours.patch
new file mode 100644
index 0000000..42ac955
--- /dev/null
+++ b/0026-Conditionally-allow-queries-for-deleted-flavours.patch
@@ -0,0 +1,141 @@
+From 4c7d671d21816f656068380e3b7a1415d98ba69c Mon Sep 17 00:00:00 2001
+From: Soren Hansen <sorhanse at cisco.com>
+Date: Wed, 23 May 2012 13:36:37 -0500
+Subject: [PATCH] Conditionally allow queries for deleted flavours
+
+Fixes bug #994935
+
+This is four commits from upstream squashed into one:
+
+   31506c0 Permit deleted instance types to be queried for active
+           instances. (By Josh Kearney)
+   f6e62c6 API users should not see deleted flavors. (By Dan Prince)
+   16d26af Revert "API users should not see deleted flavors." (By Josh
+           Kearney)
+   5157401 Do not always query deleted instance_types. (By Brian Lamar)
+
+It may seem strange to include both the change and the reversion of the
+change, but a) this is the most accurate way to reflect the history of
+the changes and b) the reversion actually includes new tests.
+
+Change-Id: Id231e9518ac176e29cc6241fff81705910dc9e9e
+---
+ nova/api/openstack/compute/servers.py |    2 +-
+ nova/compute/instance_types.py        |    4 +-
+ nova/db/sqlalchemy/models.py          |    3 +-
+ nova/tests/test_instance_types.py     |   51 ++++++++++++++++++++++++++++++++-
+ 4 files changed, 54 insertions(+), 6 deletions(-)
+
+diff --git a/nova/api/openstack/compute/servers.py b/nova/api/openstack/compute/servers.py
+index 8ca49b6..f23a2a3 100644
+--- a/nova/api/openstack/compute/servers.py
++++ b/nova/api/openstack/compute/servers.py
+@@ -704,7 +704,7 @@ class Controller(wsgi.Controller):
+ 
+         try:
+             _get_inst_type = instance_types.get_instance_type_by_flavor_id
+-            inst_type = _get_inst_type(flavor_id)
++            inst_type = _get_inst_type(flavor_id, read_deleted="no")
+ 
+             (instances, resv_id) = self.compute_api.create(context,
+                             inst_type,
+diff --git a/nova/compute/instance_types.py b/nova/compute/instance_types.py
+index 2bc470a..aa42dd7 100644
+--- a/nova/compute/instance_types.py
++++ b/nova/compute/instance_types.py
+@@ -129,10 +129,10 @@ def get_instance_type_by_name(name):
+ 
+ # TODO(termie): flavor-specific code should probably be in the API that uses
+ #               flavors.
+-def get_instance_type_by_flavor_id(flavorid):
++def get_instance_type_by_flavor_id(flavorid, read_deleted="yes"):
+     """Retrieve instance type by flavorid.
+ 
+     :raises: FlavorNotFound
+     """
+-    ctxt = context.get_admin_context()
++    ctxt = context.get_admin_context(read_deleted=read_deleted)
+     return db.instance_type_get_by_flavor_id(ctxt, flavorid)
+diff --git a/nova/db/sqlalchemy/models.py b/nova/db/sqlalchemy/models.py
+index ec5e663..101ca84 100644
+--- a/nova/db/sqlalchemy/models.py
++++ b/nova/db/sqlalchemy/models.py
+@@ -328,8 +328,7 @@ class InstanceTypes(BASE, NovaBase):
+                            foreign_keys=id,
+                            primaryjoin='and_('
+                                'Instance.instance_type_id == '
+-                               'InstanceTypes.id, '
+-                               'InstanceTypes.deleted == False)')
++                               'InstanceTypes.id)')
+ 
+ 
+ class Volume(BASE, NovaBase):
+diff --git a/nova/tests/test_instance_types.py b/nova/tests/test_instance_types.py
+index 9057f18..68519a2 100644
+--- a/nova/tests/test_instance_types.py
++++ b/nova/tests/test_instance_types.py
+@@ -145,7 +145,7 @@ class InstanceTypeTestCase(test.TestCase):
+                           'name two', 256, 1, 120, 200, flavorid)
+ 
+     def test_will_not_destroy_with_no_name(self):
+-        """Ensure destroy sad path of no name raises error"""
++        """Ensure destroy said path of no name raises error"""
+         self.assertRaises(exception.InstanceTypeNotFoundByName,
+                           instance_types.destroy, None)
+ 
+@@ -194,6 +194,55 @@ class InstanceTypeTestCase(test.TestCase):
+         fetched = instance_types.get_instance_type_by_flavor_id(flavorid)
+         self.assertEqual(default_instance_type, fetched)
+ 
++    def test_can_read_deleted_types_using_flavor_id(self):
++        """Ensure deleted instance types can be read when querying flavor_id"""
++        inst_type_name = "test"
++        inst_type_flavor_id = "test1"
++
++        inst_type = instance_types.create(inst_type_name, 256, 1, 120, 100,
++                inst_type_flavor_id)
++        self.assertEqual(inst_type_name, inst_type["name"])
++
++        # NOTE(jk0): The deleted flavor will show up here because the context
++        # in get_instance_type_by_flavor_id() is set to use read_deleted by
++        # default.
++        instance_types.destroy(inst_type["name"])
++        deleted_inst_type = instance_types.get_instance_type_by_flavor_id(
++                inst_type_flavor_id)
++        self.assertEqual(inst_type_name, deleted_inst_type["name"])
++
++    def test_read_deleted_false_converting_flavorid(self):
++        """
++        Ensure deleted instance types are not returned when not needed (for
++        example when creating a server and attempting to translate from
++        flavorid to instance_type_id.
++        """
++        instance_types.create("instance_type1", 256, 1, 120, 100, "test1")
++        instance_types.destroy("instance_type1")
++        instance_types.create("instance_type1_redo", 256, 1, 120, 100, "test1")
++
++        instance_type = instance_types.get_instance_type_by_flavor_id(
++                "test1", read_deleted="no")
++        self.assertEqual("instance_type1_redo", instance_type["name"])
++
++    def test_will_list_deleted_type_for_active_instance(self):
++        """Ensure deleted instance types with active instances can be read"""
++        ctxt = context.get_admin_context()
++        inst_type = instance_types.create("test", 256, 1, 120, 100, "test1")
++
++        instance_params = {"instance_type_id": inst_type["id"]}
++        instance = db.instance_create(ctxt, instance_params)
++
++        # NOTE(jk0): Delete the instance type and reload the instance from the
++        # DB. The instance_type object will still be available to the active
++        # instance, otherwise being None.
++        instance_types.destroy(inst_type["name"])
++        instance = db.instance_get_by_uuid(ctxt, instance["uuid"])
++
++        self.assertRaises(exception.InstanceTypeNotFound,
++                instance_types.get_instance_type, inst_type["name"])
++        self.assertTrue(instance["instance_type"])
++
+ 
+ class InstanceTypeFilteringTest(test.TestCase):
+     """Test cases for the filter option available for instance_type_get_all"""
diff --git a/0027-Fix-wrong-regex-in-cleanup_file_locks.patch b/0027-Fix-wrong-regex-in-cleanup_file_locks.patch
new file mode 100644
index 0000000..4f0181f
--- /dev/null
+++ b/0027-Fix-wrong-regex-in-cleanup_file_locks.patch
@@ -0,0 +1,58 @@
+From f2bc403879234aaaeeb61e1dca1affe18192cfa1 Mon Sep 17 00:00:00 2001
+From: Eugene Kirpichov <ekirpichov at gmail.com>
+Date: Sat, 21 Jul 2012 23:17:55 +0000
+Subject: [PATCH] Fix wrong regex in cleanup_file_locks.
+
+The sentinel filename actually has form hostname-threadid.pid,
+not hostname.threadid-pid.
+
+Launchpad bug 1018586.
+
+Update: Add Eugene to Authors for stable/essex.
+
+Change-Id: I09c01e0e63ee704b1485c196dc0b396ee03b2e5c
+(cherry picked from commit 974417b75f5f839ce4daaf080147ad154d727f10)
+---
+ Authors                  |    1 +
+ nova/tests/test_utils.py |    2 +-
+ nova/utils.py            |    2 +-
+ 3 files changed, 3 insertions(+), 2 deletions(-)
+
+diff --git a/Authors b/Authors
+index 591c449..a903742 100644
+--- a/Authors
++++ b/Authors
+@@ -62,6 +62,7 @@ Eldar Nugaev <reldan at oscloud.ru>
+ Eoghan Glynn <eglynn at redhat.com>
+ Eric Day <eday at oddments.org>
+ Eric Windisch <eric at cloudscaling.com>
++Eugene Kirpichov <ekirpichov at gmail.com>
+ Evan Callicoat <diopter at gmail.com>
+ Ewan Mellor <ewan.mellor at citrix.com>
+ François Charlier <francois.charlier at enovance.com>
+diff --git a/nova/tests/test_utils.py b/nova/tests/test_utils.py
+index 501ff91..5babf4c 100644
+--- a/nova/tests/test_utils.py
++++ b/nova/tests/test_utils.py
+@@ -908,7 +908,7 @@ class TestLockCleanup(test.TestCase):
+ 
+     def _get_sentinel_name(self, hostname, pid, thread='MainThread'):
+         return os.path.join(FLAGS.lock_path,
+-                            '%s.%s-%d' % (hostname, thread, pid))
++                            '%s-%s.%d' % (hostname, thread, pid))
+ 
+     def _create_sentinel(self, hostname, pid, thread='MainThread'):
+         name = self._get_sentinel_name(hostname, pid, thread)
+diff --git a/nova/utils.py b/nova/utils.py
+index de2da9f..01a52b5 100644
+--- a/nova/utils.py
++++ b/nova/utils.py
+@@ -986,7 +986,7 @@ def cleanup_file_locks():
+         return
+ 
+     hostname = socket.gethostname()
+-    sentinel_re = hostname + r'\..*-(\d+$)'
++    sentinel_re = hostname + r'-.*\.(\d+$)'
+     lockfile_re = r'nova-.*\.lock'
+     files = os.listdir(FLAGS.lock_path)
+ 
diff --git a/0015-ensure-atomic-manipulation-of-libvirt-disk-images.patch b/0028-ensure-atomic-manipulation-of-libvirt-disk-images.patch
similarity index 98%
rename from 0015-ensure-atomic-manipulation-of-libvirt-disk-images.patch
rename to 0028-ensure-atomic-manipulation-of-libvirt-disk-images.patch
index e2e9a3a..5ca8d3e 100644
--- a/0015-ensure-atomic-manipulation-of-libvirt-disk-images.patch
+++ b/0028-ensure-atomic-manipulation-of-libvirt-disk-images.patch
@@ -1,4 +1,4 @@
-From 8d21a20cb7ca568afaa5b9a759d7e61fb87bb786 Mon Sep 17 00:00:00 2001
+From 614d618011a2278fa5ab2a5f63637eb3f5564909 Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Fri, 16 Mar 2012 03:43:49 +0000
 Subject: [PATCH] ensure atomic manipulation of libvirt disk images
@@ -25,7 +25,7 @@ Change-Id: I81a5407665a6998128c0dee41387ef00ebddeb4d
  3 files changed, 57 insertions(+), 49 deletions(-)
 
 diff --git a/nova/utils.py b/nova/utils.py
-index de2da9f..a2242e6 100644
+index 01a52b5..0e5855a 100644
 --- a/nova/utils.py
 +++ b/nova/utils.py
 @@ -21,6 +21,7 @@
@@ -169,7 +169,7 @@ index 1e0ae0a..626f3ff 100644
  
      return metadata
 diff --git a/nova/virt/libvirt/connection.py b/nova/virt/libvirt/connection.py
-index da44ac4..2dfe2a3 100644
+index ed94f15..5bc9ce0 100644
 --- a/nova/virt/libvirt/connection.py
 +++ b/nova/virt/libvirt/connection.py
 @@ -1112,7 +1112,8 @@ class LibvirtConnection(driver.ComputeDriver):
diff --git a/0016-Ensure-we-don-t-access-the-net-when-building-docs.patch b/0029-Ensure-we-don-t-access-the-net-when-building-docs.patch
similarity index 94%
rename from 0016-Ensure-we-don-t-access-the-net-when-building-docs.patch
rename to 0029-Ensure-we-don-t-access-the-net-when-building-docs.patch
index f2b7af0..8e390a6 100644
--- a/0016-Ensure-we-don-t-access-the-net-when-building-docs.patch
+++ b/0029-Ensure-we-don-t-access-the-net-when-building-docs.patch
@@ -1,4 +1,4 @@
-From 8b0adec9ccc6c1117ea93ae7dad21b9780a3348f Mon Sep 17 00:00:00 2001
+From abf094c3941357446d1b9188c24c5bb3f1d005ac Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Fri, 6 Jan 2012 12:16:34 +0000
 Subject: [PATCH] Ensure we don't access the net when building docs
diff --git a/0017-fix-useexisting-deprecation-warnings.patch b/0030-fix-useexisting-deprecation-warnings.patch
similarity index 97%
rename from 0017-fix-useexisting-deprecation-warnings.patch
rename to 0030-fix-useexisting-deprecation-warnings.patch
index 9bd96c9..bcc91f6 100644
--- a/0017-fix-useexisting-deprecation-warnings.patch
+++ b/0030-fix-useexisting-deprecation-warnings.patch
@@ -1,4 +1,4 @@
-From d6c56537b8ad046b1b6ffd8011226f4cbe626526 Mon Sep 17 00:00:00 2001
+From 65c3799eb9050d065a94ad9992702e3ab8b52050 Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Thu, 8 Mar 2012 16:32:30 +0000
 Subject: [PATCH] fix useexisting deprecation warnings
diff --git a/0018-support-a-configurable-libvirt-injection-partition.patch b/0031-support-a-configurable-libvirt-injection-partition.patch
similarity index 97%
rename from 0018-support-a-configurable-libvirt-injection-partition.patch
rename to 0031-support-a-configurable-libvirt-injection-partition.patch
index f237b33..82c31f6 100644
--- a/0018-support-a-configurable-libvirt-injection-partition.patch
+++ b/0031-support-a-configurable-libvirt-injection-partition.patch
@@ -1,4 +1,4 @@
-From b06d4c0c4648a25ac7605905d7559e9de4cb810a Mon Sep 17 00:00:00 2001
+From 1e01e15630e654cee6cda5c327754f7ffc9e86b6 Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Wed, 18 Apr 2012 23:27:31 +0100
 Subject: [PATCH] support a configurable libvirt injection partition
@@ -47,7 +47,7 @@ index 4fb5dda..11959b2 100644
              else:
                  self.mapped_device = map_path
 diff --git a/nova/virt/libvirt/connection.py b/nova/virt/libvirt/connection.py
-index 2dfe2a3..10d8caa 100644
+index 5bc9ce0..c38283f 100644
 --- a/nova/virt/libvirt/connection.py
 +++ b/nova/virt/libvirt/connection.py
 @@ -108,6 +108,11 @@ libvirt_opts = [
diff --git a/0019-only-mount-guest-image-once-when-injecting-files.patch b/0032-only-mount-guest-image-once-when-injecting-files.patch
similarity index 98%
rename from 0019-only-mount-guest-image-once-when-injecting-files.patch
rename to 0032-only-mount-guest-image-once-when-injecting-files.patch
index 4d9fcd4..2080e94 100644
--- a/0019-only-mount-guest-image-once-when-injecting-files.patch
+++ b/0032-only-mount-guest-image-once-when-injecting-files.patch
@@ -1,4 +1,4 @@
-From 74f89b8fd765e713bdff4823210ccfa3c342cad9 Mon Sep 17 00:00:00 2001
+From b12fa5ea79d7b8adb272795ccb996c8da6578d5c Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Mon, 25 Jun 2012 13:52:46 +0100
 Subject: [PATCH] only mount guest image once when injecting files
@@ -111,7 +111,7 @@ index 04feb76..d6d6007 100644
  
      admin_password is a root password
 diff --git a/nova/virt/libvirt/connection.py b/nova/virt/libvirt/connection.py
-index 10d8caa..50ebbed 100644
+index c38283f..11e5b34 100644
 --- a/nova/virt/libvirt/connection.py
 +++ b/nova/virt/libvirt/connection.py
 @@ -970,12 +970,6 @@ class LibvirtConnection(driver.ComputeDriver):
diff --git a/0020-set-correct-SELinux-context-for-injected-ssh-keys.patch b/0033-set-correct-SELinux-context-for-injected-ssh-keys.patch
similarity index 95%
rename from 0020-set-correct-SELinux-context-for-injected-ssh-keys.patch
rename to 0033-set-correct-SELinux-context-for-injected-ssh-keys.patch
index 5667547..7266f27 100644
--- a/0020-set-correct-SELinux-context-for-injected-ssh-keys.patch
+++ b/0033-set-correct-SELinux-context-for-injected-ssh-keys.patch
@@ -1,4 +1,4 @@
-From da96aac3cfcef22f03a2d3962b5fc0e15a934658 Mon Sep 17 00:00:00 2001
+From ad049175073aba988a1ed62bb4d87e462dd479de Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Wed, 27 Jun 2012 10:29:57 +0100
 Subject: [PATCH] set correct SELinux context for injected ssh keys
@@ -17,10 +17,10 @@ Change-Id: Ibf3869e3ee477e91623e0c030838c1ec8a6128a6
  2 files changed, 37 insertions(+), 0 deletions(-)
 
 diff --git a/nova/rootwrap/compute.py b/nova/rootwrap/compute.py
-index bb53abc..0d43caa 100755
+index a3d7ec0..d28d3a0 100755
 --- a/nova/rootwrap/compute.py
 +++ b/nova/rootwrap/compute.py
-@@ -182,6 +182,10 @@ filterlist = [
+@@ -189,6 +189,10 @@ filterlist = [
      # nova/virt/libvirt/utils.py: 'qemu-img'
      filters.CommandFilter("/usr/bin/qemu-img", "root"),
  
diff --git a/0022-ensure-libguestfs-mounts-are-cleaned-up.patch b/0034-ensure-libguestfs-mounts-are-cleaned-up.patch
similarity index 97%
rename from 0022-ensure-libguestfs-mounts-are-cleaned-up.patch
rename to 0034-ensure-libguestfs-mounts-are-cleaned-up.patch
index 84b2748..4892ce2 100644
--- a/0022-ensure-libguestfs-mounts-are-cleaned-up.patch
+++ b/0034-ensure-libguestfs-mounts-are-cleaned-up.patch
@@ -1,4 +1,4 @@
-From 3e48d95cc79e77c1e51ed1fbc00b9fe46d800f73 Mon Sep 17 00:00:00 2001
+From decebd38721c5e6c054e3b48a130efd154b283c9 Mon Sep 17 00:00:00 2001
 From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
 Date: Wed, 11 Jul 2012 23:45:28 +0100
 Subject: [PATCH] ensure libguestfs mounts are cleaned up
diff --git a/0035-Adding-networking-rules-to-vm-s-on-compute-service-s.patch b/0035-Adding-networking-rules-to-vm-s-on-compute-service-s.patch
new file mode 100644
index 0000000..967f94b
--- /dev/null
+++ b/0035-Adding-networking-rules-to-vm-s-on-compute-service-s.patch
@@ -0,0 +1,45 @@
+From 46c220bb24636c9e3996041c37f08e890e42bcfb Mon Sep 17 00:00:00 2001
+From: Derek Higgins <derekh at redhat.com>
+Date: Mon, 23 Jul 2012 10:46:41 +0100
+Subject: [PATCH] Adding networking rules to vm's on compute service startup
+
+Fixes bug 1027105
+
+Restarting nova-compute resulted in a new empty iptables chain
+"nova-compute-FORWARD" being create. This commit adds a single
+call to plug_vifs which ensures the appropriate filters (and
+bridge) are present on service startup.
+
+Change-Id: I51cbb56acbb244ddddd951a26d3168cf5a9c0314
+(cherry picked from commit c2e957ceb555b88084033d9a1c15a4f338b1476e)
+---
+ nova/compute/manager.py |    9 ++++++++-
+ 1 files changed, 8 insertions(+), 1 deletions(-)
+
+diff --git a/nova/compute/manager.py b/nova/compute/manager.py
+index 784727f..0ce6e31 100644
+--- a/nova/compute/manager.py
++++ b/nova/compute/manager.py
+@@ -235,7 +235,7 @@ class ComputeManager(manager.SchedulerDependentManager):
+         self.driver.init_host(host=self.host)
+         context = nova.context.get_admin_context()
+         instances = self.db.instance_get_all_by_host(context, self.host)
+-        for instance in instances:
++        for count, instance in enumerate(instances):
+             instance_uuid = instance['uuid']
+             db_state = instance['power_state']
+             drv_state = self._get_power_state(context, instance)
+@@ -247,6 +247,13 @@ class ComputeManager(manager.SchedulerDependentManager):
+                         '%(db_state)s.'), locals(), instance=instance)
+ 
+             net_info = compute_utils.get_nw_info_for_instance(instance)
++
++            # We're calling plug_vifs to ensure bridge and iptables
++            # filters are present, calling it once is enough.
++            if count == 0:
++                legacy_net_info = self._legacy_nw_info(net_info)
++                self.driver.plug_vifs(instance, legacy_net_info)
++
+             if ((expect_running and FLAGS.resume_guests_state_on_host_boot) or
+                 FLAGS.start_guests_on_host_boot):
+                 LOG.info(_('Rebooting instance after nova-compute restart.'),
diff --git a/0036-Tolerance-when-parsing-null-connection-info-in-BDM.patch b/0036-Tolerance-when-parsing-null-connection-info-in-BDM.patch
new file mode 100644
index 0000000..a097c0b
--- /dev/null
+++ b/0036-Tolerance-when-parsing-null-connection-info-in-BDM.patch
@@ -0,0 +1,41 @@
+From cd6f94cbb260248f5092fb47e715e06767ba1cae Mon Sep 17 00:00:00 2001
+From: Joe Heck <heckj at mac.com>
+Date: Fri, 1 Jun 2012 21:51:48 +0000
+Subject: [PATCH] Tolerance when parsing null connection info in BDM
+
+Resolves bug 1007615.
+
+Defensive coding against attempt to decode None as a JSON-encoding
+of connection info in an instance block device mapping.
+
+(cherry picked from commit 7d57cc16a6ab3b286e4fd3a479e5b40160980304)
+
+Change-Id: If7afa4fb030b3c53a0b80737ff792e42cc4d3101
+---
+ nova/compute/manager.py |   13 +++++++++----
+ 1 files changed, 9 insertions(+), 4 deletions(-)
+
+diff --git a/nova/compute/manager.py b/nova/compute/manager.py
+index 0ce6e31..4cf12c8 100644
+--- a/nova/compute/manager.py
++++ b/nova/compute/manager.py
+@@ -653,10 +653,15 @@ class ComputeManager(manager.SchedulerDependentManager):
+         bdms = self._get_instance_volume_bdms(context, instance_id)
+         block_device_mapping = []
+         for bdm in bdms:
+-            cinfo = utils.loads(bdm['connection_info'])
+-            block_device_mapping.append({'connection_info': cinfo,
+-                                         'mount_device':
+-                                         bdm['device_name']})
++            try:
++                cinfo = utils.loads(bdm['connection_info'])
++                block_device_mapping.append({'connection_info': cinfo,
++                                             'mount_device':
++                                             bdm['device_name']})
++            except TypeError:
++                # if the block_device_mapping has no value in connection_info
++                # (returned as None), don't include in the mapping
++                pass
+         # NOTE(vish): The mapping is passed in so the driver can disconnect
+         #             from remote volumes if necessary
+         return {'block_device_mapping': block_device_mapping}
diff --git a/0037-Support-EC2-CreateImage-API-for-boot-from-volume.patch b/0037-Support-EC2-CreateImage-API-for-boot-from-volume.patch
new file mode 100644
index 0000000..abc2eca
--- /dev/null
+++ b/0037-Support-EC2-CreateImage-API-for-boot-from-volume.patch
@@ -0,0 +1,185 @@
+From 4e57f9a6f552e3516917ecfcb48aab3d9a9b8482 Mon Sep 17 00:00:00 2001
+From: Eoghan Glynn <eglynn at redhat.com>
+Date: Mon, 9 Jul 2012 11:59:56 +0000
+Subject: [PATCH] Support EC2 CreateImage API for boot-from-volume
+
+Fixes bug lp 988335
+
+For fidelity with AWS, where the EC2 CreateImage API is only
+supported for EBS-backed instances, we now support this API
+for booted-from-volume nova servers.
+
+We create a "place-holder" image in glance with the image data
+being effectively empty, and the following properties set:
+
+  * the imaged instance's kernel and ramdisk IDs
+  * block device mapping containing the appropriate snapshot ID(s)
+
+so that we can boot from this image without providing additional
+context (such as via the nova boot --block-device-mapping option)
+
+Change-Id: I0b3d18d7922f2ad1bc687fa88e2f5d4cf5aa068b
+---
+ nova/api/ec2/cloud.py            |   44 ++++++++++++++++++++++------
+ nova/tests/api/ec2/test_cloud.py |   59 +++++++++++++++++++++++++++++++++----
+ 2 files changed, 87 insertions(+), 16 deletions(-)
+
+diff --git a/nova/api/ec2/cloud.py b/nova/api/ec2/cloud.py
+index 91182e8..47325af 100644
+--- a/nova/api/ec2/cloud.py
++++ b/nova/api/ec2/cloud.py
+@@ -1591,6 +1591,7 @@ class CloudController(object):
+         # NOTE(yamahata): name/description are ignored by register_image(),
+         #                 do so here
+         no_reboot = kwargs.get('no_reboot', False)
++        name = kwargs.get('name')
+         validate_ec2_id(instance_id)
+         ec2_instance_id = instance_id
+         instance_id = ec2utils.ec2_id_to_id(ec2_instance_id)
+@@ -1624,14 +1625,22 @@ class CloudController(object):
+                     raise exception.EC2APIError(
+                         _('Couldn\'t stop instance with in %d sec') % timeout)
+ 
+-        src_image = self._get_image(context, instance['image_ref'])
+-        properties = src_image['properties']
++        glance_uuid = instance['image_ref']
++        ec2_image_id = ec2utils.glance_id_to_ec2_id(context, glance_uuid)
++        src_image = self._get_image(context, ec2_image_id)
++        new_image = dict(src_image)
++        properties = new_image['properties']
+         if instance['root_device_name']:
+             properties['root_device_name'] = instance['root_device_name']
+ 
++        # meaningful image name
++        name_map = dict(instance=instance['uuid'], now=utils.isotime())
++        new_image['name'] = (name or
++                             _('image of %(instance)s at %(now)s') % name_map)
++
+         mapping = []
+         bdms = db.block_device_mapping_get_all_by_instance(context,
+-                                                           instance_id)
++                                                           instance['uuid'])
+         for bdm in bdms:
+             if bdm.no_device:
+                 continue
+@@ -1644,15 +1653,16 @@ class CloudController(object):
+                     m[attr] = val
+ 
+             volume_id = m.get('volume_id')
+-            if m.get('snapshot_id') and volume_id:
++            snapshot_id = m.get('snapshot_id')
++            if snapshot_id and volume_id:
+                 # create snapshot based on volume_id
+                 volume = self.volume_api.get(context, volume_id)
+                 # NOTE(yamahata): Should we wait for snapshot creation?
+                 #                 Linux LVM snapshot creation completes in
+                 #                 short time, it doesn't matter for now.
++                name = _('snapshot for %s') % new_image['name']
+                 snapshot = self.volume_api.create_snapshot_force(
+-                        context, volume, volume['display_name'],
+-                        volume['display_description'])
++                        context, volume, name, volume['display_description'])
+                 m['snapshot_id'] = snapshot['id']
+                 del m['volume_id']
+ 
+@@ -1679,11 +1689,27 @@ class CloudController(object):
+             properties['block_device_mapping'] = mapping
+ 
+         for attr in ('status', 'location', 'id'):
+-            src_image.pop(attr, None)
++            new_image.pop(attr, None)
++
++        # the new image is simply a bucket of properties (particularly the
++        # block device mapping, kernel and ramdisk IDs) with no image data,
++        # hence the zero size
++        new_image['size'] = 0
++
++        def _unmap_id_property(properties, name):
++            if properties[name]:
++                properties[name] = ec2utils.id_to_glance_id(context,
++                                                            properties[name])
+ 
+-        image_id = self._register_image(context, src_image)
++        # ensure the ID properties are unmapped back to the glance UUID
++        _unmap_id_property(properties, 'kernel_id')
++        _unmap_id_property(properties, 'ramdisk_id')
++
++        new_image = self.image_service.service.create(context, new_image,
++                                                      data='')
++        ec2_id = ec2utils.glance_id_to_ec2_id(context, new_image['id'])
+ 
+         if restart_instance:
+             self.compute_api.start(context, instance_id=instance_id)
+ 
+-        return {'imageId': image_id}
++        return {'imageId': ec2_id}
+diff --git a/nova/tests/api/ec2/test_cloud.py b/nova/tests/api/ec2/test_cloud.py
+index 4ed3c04..01ac95a 100644
+--- a/nova/tests/api/ec2/test_cloud.py
++++ b/nova/tests/api/ec2/test_cloud.py
+@@ -2064,13 +2064,58 @@ class CloudTestCase(test.TestCase):
+                   'max_count': 1}
+         ec2_instance_id = self._run_instance(**kwargs)
+ 
+-        # TODO(yamahata): s3._s3_create() can't be tested easily by unit test
+-        #                 as there is no unit test for s3.create()
+-        ## result = self.cloud.create_image(self.context, ec2_instance_id,
+-        ##                                  no_reboot=True)
+-        ## ec2_image_id = result['imageId']
+-        ## created_image = self.cloud.describe_images(self.context,
+-        ##                                            [ec2_image_id])
++        def fake_show(meh, context, id):
++            bdm = [dict(snapshot_id=snapshots[0],
++                        volume_size=1,
++                        device_name='vda',
++                        delete_on_termination=False)]
++            props = dict(kernel_id='cedef40a-ed67-4d10-800e-17455edce175',
++                         ramdisk_id='76fa36fc-c930-4bf3-8c8a-ea2a2420deb6',
++                         block_device_mapping=bdm)
++            return dict(id=id,
++                        properties=props,
++                        container_format='ami',
++                        status='active',
++                        is_public=True)
++
++        self.stubs.Set(fake._FakeImageService, 'show', fake_show)
++
++        def fake_block_device_mapping_get_all_by_instance(context, inst_id):
++            class BDM(object):
++                def __init__(self):
++                    self.no_device = None
++                    self.values = dict(snapshot_id=snapshots[0],
++                                       volume_id=volumes[0],
++                                       virtual_name=None,
++                                       volume_size=1,
++                                       device_name='vda',
++                                       delete_on_termination=False)
++
++                def __getattr__(self, name):
++                    return self.values.get(name)
++
++                def __getitem__(self, key):
++                    return self.values.get(key)
++
++            return [BDM()]
++
++        self.stubs.Set(db, 'block_device_mapping_get_all_by_instance',
++                       fake_block_device_mapping_get_all_by_instance)
++
++        result = self.cloud.create_image(self.context, ec2_instance_id,
++                                         no_reboot=True)
++        ec2_ids = [result['imageId']]
++        created_image = self.cloud.describe_images(self.context,
++                                                   ec2_ids)['imagesSet'][0]
++
++        self.assertTrue('blockDeviceMapping' in created_image)
++        bdm = created_image['blockDeviceMapping'][0]
++        self.assertEquals(bdm.get('deviceName'), 'vda')
++        self.assertTrue('ebs' in bdm)
++        self.assertEquals(bdm['ebs'].get('snapshotId'),
++                          'snap-%08x' % snapshots[0])
++        self.assertEquals(created_image.get('kernelId'), 'aki-00000001')
++        self.assertEquals(created_image.get('ramdiskId'), 'ari-00000002')
+ 
+         self.cloud.terminate_instances(self.context, [ec2_instance_id])
+         for vol in volumes:
diff --git a/0038-EC2-DescribeImages-reports-correct-rootDeviceType.patch b/0038-EC2-DescribeImages-reports-correct-rootDeviceType.patch
new file mode 100644
index 0000000..92c18a6
--- /dev/null
+++ b/0038-EC2-DescribeImages-reports-correct-rootDeviceType.patch
@@ -0,0 +1,66 @@
+From d18beab9fb9c5f61b7a8ec9d64dc95839ccc537e Mon Sep 17 00:00:00 2001
+From: Eoghan Glynn <eglynn at redhat.com>
+Date: Sat, 14 Jul 2012 21:30:43 +0100
+Subject: [PATCH] EC2 DescribeImages reports correct rootDeviceType
+
+Fixes LP 1024354
+
+A root device type of instance-store was incorrectly reported for
+boot-from-volume images (i.e. the analogue of EBS-backed AMIs).
+
+When comparing the block device mapping device name with the root
+device name, we now tolerate a missing leading '/dev/' path.
+
+Change-Id: I1d3bda780deee52f5d41e3af041aba7e6305dfde
+---
+ nova/api/ec2/cloud.py            |    4 +++-
+ nova/block_device.py             |    2 +-
+ nova/tests/api/ec2/test_cloud.py |    2 ++
+ 3 files changed, 6 insertions(+), 2 deletions(-)
+
+diff --git a/nova/api/ec2/cloud.py b/nova/api/ec2/cloud.py
+index 47325af..7172954 100644
+--- a/nova/api/ec2/cloud.py
++++ b/nova/api/ec2/cloud.py
+@@ -1445,8 +1445,10 @@ class CloudController(object):
+         properties = image['properties']
+         root_device_name = block_device.properties_root_device_name(properties)
+         root_device_type = 'instance-store'
++
+         for bdm in properties.get('block_device_mapping', []):
+-            if (bdm.get('device_name') == root_device_name and
++            if (block_device.strip_dev(bdm.get('device_name')) ==
++                block_device.strip_dev(root_device_name) and
+                 ('snapshot_id' in bdm or 'volume_id' in bdm) and
+                 not bdm.get('no_device')):
+                 root_device_type = 'ebs'
+diff --git a/nova/block_device.py b/nova/block_device.py
+index 1b7d381..1ddac43 100644
+--- a/nova/block_device.py
++++ b/nova/block_device.py
+@@ -71,4 +71,4 @@ _dev = re.compile('^/dev/')
+ 
+ def strip_dev(device_name):
+     """remove leading '/dev/'"""
+-    return _dev.sub('', device_name)
++    return _dev.sub('', device_name) if device_name else device_name
+diff --git a/nova/tests/api/ec2/test_cloud.py b/nova/tests/api/ec2/test_cloud.py
+index 01ac95a..d8da26d 100644
+--- a/nova/tests/api/ec2/test_cloud.py
++++ b/nova/tests/api/ec2/test_cloud.py
+@@ -2071,6 +2071,7 @@ class CloudTestCase(test.TestCase):
+                         delete_on_termination=False)]
+             props = dict(kernel_id='cedef40a-ed67-4d10-800e-17455edce175',
+                          ramdisk_id='76fa36fc-c930-4bf3-8c8a-ea2a2420deb6',
++                         root_device_name='/dev/vda',
+                          block_device_mapping=bdm)
+             return dict(id=id,
+                         properties=props,
+@@ -2116,6 +2117,7 @@ class CloudTestCase(test.TestCase):
+                           'snap-%08x' % snapshots[0])
+         self.assertEquals(created_image.get('kernelId'), 'aki-00000001')
+         self.assertEquals(created_image.get('ramdiskId'), 'ari-00000002')
++        self.assertEquals(created_image.get('rootDeviceType'), 'ebs')
+ 
+         self.cloud.terminate_instances(self.context, [ec2_instance_id])
+         for vol in volumes:
diff --git a/0039-Reject-EC2-CreateImage-for-instance-store.patch b/0039-Reject-EC2-CreateImage-for-instance-store.patch
new file mode 100644
index 0000000..ad0aacf
--- /dev/null
+++ b/0039-Reject-EC2-CreateImage-for-instance-store.patch
@@ -0,0 +1,158 @@
+From efc454dbb6a422e36da081827b4f566a4ee05854 Mon Sep 17 00:00:00 2001
+From: Eoghan Glynn <eglynn at redhat.com>
+Date: Tue, 17 Jul 2012 15:20:30 +0100
+Subject: [PATCH] Reject EC2 CreateImage for instance-store
+
+For fidelity with AWS, we explicitly do not support the EC2 CreateImage
+API for the analogue of instance-store-backed instances.
+
+Change-Id: I266a021ce53dbb1f521201f1cdc614b08c31bf8d
+---
+ nova/api/ec2/cloud.py            |   13 ++++++++-
+ nova/compute/api.py              |   14 ++++++++++
+ nova/tests/api/ec2/test_cloud.py |   52 +++++++++++++++++++++++++++++++++++---
+ 3 files changed, 73 insertions(+), 6 deletions(-)
+
+diff --git a/nova/api/ec2/cloud.py b/nova/api/ec2/cloud.py
+index 7172954..e9bf1b2 100644
+--- a/nova/api/ec2/cloud.py
++++ b/nova/api/ec2/cloud.py
+@@ -1599,6 +1599,17 @@ class CloudController(object):
+         instance_id = ec2utils.ec2_id_to_id(ec2_instance_id)
+         instance = self.compute_api.get(context, instance_id)
+ 
++        bdms = self.compute_api.get_instance_bdms(context, instance)
++
++        # CreateImage only supported for the analogue of EBS-backed instances
++        if not self.compute_api.is_volume_backed_instance(context, instance,
++                                                          bdms):
++            root = instance['root_device_name']
++            msg = _("Invalid value '%(ec2_instance_id)s' for instanceId. "
++                    "Instance does not have a volume attached at root "
++                    "(%(root)s)") % locals()
++            raise exception.InvalidParameterValue(err=msg)
++
+         # stop the instance if necessary
+         restart_instance = False
+         if not no_reboot:
+@@ -1641,8 +1652,6 @@ class CloudController(object):
+                              _('image of %(instance)s at %(now)s') % name_map)
+ 
+         mapping = []
+-        bdms = db.block_device_mapping_get_all_by_instance(context,
+-                                                           instance['uuid'])
+         for bdm in bdms:
+             if bdm.no_device:
+                 continue
+diff --git a/nova/compute/api.py b/nova/compute/api.py
+index 48f3d47..d756885 100644
+--- a/nova/compute/api.py
++++ b/nova/compute/api.py
+@@ -1685,6 +1685,20 @@ class API(BaseAPI):
+         uuids = [instance['uuid'] for instance in instances]
+         return self.db.instance_fault_get_by_instance_uuids(context, uuids)
+ 
++    def get_instance_bdms(self, context, instance):
++        """Get all bdm tables for specified instance."""
++        return self.db.block_device_mapping_get_all_by_instance(context,
++                instance['uuid'])
++
++    def is_volume_backed_instance(self, context, instance, bdms):
++        bdms = bdms or self.get_instance_bdms(context, instance)
++        for bdm in bdms:
++            if (block_device.strip_dev(bdm.device_name) ==
++                block_device.strip_dev(instance['root_device_name'])):
++                return True
++        else:
++            return False
++
+ 
+ class HostAPI(BaseAPI):
+     """Sub-set of the Compute Manager API for managing host operations."""
+diff --git a/nova/tests/api/ec2/test_cloud.py b/nova/tests/api/ec2/test_cloud.py
+index d8da26d..d4109e4 100644
+--- a/nova/tests/api/ec2/test_cloud.py
++++ b/nova/tests/api/ec2/test_cloud.py
+@@ -2067,11 +2067,11 @@ class CloudTestCase(test.TestCase):
+         def fake_show(meh, context, id):
+             bdm = [dict(snapshot_id=snapshots[0],
+                         volume_size=1,
+-                        device_name='vda',
++                        device_name='sda1',
+                         delete_on_termination=False)]
+             props = dict(kernel_id='cedef40a-ed67-4d10-800e-17455edce175',
+                          ramdisk_id='76fa36fc-c930-4bf3-8c8a-ea2a2420deb6',
+-                         root_device_name='/dev/vda',
++                         root_device_name='/dev/sda1',
+                          block_device_mapping=bdm)
+             return dict(id=id,
+                         properties=props,
+@@ -2089,7 +2089,7 @@ class CloudTestCase(test.TestCase):
+                                        volume_id=volumes[0],
+                                        virtual_name=None,
+                                        volume_size=1,
+-                                       device_name='vda',
++                                       device_name='sda1',
+                                        delete_on_termination=False)
+ 
+                 def __getattr__(self, name):
+@@ -2111,7 +2111,7 @@ class CloudTestCase(test.TestCase):
+ 
+         self.assertTrue('blockDeviceMapping' in created_image)
+         bdm = created_image['blockDeviceMapping'][0]
+-        self.assertEquals(bdm.get('deviceName'), 'vda')
++        self.assertEquals(bdm.get('deviceName'), 'sda1')
+         self.assertTrue('ebs' in bdm)
+         self.assertEquals(bdm['ebs'].get('snapshotId'),
+                           'snap-%08x' % snapshots[0])
+@@ -2128,6 +2128,50 @@ class CloudTestCase(test.TestCase):
+ 
+         self._restart_compute_service()
+ 
++    def test_create_image_instance_store(self):
++        """
++        Ensure CreateImage fails as expected for an instance-store-backed
++        instance
++        """
++        # enforce periodic tasks run in short time to avoid wait for 60s.
++        self._restart_compute_service(periodic_interval=0.3)
++
++        (volumes, snapshots) = self._setUpImageSet(
++            create_volumes_and_snapshots=True)
++
++        kwargs = {'image_id': 'ami-1',
++                  'instance_type': FLAGS.default_instance_type,
++                  'max_count': 1}
++        ec2_instance_id = self._run_instance(**kwargs)
++
++        def fake_block_device_mapping_get_all_by_instance(context, inst_id):
++            class BDM(object):
++                def __init__(self):
++                    self.no_device = None
++                    self.values = dict(snapshot_id=snapshots[0],
++                                       volume_id=volumes[0],
++                                       virtual_name=None,
++                                       volume_size=1,
++                                       device_name='vda',
++                                       delete_on_termination=False)
++
++                def __getattr__(self, name):
++                    return self.values.get(name)
++
++                def __getitem__(self, key):
++                    return self.values.get(key)
++
++            return [BDM()]
++
++        self.stubs.Set(db, 'block_device_mapping_get_all_by_instance',
++                       fake_block_device_mapping_get_all_by_instance)
++
++        self.assertRaises(exception.InvalidParameterValue,
++                          self.cloud.create_image,
++                          self.context,
++                          ec2_instance_id,
++                          no_reboot=True)
++
+     @staticmethod
+     def _fake_bdm_get(ctxt, id):
+             return [{'volume_id': 87654321,
diff --git a/0040-Fix-EC2-CreateImage-no_reboot-logic.patch b/0040-Fix-EC2-CreateImage-no_reboot-logic.patch
new file mode 100644
index 0000000..8203793
--- /dev/null
+++ b/0040-Fix-EC2-CreateImage-no_reboot-logic.patch
@@ -0,0 +1,94 @@
+From 885c385b63ef2ac9813f6a40dc1d885cc010ed88 Mon Sep 17 00:00:00 2001
+From: Eoghan Glynn <eglynn at redhat.com>
+Date: Tue, 17 Jul 2012 18:18:07 +0100
+Subject: [PATCH] Fix EC2 CreateImage no_reboot logic
+
+Previously the call to restart the imaged instance was incorrect.
+
+This is now fixed and unit tested.
+
+Change-Id: Ifde193e084ecdbc37a57150f28d833ae276f49c6
+---
+ nova/api/ec2/cloud.py            |    2 +-
+ nova/tests/api/ec2/test_cloud.py |   27 +++++++++++++++++++++++++--
+ 2 files changed, 26 insertions(+), 3 deletions(-)
+
+diff --git a/nova/api/ec2/cloud.py b/nova/api/ec2/cloud.py
+index e9bf1b2..88b8861 100644
+--- a/nova/api/ec2/cloud.py
++++ b/nova/api/ec2/cloud.py
+@@ -1721,6 +1721,6 @@ class CloudController(object):
+         ec2_id = ec2utils.glance_id_to_ec2_id(context, new_image['id'])
+ 
+         if restart_instance:
+-            self.compute_api.start(context, instance_id=instance_id)
++            self.compute_api.start(context, instance)
+ 
+         return {'imageId': ec2_id}
+diff --git a/nova/tests/api/ec2/test_cloud.py b/nova/tests/api/ec2/test_cloud.py
+index d4109e4..cd3c7a3 100644
+--- a/nova/tests/api/ec2/test_cloud.py
++++ b/nova/tests/api/ec2/test_cloud.py
+@@ -40,6 +40,7 @@ from nova import log as logging
+ from nova import rpc
+ from nova import test
+ from nova import utils
++from nova.virt import driver
+ 
+ 
+ LOG = logging.getLogger(__name__)
+@@ -2051,7 +2052,7 @@ class CloudTestCase(test.TestCase):
+ 
+         db.volume_destroy(self.context, vol['id'])
+ 
+-    def test_create_image(self):
++    def _do_test_create_image(self, no_reboot):
+         """Make sure that CreateImage works"""
+         # enforce periodic tasks run in short time to avoid wait for 60s.
+         self._restart_compute_service(periodic_interval=0.3)
+@@ -2103,8 +2104,20 @@ class CloudTestCase(test.TestCase):
+         self.stubs.Set(db, 'block_device_mapping_get_all_by_instance',
+                        fake_block_device_mapping_get_all_by_instance)
+ 
++        virt_driver = {}
++
++        def fake_power_on(self, instance):
++            virt_driver['powered_on'] = True
++
++        self.stubs.Set(driver.ComputeDriver, 'power_on', fake_power_on)
++
++        def fake_power_off(self, instance):
++            virt_driver['powered_off'] = True
++
++        self.stubs.Set(driver.ComputeDriver, 'power_off', fake_power_off)
++
+         result = self.cloud.create_image(self.context, ec2_instance_id,
+-                                         no_reboot=True)
++                                         no_reboot=no_reboot)
+         ec2_ids = [result['imageId']]
+         created_image = self.cloud.describe_images(self.context,
+                                                    ec2_ids)['imagesSet'][0]
+@@ -2118,6 +2131,8 @@ class CloudTestCase(test.TestCase):
+         self.assertEquals(created_image.get('kernelId'), 'aki-00000001')
+         self.assertEquals(created_image.get('ramdiskId'), 'ari-00000002')
+         self.assertEquals(created_image.get('rootDeviceType'), 'ebs')
++        self.assertNotEqual(virt_driver.get('powered_on'), no_reboot)
++        self.assertNotEqual(virt_driver.get('powered_off'), no_reboot)
+ 
+         self.cloud.terminate_instances(self.context, [ec2_instance_id])
+         for vol in volumes:
+@@ -2128,6 +2143,14 @@ class CloudTestCase(test.TestCase):
+ 
+         self._restart_compute_service()
+ 
++    def test_create_image_no_reboot(self):
++        """Make sure that CreateImage works"""
++        self._do_test_create_image(True)
++
++    def test_create_image_with_reboot(self):
++        """Make sure that CreateImage works"""
++        self._do_test_create_image(False)
++
+     def test_create_image_instance_store(self):
+         """
+         Ensure CreateImage fails as expected for an instance-store-backed
diff --git a/0041-use-boto-s-HTTPResponse-class-for-versions-of-boto-2.patch b/0041-use-boto-s-HTTPResponse-class-for-versions-of-boto-2.patch
new file mode 100644
index 0000000..0855be7
--- /dev/null
+++ b/0041-use-boto-s-HTTPResponse-class-for-versions-of-boto-2.patch
@@ -0,0 +1,66 @@
+From 2a5a35e08173a8118b0490fc509df7eeac3970ea Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?Ionu=C8=9B=20Ar=C8=9B=C4=83ri=C8=99i?= <iartarisi at suse.cz>
+Date: Tue, 24 Jul 2012 11:33:53 +0200
+Subject: [PATCH] use boto's HTTPResponse class for versions of boto >=2.5.2
+
+Fixes bug: 1027984
+
+Change-Id: I2101ddaa78ede90f39b55d28aab73e7f5a816af5
+---
+ Authors                |    1 +
+ nova/tests/test_api.py |   10 +++++++---
+ 2 files changed, 8 insertions(+), 3 deletions(-)
+
+diff --git a/Authors b/Authors
+index a903742..97734ee 100644
+--- a/Authors
++++ b/Authors
+@@ -75,6 +75,7 @@ Hengqing Hu <hudayou at hotmail.com>
+ Hisaharu Ishii <ishii.hisaharu at lab.ntt.co.jp>
+ Hisaki Ohara <hisaki.ohara at intel.com>
+ Ilya Alekseyev <ilyaalekseyev at acm.org>
++Ionuț Arțăriși <iartarisi at suse.cz>
+ Isaku Yamahata <yamahata at valinux.co.jp>
+ Ivan Kolodyazhny <e0ne at e0ne.info>
+ J. Daniel Schmidt <jdsn at suse.de>
+diff --git a/nova/tests/test_api.py b/nova/tests/test_api.py
+index a52319f..4a04783 100644
+--- a/nova/tests/test_api.py
++++ b/nova/tests/test_api.py
+@@ -19,13 +19,17 @@
+ """Unit tests for the API endpoint"""
+ 
+ import datetime
+-import httplib
+ import random
+ import StringIO
+ 
+ import boto
+ from boto.ec2 import regioninfo
+ from boto import exception as boto_exc
++# newer versions of boto use their own wrapper on top of httplib.HTTPResponse
++try:
++    from boto.connection import HTTPResponse
++except ImportError:
++    from httplib import HTTPResponse
+ import webob
+ 
+ from nova import block_device
+@@ -55,7 +59,7 @@ class FakeHttplibConnection(object):
+ 
+     requests made via this connection actually get translated and routed into
+     our WSGI app, we then wait for the response and turn it back into
+-    the httplib.HTTPResponse that boto expects.
++    the HTTPResponse that boto expects.
+     """
+     def __init__(self, app, host, is_secure=False):
+         self.app = app
+@@ -74,7 +78,7 @@ class FakeHttplibConnection(object):
+         # guess that's a function the web server usually provides.
+         resp = "HTTP/1.0 %s" % resp
+         self.sock = FakeHttplibSocket(resp)
+-        self.http_response = httplib.HTTPResponse(self.sock)
++        self.http_response = HTTPResponse(self.sock)
+         # NOTE(vish): boto is accessing private variables for some reason
+         self._HTTPConnection__response = self.http_response
+         self.http_response.begin()
diff --git a/0042-Convert-remaining-network-API-casts-to-calls.patch b/0042-Convert-remaining-network-API-casts-to-calls.patch
new file mode 100644
index 0000000..8b16981
--- /dev/null
+++ b/0042-Convert-remaining-network-API-casts-to-calls.patch
@@ -0,0 +1,97 @@
+From 3feabf6a93104a1eb0da3106288a8c4c65056c57 Mon Sep 17 00:00:00 2001
+From: Phil Day <philip.day at hp.com>
+Date: Wed, 11 Jul 2012 09:26:11 +0100
+Subject: [PATCH] Convert remaining network API casts to calls
+
+Fix for Bug 1021340
+
+During compute/terminate_instance networking is de-allocated by a call to
+network/api/deallocate_for_instance(), which is implemented as an rpc.cast to
+the network manager. This in turn will eventually call
+network/manager/deallocate_fixed_ip(), which in turn call the compute API to
+trigger a security group refresh, which will get the instance from the database
+
+However because original call to the network manager is a cast there is a chance
+that the compute manager will delete the instance record in the DB before the
+compute API (in the network manager) tries to retrieve the instance. At this
+point the security group refresh fails (leaving rules in place which are a
+security risk when the IP is reused), and potentially stopping otheraspects
+of the network deallocation from completing.
+
+Changing this from rpc.call to rpc.cast will fix this issue.
+
+Aside from this specific use of a cast there are 4 other casts in the
+network API:
+  add_fixed_ip_to_instance
+  remove_fixed_ip_from_instance
+  add_network_to_project
+  release_floating_ip
+
+and to avoid other timing issues these will also be converted to calls.
+
+Change-Id: I5cdcc628293d3e7cf165c5ffe4883f138783f73f
+(cherry picked from commit 34f9d7e974d0e09c723e0a04ed6eecd1b482e77d)
+---
+ Authors             |    1 +
+ nova/network/api.py |   10 +++++-----
+ 2 files changed, 6 insertions(+), 5 deletions(-)
+
+diff --git a/Authors b/Authors
+index 97734ee..d28e842 100644
+--- a/Authors
++++ b/Authors
+@@ -159,6 +159,7 @@ Ollie Leahy <oliver.leahy at hp.com>
+ Pádraig Brady <pbrady at redhat.com>
+ Paul Voccio <paul at openstack.org>
+ Peng Yong <ppyy at pubyun.com>
++Phil Day <philip.day at hp.com>
+ Philip Knouff <philip.knouff at mailtrust.com>
+ Ralf Haferkamp <rhafer at suse.de>
+ Renuka Apte <renuka.apte at citrix.com>
+diff --git a/nova/network/api.py b/nova/network/api.py
+index 96a7a2f..6748950 100644
+--- a/nova/network/api.py
++++ b/nova/network/api.py
+@@ -126,7 +126,7 @@ class API(base.Base):
+     def release_floating_ip(self, context, address,
+                             affect_auto_assigned=False):
+         """Removes floating ip with address from a project. (deallocates)"""
+-        rpc.cast(context,
++        rpc.call(context,
+                  FLAGS.network_topic,
+                  {'method': 'deallocate_floating_ip',
+                   'args': {'address': address,
+@@ -185,7 +185,7 @@ class API(base.Base):
+         args['instance_id'] = instance['id']
+         args['project_id'] = instance['project_id']
+         args['host'] = instance['host']
+-        rpc.cast(context, FLAGS.network_topic,
++        rpc.call(context, FLAGS.network_topic,
+                  {'method': 'deallocate_for_instance',
+                   'args': args})
+ 
+@@ -194,7 +194,7 @@ class API(base.Base):
+         args = {'instance_id': instance['id'],
+                 'host': instance['host'],
+                 'network_id': network_id}
+-        rpc.cast(context, FLAGS.network_topic,
++        rpc.call(context, FLAGS.network_topic,
+                  {'method': 'add_fixed_ip_to_instance',
+                   'args': args})
+ 
+@@ -204,13 +204,13 @@ class API(base.Base):
+         args = {'instance_id': instance['id'],
+                 'host': instance['host'],
+                 'address': address}
+-        rpc.cast(context, FLAGS.network_topic,
++        rpc.call(context, FLAGS.network_topic,
+                  {'method': 'remove_fixed_ip_from_instance',
+                   'args': args})
+ 
+     def add_network_to_project(self, context, project_id):
+         """Force adds another network to a project."""
+-        rpc.cast(context, FLAGS.network_topic,
++        rpc.call(context, FLAGS.network_topic,
+                  {'method': 'add_network_to_project',
+                   'args': {'project_id': project_id}})
+ 
diff --git a/0043-Moving-where-the-fixed-ip-deallocation-happens.patch b/0043-Moving-where-the-fixed-ip-deallocation-happens.patch
new file mode 100644
index 0000000..cfa1357
--- /dev/null
+++ b/0043-Moving-where-the-fixed-ip-deallocation-happens.patch
@@ -0,0 +1,106 @@
+From a301bb5f81af84816af15ab178e13ba226a7535e Mon Sep 17 00:00:00 2001
+From: David McNally <dave.mcnally at hp.com>
+Date: Fri, 27 Jul 2012 13:32:14 +0100
+Subject: [PATCH] Moving where the fixed ip deallocation happens.
+
+Fixes bug 1021352.
+
+In network/manager/deallocate_fixed_ip the call
+to mark the IP as no longer allocated occurs before
+the call to update security group rules. This means
+that if an error occurs in the security group
+processing, or if for some reason it is very slow
+there is a risk that that the address is reused by
+another tenant before the rules relating to this address
+have been fully revoked.
+
+Moving the db call to after the call to trigger the
+security group refresh would avoid the issue when an
+error occurs (the fixed_ip should not be released in
+this case).
+
+Change-Id: Iaba1af5c9a17fbbb82e42522b1060773de61550a
+(cherry picked from commit 44132acbe91092de1188a3015a2c7155b5ec774c)
+---
+ Authors                            |    1 +
+ nova/network/manager.py            |    7 ++++---
+ nova/tests/network/test_manager.py |   29 +++++++++++++++++++++++++++++
+ 3 files changed, 34 insertions(+), 3 deletions(-)
+
+diff --git a/Authors b/Authors
+index d28e842..73dd444 100644
+--- a/Authors
++++ b/Authors
+@@ -43,6 +43,7 @@ Dan Wendlandt <dan at nicira.com>
+ Daniel P. Berrange <berrange at redhat.com>
+ Dave Lapsley <dlapsley at nicira.com>
+ Dave Walker <Dave.Walker at canonical.com>
++David McNally <dave.mcnally at hp.com>
+ David Pravec <David.Pravec at danix.org>
+ David Subiros <david.perez5 at hp.com>
+ Dean Troyer <dtroyer at gmail.com>
+diff --git a/nova/network/manager.py b/nova/network/manager.py
+index 2354879..1b9e98e 100644
+--- a/nova/network/manager.py
++++ b/nova/network/manager.py
+@@ -1201,9 +1201,6 @@ class NetworkManager(manager.SchedulerDependentManager):
+         """Returns a fixed ip to the pool."""
+         fixed_ip_ref = self.db.fixed_ip_get_by_address(context, address)
+         vif_id = fixed_ip_ref['virtual_interface_id']
+-        self.db.fixed_ip_update(context, address,
+-                                {'allocated': False,
+-                                 'virtual_interface_id': None})
+         instance_id = fixed_ip_ref['instance_id']
+         self._do_trigger_security_group_members_refresh_for_instance(
+                                                                    instance_id)
+@@ -1238,6 +1235,10 @@ class NetworkManager(manager.SchedulerDependentManager):
+             #             callback will get called by nova-dhcpbridge.
+             self.driver.release_dhcp(dev, address, vif['address'])
+ 
++        self.db.fixed_ip_update(context, address,
++                                {'allocated': False,
++                                 'virtual_interface_id': None})
++
+     def lease_fixed_ip(self, context, address):
+         """Called by dhcp-bridge when ip is leased."""
+         LOG.debug(_('Leased IP |%(address)s|'), locals(), context=context)
+diff --git a/nova/tests/network/test_manager.py b/nova/tests/network/test_manager.py
+index a4b6c30..4a7e2ef 100644
+--- a/nova/tests/network/test_manager.py
++++ b/nova/tests/network/test_manager.py
+@@ -937,6 +937,35 @@ class VlanNetworkTestCase(test.TestCase):
+         self.flags(force_dhcp_release=True)
+         self.network.deallocate_fixed_ip(context1, fix_addr, 'fake')
+ 
++    def test_fixed_ip_cleanup_fail(self):
++        """Verify IP is not deallocated if the security group refresh fails."""
++        def network_get(_context, network_id):
++            return networks[network_id]
++
++        self.stubs.Set(db, 'network_get', network_get)
++
++        context1 = context.RequestContext('user', 'project1')
++
++        instance = db.instance_create(context1,
++                {'project_id': 'project1'})
++
++        elevated = context1.elevated()
++        fix_addr = db.fixed_ip_associate_pool(elevated, 1, instance['uuid'])
++        values = {'allocated': True,
++                  'virtual_interface_id': 3}
++        db.fixed_ip_update(elevated, fix_addr, values)
++        fixed = db.fixed_ip_get_by_address(elevated, fix_addr)
++        network = db.network_get(elevated, fixed['network_id'])
++
++        db.instance_destroy(self.context.elevated(), instance['uuid'])
++        self.assertRaises(exception.InstanceNotFound,
++                                  self.network.deallocate_fixed_ip,
++                                  context1,
++                                  fix_addr,
++                                  'fake')
++        fixed = db.fixed_ip_get_by_address(elevated, fix_addr)
++        self.assertTrue(fixed['allocated'])
++
+ 
+ class CommonNetworkTestCase(test.TestCase):
+ 
diff --git a/0044-fix-the-qpid_heartbeat-option-so-that-it-s-effective.patch b/0044-fix-the-qpid_heartbeat-option-so-that-it-s-effective.patch
new file mode 100644
index 0000000..217400e
--- /dev/null
+++ b/0044-fix-the-qpid_heartbeat-option-so-that-it-s-effective.patch
@@ -0,0 +1,27 @@
+From 6331ce6abb9c7cd1afe9590cd6496b8fff23e9a6 Mon Sep 17 00:00:00 2001
+From: =?UTF-8?q?P=C3=A1draig=20Brady?= <pbrady at redhat.com>
+Date: Mon, 30 Jul 2012 01:54:14 +0100
+Subject: [PATCH] fix the qpid_heartbeat option so that it's effective
+
+The 'hearbeat' typo caused this setting to be ineffective.
+
+Present Since: essex-1-861-gbe96c43
+Fixes bug: 1030430
+Change-Id: Ibb9d7484b9d11a6904cc9e2a8dde6d9164ee05b1
+---
+ nova/rpc/impl_qpid.py |    2 +-
+ 1 files changed, 1 insertions(+), 1 deletions(-)
+
+diff --git a/nova/rpc/impl_qpid.py b/nova/rpc/impl_qpid.py
+index 289f21b..e19079e 100644
+--- a/nova/rpc/impl_qpid.py
++++ b/nova/rpc/impl_qpid.py
+@@ -317,7 +317,7 @@ class Connection(object):
+                     FLAGS.qpid_reconnect_interval_min)
+         if FLAGS.qpid_reconnect_interval:
+             self.connection.reconnect_interval = FLAGS.qpid_reconnect_interval
+-        self.connection.hearbeat = FLAGS.qpid_heartbeat
++        self.connection.heartbeat = FLAGS.qpid_heartbeat
+         self.connection.protocol = FLAGS.qpid_protocol
+         self.connection.tcp_nodelay = FLAGS.qpid_tcp_nodelay
+ 
diff --git a/openstack-nova.spec b/openstack-nova.spec
index f661ee8..995085c 100644
--- a/openstack-nova.spec
+++ b/openstack-nova.spec
@@ -2,7 +2,7 @@
 
 Name:             openstack-nova
 Version:          2012.1.1
-Release:          10%{?dist}
+Release:          11%{?dist}
 Summary:          OpenStack Compute (nova)
 
 Group:            Applications/System
@@ -32,26 +32,47 @@ Source24:         nova-sudoers
 #
 # patches_base=2012.1.1
 #
-Patch0003: 0003-Call-libvirt_volume_driver-with-right-mountpoint.patch
-Patch0004: 0004-Use-fake_libvirt_utils-for-libvirt-console-tests.patch
-Patch0005: 0005-Fixes-ram_allocation_ratio-based-over-subscription.patch
-Patch0006: 0006-Stop-nova_ipam_lib-from-changing-the-timeout-setting.patch
-Patch0007: 0007-Prevent-file-injection-writing-to-host-filesystem.patch
-Patch0008: 0008-Distinguish-over-quota-for-volume-size-and-number.patch
-Patch0009: 0009-Expose-over-quota-exceptions-via-native-API.patch
-Patch0010: 0010-Fix-call-to-network_get_all_by_uuids.patch
-Patch0011: 0011-fix-libvirt-get_memory_mb_total-with-xen.patch
-Patch0012: 0012-Use-compute_api.get_all-in-affinity-filters.patch
-Patch0013: 0013-Use-default-qemu-img-cluster-size-in-libvirt-connect.patch
-Patch0014: 0014-Return-413-status-on-over-quota-in-the-native-API.patch
-Patch0015: 0015-ensure-atomic-manipulation-of-libvirt-disk-images.patch
-Patch0016: 0016-Ensure-we-don-t-access-the-net-when-building-docs.patch
-Patch0017: 0017-fix-useexisting-deprecation-warnings.patch
-Patch0018: 0018-support-a-configurable-libvirt-injection-partition.patch
-Patch0019: 0019-only-mount-guest-image-once-when-injecting-files.patch
-Patch0020: 0020-set-correct-SELinux-context-for-injected-ssh-keys.patch
-Patch0021: 0021-ensure-libguestfs-has-completed-before-proceeding.patch
-Patch0022: 0022-ensure-libguestfs-mounts-are-cleaned-up.patch
+Patch0004: 0004-Call-libvirt_volume_driver-with-right-mountpoint.patch
+Patch0005: 0005-Use-fake_libvirt_utils-for-libvirt-console-tests.patch
+Patch0006: 0006-Fixes-ram_allocation_ratio-based-over-subscription.patch
+Patch0007: 0007-Stop-nova_ipam_lib-from-changing-the-timeout-setting.patch
+Patch0008: 0008-Prevent-file-injection-writing-to-host-filesystem.patch
+Patch0009: 0009-Distinguish-over-quota-for-volume-size-and-number.patch
+Patch0010: 0010-Expose-over-quota-exceptions-via-native-API.patch
+Patch0011: 0011-Fix-call-to-network_get_all_by_uuids.patch
+Patch0012: 0012-fix-libvirt-get_memory_mb_total-with-xen.patch
+Patch0013: 0013-ensure-libguestfs-has-completed-before-proceeding.patch
+Patch0014: 0014-Use-compute_api.get_all-in-affinity-filters.patch
+Patch0015: 0015-fix-metadata-file-injection-with-xen.patch
+Patch0016: 0016-Fixes-affinity-filters-when-hints-is-None.patch
+Patch0017: 0017-Addtional-CommandFilters-to-fix-rootwrap-on-SLES.patch
+Patch0018: 0018-Fix-marker-behavior-for-flavors.patch
+Patch0019: 0019-Use-default-qemu-img-cluster-size-in-libvirt-connect.patch
+Patch0020: 0020-Return-413-status-on-over-quota-in-the-native-API.patch
+Patch0021: 0021-Handle-local-remote-exceptions-consistently.patch
+Patch0022: 0022-libvirt-fix-qcow2-size-on-live-block-migration.patch
+Patch0023: 0023-Backport-fix-for-API-listing-of-os-hosts.patch
+Patch0024: 0024-Avoid-lazy-loading-errors-on-instance_type.patch
+Patch0025: 0025-Avoid-casts-in-network-manager-to-prevent-races.patch
+Patch0026: 0026-Conditionally-allow-queries-for-deleted-flavours.patch
+Patch0027: 0027-Fix-wrong-regex-in-cleanup_file_locks.patch
+Patch0028: 0028-ensure-atomic-manipulation-of-libvirt-disk-images.patch
+Patch0029: 0029-Ensure-we-don-t-access-the-net-when-building-docs.patch
+Patch0030: 0030-fix-useexisting-deprecation-warnings.patch
+Patch0031: 0031-support-a-configurable-libvirt-injection-partition.patch
+Patch0032: 0032-only-mount-guest-image-once-when-injecting-files.patch
+Patch0033: 0033-set-correct-SELinux-context-for-injected-ssh-keys.patch
+Patch0034: 0034-ensure-libguestfs-mounts-are-cleaned-up.patch
+Patch0035: 0035-Adding-networking-rules-to-vm-s-on-compute-service-s.patch
+Patch0036: 0036-Tolerance-when-parsing-null-connection-info-in-BDM.patch
+Patch0037: 0037-Support-EC2-CreateImage-API-for-boot-from-volume.patch
+Patch0038: 0038-EC2-DescribeImages-reports-correct-rootDeviceType.patch
+Patch0039: 0039-Reject-EC2-CreateImage-for-instance-store.patch
+Patch0040: 0040-Fix-EC2-CreateImage-no_reboot-logic.patch
+Patch0041: 0041-use-boto-s-HTTPResponse-class-for-versions-of-boto-2.patch
+Patch0042: 0042-Convert-remaining-network-API-casts-to-calls.patch
+Patch0043: 0043-Moving-where-the-fixed-ip-deallocation-happens.patch
+Patch0044: 0044-fix-the-qpid_heartbeat-option-so-that-it-s-effective.patch
 
 BuildArch:        noarch
 BuildRequires:    intltool
@@ -355,7 +376,6 @@ This package contains documentation files for nova.
 %prep
 %setup -q -n nova-%{version}
 
-%patch0003 -p1
 %patch0004 -p1
 %patch0005 -p1
 %patch0006 -p1
@@ -375,6 +395,28 @@ This package contains documentation files for nova.
 %patch0020 -p1
 %patch0021 -p1
 %patch0022 -p1
+%patch0023 -p1
+%patch0024 -p1
+%patch0025 -p1
+%patch0026 -p1
+%patch0027 -p1
+%patch0028 -p1
+%patch0029 -p1
+%patch0030 -p1
+%patch0031 -p1
+%patch0032 -p1
+%patch0033 -p1
+%patch0034 -p1
+%patch0035 -p1
+%patch0036 -p1
+%patch0037 -p1
+%patch0038 -p1
+%patch0039 -p1
+%patch0040 -p1
+%patch0041 -p1
+%patch0042 -p1
+%patch0043 -p1
+%patch0044 -p1
 
 find . \( -name .gitignore -o -name .placeholder \) -delete
 
@@ -763,6 +805,28 @@ fi
 %endif
 
 %changelog
+* Sun Jul 30 2012 Pádraig Brady <P at draigBrady.com> - 2012.1.1-11
+- Update from stable upstream including...
+- Fix metadata file injection with xen
+- Fix affinity filters when hints is None
+- Fix marker behavior for flavors
+- Handle local remote exceptions consistently
+- Fix qcow2 size on libvirt live block migration
+- Fix for API listing of os hosts
+- Avoid lazy loading errors on instance_type
+- Avoid casts in network manager to prevent races
+- Conditionally allow queries for deleted flavours
+- Fix wrong regex in cleanup_file_locks
+- Add net rules to VMs on compute service start
+- Tolerate parsing null connection info in BDM
+- Support EC2 CreateImage API for boot from volume
+- EC2 DescribeImages reports correct rootDeviceType
+- Reject EC2 CreateImage for instance store
+- Fix EC2 CreateImage no_reboot logic
+- Convert remaining network API casts to calls
+- Move where the fixed ip deallocation happens
+- Fix the qpid_heartbeat option so that it's effective
+
 * Fri Jul 27 2012 Pádraig Brady <P at draigBrady.com> - 2012.1.1-10
 - Split out into more sub packages
 


More information about the scm-commits mailing list