VirtualBox has a bug where the IPv6 route is lost on every other configuration of a host-only network. This is also triggered when a VM is booted. To fix this, we test the route-ability of all IPv6 networks, and reconfigure if necessary. This is very fast but we still only do this if we have any IPv6 networks.
65 lines
1.9 KiB
Ruby
65 lines
1.9 KiB
Ruby
require "ipaddr"
|
|
require "socket"
|
|
|
|
require "log4r"
|
|
|
|
require "vagrant/util/scoped_hash_override"
|
|
|
|
module VagrantPlugins
|
|
module ProviderVirtualBox
|
|
module Action
|
|
# This middleware works around a bug in VirtualBox where booting
|
|
# a VM with an IPv6 host-only network will someties lose the
|
|
# route to that machine.
|
|
class NetworkFixIPv6
|
|
include Vagrant::Util::ScopedHashOverride
|
|
|
|
def initialize(app, env)
|
|
@logger = Log4r::Logger.new("vagrant::plugins::virtualbox::network")
|
|
@app = app
|
|
end
|
|
|
|
def call(env)
|
|
@env = env
|
|
|
|
# Determine if we have an IPv6 network
|
|
has_v6 = false
|
|
env[:machine].config.vm.networks.each do |type, options|
|
|
next if type != :private_network
|
|
options = scoped_hash_override(options, :virtualbox)
|
|
next if options[:ip] == ""
|
|
if IPAddr.new(options[:ip]).ipv6?
|
|
has_v6 = true
|
|
break
|
|
end
|
|
end
|
|
|
|
# Call up
|
|
@app.call(env)
|
|
|
|
# If we have no IPv6, forget it
|
|
return if !has_v6
|
|
|
|
# We do, so fix them if we must
|
|
env[:machine].provider.driver.read_host_only_interfaces.each do |interface|
|
|
# Ignore interfaces without an IPv6 address
|
|
next if interface[:ipv6] == ""
|
|
|
|
# Make the test IP. This is just the highest value IP
|
|
ip = IPAddr.new(interface[:ipv6])
|
|
ip |= IPAddr.new(":#{":FFFF" * (interface[:ipv6_prefix].to_i / 16)}")
|
|
|
|
@logger.info("testing IPv6: #{ip}")
|
|
begin
|
|
UDPSocket.new(Socket::AF_INET6).connect(ip.to_s, 80)
|
|
rescue Errno::EHOSTUNREACH
|
|
@logger.info("IPv6 host unreachable. Fixing: #{ip}")
|
|
env[:machine].provider.driver.reconfig_host_only(interface)
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|