Fix: pass MAC addresses to vagrant to configure interfaces correctly

This commit is contained in:
Dan Williams 2015-07-10 17:12:09 -05:00
parent 6b63db535a
commit 6d92d3a201
2 changed files with 78 additions and 1 deletions

View File

@ -0,0 +1,69 @@
From ee7afab369dc7e80128ff35a2ff11f6eab23d368 Mon Sep 17 00:00:00 2001
From: Dan Williams <dcbw@redhat.com>
Date: Tue, 30 Jun 2015 16:24:30 -0500
Subject: [PATCH] Read MAC address from libvirt and pass up to Vagrant
Configuring networks based solely on slot numbers doesn't work very
well, since there's no way to guarantee that the interface Vagrant
finds is the same one that vagrant-libvirt created at that index.
For example, Vagrant's Fedora configure_networks action does this:
machine.communicate.sudo("ls /sys/class/net | grep -v lo") do |_, result|
interface_names = result.split("\n")
end
interface_names = networks.map do |network|
"#{interface_names[network[:interface]]}"
end
which means that if your image has 'docker' pre-installed, then
interface_names[0] = "docker0" and hilarity ensues, with the first
non-management network being assigned to the vagrant-libvirt
management interface.
Since interface names are very unreliable (they can be renamed by
udev at will or when hardware changes) the only way to ensure that
the interface vagrant-libvirt attaches to the domain maps to the
correct one inside the VM is by MAC address. Pull the MAC address
out of the libvirt config once the interface has been attached and
pass that up to Vagrant so we have a chance of doing the right thing.
---
lib/vagrant-libvirt/action/create_network_interfaces.rb | 17 ++++++++++++++++-
1 file changed, 16 insertions(+), 1 deletion(-)
diff --git a/lib/vagrant-libvirt/action/create_network_interfaces.rb b/lib/vagrant-libvirt/action/create_network_interfaces.rb
index 35886ad..cbe7562 100644
--- a/lib/vagrant-libvirt/action/create_network_interfaces.rb
+++ b/lib/vagrant-libvirt/action/create_network_interfaces.rb
@@ -96,6 +96,21 @@ def call(env)
raise Errors::AttachDeviceError,
:error_message => e.message
end
+
+ # Re-read the network configuration and grab the MAC address
+ if !@mac
+ xml = Nokogiri::XML(domain.xml_desc)
+ if iface_configuration[:iface_type] == :public_network
+ if @type == 'direct'
+ @mac = xml.xpath("/domain/devices/interface[source[@dev='#{@device}']]/mac/@address")
+ else
+ @mac = xml.xpath("/domain/devices/interface[source[@bridge='#{@device}']]/mac/@address")
+ end
+ else
+ @mac = xml.xpath("/domain/devices/interface[source[@network='#{@network_name}']]/mac/@address")
+ end
+ iface_configuration[:mac] = @mac.to_s
+ end
end
# Continue the middleware chain.
@@ -116,7 +131,7 @@ def call(env)
network = {
:interface => slot_number,
:use_dhcp_assigned_default_route => options[:use_dhcp_assigned_default_route],
- #:mac => ...,
+ :mac_address => options[:mac],
}
if options[:ip]

View File

@ -2,7 +2,7 @@
Name: %{vagrant_plugin_name}
Version: 0.0.30
Release: 2%{?dist}
Release: 3%{?dist}
Summary: libvirt provider for Vagrant
Group: Development/Languages
License: MIT
@ -10,6 +10,10 @@ URL: https://github.com/pradels/vagrant-libvirt
Source0: https://rubygems.org/gems/%{vagrant_plugin_name}-%{version}.gem
Source1: 10-vagrant-libvirt.rules
# Pass MAC addresses up to vagrant to ensure interfaces are configured correctly
# https://github.com/pradels/vagrant-libvirt/pull/408
Patch0: vagrant-libvirt-match-interface-by-mac.patch
Requires(pre): shadow-utils
Requires(posttrans): vagrant
Requires(preun): vagrant
@ -50,6 +54,7 @@ gem unpack %{SOURCE0}
gem spec %{SOURCE0} -l --ruby > %{vagrant_plugin_name}.gemspec
%patch0 -p1
%build
gem build %{vagrant_plugin_name}.gemspec
@ -109,6 +114,9 @@ getent group vagrant >/dev/null || groupadd -r vagrant
%changelog
* Fri Jul 10 2015 Dan Williams <dcbw@redhat.com> - 0.0.30-3
- Fix: pass MAC addresses to vagrant to configure interfaces correctly
* Fri Jun 19 2015 Fedora Release Engineering <rel-eng@lists.fedoraproject.org> - 0.0.30-2
- Rebuilt for https://fedoraproject.org/wiki/Fedora_23_Mass_Rebuild