Experimenting with an IPv6 network that coexists with IPv4
In this experiment you'll setup your first IPv6 network to live alongside your IPv4 legacy network. I'm assuming you've already worked with the experiments in the first two blog posts in this series. We're going to demonstrate the principle behind Dual Stack networking and prove to ourselves that running an IPv6 network alongside an IPv4 network is no big deal.
First, grab those few machines that you had on the isolated IPv6 experiment network. Fold them back into your network the way that they always were. Let them reclaim their old IPv4 addresses. (I'll assume that they're in RFC-1918 space, since this series is aimed at the hobbyist-home-user.) Now go to each of them in turn and dynamicall re-assign their IPv6 addresses via the command line.
Once you do, run an ifconfig em0
for example. The output should then look
something like this:
% ifconfig em0
em0: flags=1008843<UP,BROADCAST,RUNNING,SIMPLEX,MULTICAST,LOWER_UP> metric 0 mtu 1500
options=8209b<RXCSUM,TXCSUM,VLAN_MTU,VLAN_HWTAGGING,VLAN_HWCSUM,WOL_MAGIC,LINKSTATE>
ether 10:20:30:40:50:60
inet 10.1.10.42 netmask 0xffffff00 broadcast 10.1.10.255
inet6 fe80::1220:30ff:fe40:5060%em0 prefixlen 64 scopeid 0x1
inet6 fd01:2:3:4:5:6:7:c prefixlen 112
media: Ethernet autoselect (1000baseT <full-duplex>)
status: active
Once a few machines are up like this, you should be able to ping
them on both
their 4 address and their 6 address. (Ignore the fe80::
IPv6 address on the
card for the moment. We'll come back to that in another blog post. For now, don't mess with these
addresses or try to ping
them or SSH to them.) If ping
s work you should be
able to SSH to them too. On both their legacy network addresses and the shiny
new IPv6 addresses you gave them. Don't worry too much about coming up with a
good IPv6 address plan for your experimental network. You're going to throw
this one away. Just keep it simple.
When SSHing to various machines, you can run echo $SSH_CLIENT
and it will
print the source address of your connection. Verify that connections to
IPv6 addresses come from the expected IPv6 source and the same for IPv4.
You should be able to do all of this without impacting any network traffic
for machines not participating in these experiments. For those which are
participating, they should be unaffected as well, but some operating systems
have some quirks with reaching the wider internet when there's local IPv6
that can't reach the internet. This is a transition step, of course...
so we'll deal with that a bit later.
Now you've gotten a few hosts to converse via Modern IP and in a way that's integrated with your existing infrastructure. Congratulations. You're now running a dual-stack network. Dual-stack networks are an important part of the IPv6 transition strategy. Any plan which has to upgrade nodes that only speak IPv4 to be able to continue speaking classic IPv4 with still-un-upgraded nodes but speak some enhancement or another with each other would have to go through this state.
Dual-stack explicitly doesn't map IPv4 into any part of the IPv6 address space. If it did, there's no benefit. The altered packet header cannot be understood by IPv4 legacy hosts, and thus legacy packets would have to always be sent to any host in the "might not speak IPv6" range, because it cannot be known what they speak. Any effort which is surmised as "we need to go around to them all and teach them the new address space" is precisely the same task that IPv6 deployment has been trying to accomplish for three decades, now.
Keeping the two stacks entirely separate is the cleanest way to handle this. But they can coexist in the same physical network, just like we've setup now. Over time, more traffic should be routed over the new IPv6 space. As flows move from legacy to modern IP, the legacy IP space becomes ever more irrelevant. Already (as of 2023) on the wider internet, the majority of the traffic being carried is over IPv6, not IPv4. This trend is going to continue, and it seems to be slightly accelerating. The IPv4 shortage/endgame is forcing more and more traffic towards IPv6.
So, how does this affect our experiment? Well, the days of talking to hosts
by IP address are long in the past. These days we use DNS on the wider
network, and for home networks we either use DNS or /etc/hosts
files.
Names are fantastic tools for migration to Modern IP. We can associate
a name with an address in both IPv4 and IPv6, when that host is running
dual-stack. Any host running legacy-only will decline to ask what the
IPv6 address of a host is. For dual-stack hosts that want to talk to
other dual stack hosts, they can choose whether to talk over IPv4 or
IPv6 -- there's a set of algorithms to determine which to use. (Someday I'll write
a blog post ranting about that algorithm, "Happy Eyeballs".) And for IPv6-only
hosts (a growing number, online), they're stuck with the opposite problem
to IPv4 only hosts. However, there are some migration tools which permit
mapping parts or all of IPv4 space into IPv6 space -- all under the control
of the network administrator of that 6-only site.
So let's make our experimental dual-stack network have IPv6 mappings for our names.
Suppose this is your /etc/hosts
file on all of your machines:
127.0.0.1 localhost
10.1.10.22 ssh-server
10.1.10.30 build-server
10.1.10.80 webhost
10.1.10.99 workstation
We can modernize it thus:
127.0.0.1 localhost
10.1.10.22 ssh-server
10.1.10.30 build-server
10.1.10.80 webhost
10.1.10.99 workstation
# IPv6 names:
::1 localhost # This is probably already in your hosts file!
fd01:2:3:4:5:6:7:22 ssh-server
fd01:2:3:4:5:6:7:30 build-server
fd01:2:3:4:5:6:7:80 webhost
fd01:2:3:4:5:6:7:99 workstation
# Note that although the human-readable digits in the last group
# match between IPv4 and IPv6, they're not the same bit pattern.
# This is perfectly acceptable. There's no requirement for similarity of
# addresses between the two protocols for the same machine.
You should run a DNS server -- gossiping around versions of hosts files is tedious, error prone, and painful. If you run a DNS server (I hope you do!), you might augment your zone file thus:
; ...
ssh-server IN A 10.1.10.22
build-server IN A 10.1.10.30
webhost IN A 10.1.10.80
workstation IN A 10.1.10.99
; Add additional `AAAA` records for the 6-enabled hosts.
; These can be interlaced with A records for better readability,
; if desired.
ssh-server IN AAAA fd01:2:3:4:5:6:7:22
build-server IN AAAA fd01:2:3:4:5:6:7:30
webhost IN AAAA fd01:2:3:4:5:6:7:80
workstation IN AAAA fd01:2:3:4:5:6:7:99
Once your host names are available to all machines, you'll find that legacy-only hosts just don't care about this change. And your new dual-stack hosts will automatically start to try to talk more 6 with each other. You should be able to run your network for days like this. You may find that the dual stack hosts have slower global internet response time due to trying to talk IPv6 globally but being unable to do so.
Most of those issues have been resolved for most operating systems, but it was the leading cause for why the terrible advice "disable IPv6 to fix connection problems" was promulgated and actually "seemed to work". We're not going to turn off IPv6. At least not permanently. For any machine which is having some problems, it's fine to reboot it such that it doesn't have an IPv6 address anymore. (Remember that we manually provisioned these addresses for these machines after they booted. So there should be no permanent static IPv6 assignment. You may wish to remove the IPv6 hosts file entries or DNS entries for machines you've had to disable IPv6 on. We'll get to re-enabling it, though.)