Skip to content

Commit 6c3d5de

Browse files
author
Dmitriy Rabotyagov
committed
Ensure MAC addresses characters are in the same case
Currently neutron can report ports to have MAC addresses in upper case when they're created like that. In the meanwhile libvirt configuration file always stores MAC in lower case which leads to KeyError while trying to retrieve migrate_vif. Closes-Bug: #1945646 Change-Id: Ie3129ee395427337e9abcef2f938012608f643e1 (cherry picked from commit 6a15169) (cherry picked from commit 63a6388)
1 parent 1edabab commit 6c3d5de

File tree

2 files changed

+51
-3
lines changed

2 files changed

+51
-3
lines changed

nova/tests/unit/virt/libvirt/test_migration.py

Lines changed: 42 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -948,7 +948,48 @@ def test_update_vif_xml_no_matching_vif(self):
948948
doc = etree.fromstring(original_xml)
949949
ex = self.assertRaises(KeyError, migration._update_vif_xml,
950950
doc, data, get_vif_config)
951-
self.assertIn("CA:FE:DE:AD:BE:EF", str(ex))
951+
self.assertIn("ca:fe:de:ad:be:ef", str(ex))
952+
953+
def test_update_vif_xml_lower_case_mac(self):
954+
"""Tests that the vif in the migrate data is not found in the existing
955+
guest interfaces.
956+
"""
957+
conf = vconfig.LibvirtConfigGuestInterface()
958+
conf.net_type = "bridge"
959+
conf.source_dev = "qbra188171c-ea"
960+
conf.target_dev = "tapa188171c-ea"
961+
conf.mac_addr = "DE:AD:BE:EF:CA:FE"
962+
conf.model = "virtio"
963+
original_xml = """<domain>
964+
<uuid>3de6550a-8596-4937-8046-9d862036bca5</uuid>
965+
<devices>
966+
<interface type="bridge">
967+
<mac address="de:ad:be:ef:ca:fe"/>
968+
<model type="virtio"/>
969+
<source bridge="qbra188171c-ea"/>
970+
<target dev="tapa188171c-ea"/>
971+
<virtualport type="openvswitch">
972+
<parameters interfaceid="%s"/>
973+
</virtualport>
974+
<address type='pci' domain='0x0000' bus='0x00' slot='0x04'
975+
function='0x0'/>
976+
</interface>
977+
</devices>
978+
</domain>""" % uuids.ovs
979+
expected_xml = """<domain>
980+
<uuid>3de6550a-8596-4937-8046-9d862036bca5</uuid>
981+
<devices>
982+
<interface type="bridge">
983+
<mac address="DE:AD:BE:EF:CA:FE"/>
984+
<model type="virtio"/>
985+
<source bridge="qbra188171c-ea"/>
986+
<target dev="tapa188171c-ea"/>
987+
<address type='pci' domain='0x0000' bus='0x00' slot='0x04'
988+
function='0x0'/>
989+
</interface>
990+
</devices>
991+
</domain>"""
992+
self._test_update_vif_xml(conf, original_xml, expected_xml)
952993

953994

954995
class MigrationMonitorTestCase(test.NoDBTestCase):

nova/virt/libvirt/migration.py

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -339,14 +339,21 @@ def _update_vif_xml(xml_doc, migrate_data, get_vif_config):
339339
instance_uuid = xml_doc.findtext('uuid')
340340
parser = etree.XMLParser(remove_blank_text=True)
341341
interface_nodes = xml_doc.findall('./devices/interface')
342-
migrate_vif_by_mac = {vif.source_vif['address']: vif
342+
# MAC address stored for port in neutron DB and in domain XML
343+
# might be in different cases, so to harmonize that
344+
# we convert MAC to lower case for dict key.
345+
migrate_vif_by_mac = {vif.source_vif['address'].lower(): vif
343346
for vif in migrate_data.vifs}
344347
for interface_dev in interface_nodes:
345348
mac = interface_dev.find('mac')
346349
mac = mac if mac is not None else {}
347350
mac_addr = mac.get('address')
348351
if mac_addr:
349-
migrate_vif = migrate_vif_by_mac[mac_addr]
352+
# MAC address stored in libvirt should always be normalized
353+
# and stored in lower case. But just to be extra safe here
354+
# we still normalize MAC retrieved from XML to be absolutely
355+
# sure it will be the same with the Neutron provided one.
356+
migrate_vif = migrate_vif_by_mac[mac_addr.lower()]
350357
vif = migrate_vif.get_dest_vif()
351358
# get_vif_config is a partial function of
352359
# nova.virt.libvirt.vif.LibvirtGenericVIFDriver.get_config

0 commit comments

Comments
 (0)