Altibox now supports native IPv6 and IPv4 stacks and gone are the days of dealing with IPv6 rapid deployment otherwise abbreviated as 6rd. Here is my updated config for my Mikrotik router using IPv6 dhcp-client instead of 6rd.
In my previous article Altibox IPv6 with 6to4 we needed to pre-plan IPv6 addresses based on our IPv4 address before connecting. By using native IPv6 DHCP client we can skip all that and just set up a ipv6-client and then do address planning after we get our prefix delegation via the client.
Altibox provides a webpage explaining their support for IPv6 and the main message is that you need to start a dhcp-client on your router to get IPv6 prefix delegations. https://wiki.mikrotik.com/Manual:IPv6/DHCP_Client
Enabling the IPv6 DHCP Client
Let’s start by putting the Altibox central in Bridge Mode. More info from Altibox here.
Note: Using your own router without the Altibox central is out of scope for this article.
Setting up a dhcp-client is pretty straight forward. We start by assigning the first address we get from the prefix delegation on our bridge
interface and secondly create a dhcp-client on our ether1
which is my WAN port. We also add-default-route
, give the dynamic addres pool a name and hinting that we want a ::/56
block delegation. Lastly we are asking that the dhcp-client should handle address and prefix delgation and that we won’t be using the ISPs DNS’es.
# Add the first address from the prefix that will be delegated to us
/ipv6 address
add address=::1 from-pool=ipv6-pd interface=bridge
# Start the dhcp-client
/ipv6 dhcp-client
add add-default-route=yes comment="Altibox pd" interface=ether1 pool-name=ipv6-pd prefix-hint=::/56 request=address,prefix use-peer-dns=no
Then we activate neighbour discovery and configure the defaults for the prefix.
/ipv6 nd
set [ find default=yes ] mtu=1480
/ipv6 nd prefix default
set autonomous=yes preferred-lifetime=1w valid-lifetime=4w2d
Verifying connectivity
Please note: I have replaced parts of the addresses with
cafe
,b00b
orbabe
for masking parts of the real addresses. I also like silly stuff and playing with the words that you can create in your ipv6 addressing. IPv6 addresses use hexadecimal notation ranging from 0-9 and a-f.
Let’s investigate our address and prefix delegation from Altibox. We can see that our delegation prefix is 2a01:799:192:cafe::/56
and our router’s address is 2a01:798:100:600:b5b5:70e4:f0f0:b00b
/ipv6/dhcp-client print
Columns: INTERFACE, STATUS, REQUEST, PREFIX, ADDRESS
# INTERFACE STATUS REQUEST PREFIX ADDRESS
;;; Altibox pd
0 ether1 bound address 2a01:799:192:cafe::/56, 6h28m32s 2a01:798:100:600:b5b5:70e4:f0f0:b00b, 6h28m32s
prefix
# Print more detail for the same connection. I mangled with the output for better readability
/ipv6/dhcp-client/print detail
Flags: D - dynamic; X - disabled, I - invalid
0 ;;; Altibox pd
interface=ether1 status=bound duid="0x000b00b0cafe" dhcp-server-v6=fe80::201:3ff:babe:1
request=address,prefix add-default-route=yes default-route-distance=1 use-peer-dns=no
allow-reconfigure=no dhcp-options="" pool-name="ipv6-pd" pool-prefix-length=64
prefix-hint=::/56 prefix-address-lists="" dhcp-options=""
prefix=2a01:799:192:cafe::/56, 6h11m20s address=2a01:798:100:600:b5b5:70e4:f0f0:b00b, 6h11m20s
# print out ipv6 addresses
/ipv6/address print
Flags: D - DYNAMIC; G - GLOBAL, L - LINK-LOCAL
Columns: ADDRESS, FROM-POOL
# ADDRESS FROM-POOL
0 D ::1/128
1 DG 2a01:798:100:600:b5b5:70e4:f0f0:b00b/128
2 G 2a01:799:192:cafe::1/64 ipv6-pd
# print out the ipv6 routes
/ipv6/route/print
Flags: D - DYNAMIC; I - INACTIVE, A - ACTIVE; c - CONNECT, d - DHCP; H - HW-OF>
Columns: DST-ADDRESS, GATEWAY, DISTANCE
DST-ADDRESS GATEWAY D
DAd ::/0 fe80::201:3ff:babe:1%ether1 1
DAd 2a01:799:192:cafe::/56 1
DAc 2a01:799:192:cafe::/64 bridge 0
Pingtest on the router
Perform a ping test directly on the router. Please note the nuance of using the ping [:resolve some.ipv6host.tld]
notation when pinging ipv6 addresses.
/ping [:resolve ipv6.google.com]
SEQ HOST SIZE TTL TIME STATUS
0 2a00:1450:400f:801::200e 56 61 8ms770us echo reply
1 2a00:1450:400f:801::200e 56 61 8ms838us echo reply
2 2a00:1450:400f:801::200e 56 61 8ms869us echo reply
3 2a00:1450:400f:801::200e 56 61 8ms864us echo reply
sent=4 received=4 packet-loss=0% min-rtt=8ms770us avg-rtt=8ms835us max-rtt=8ms869us
Testing on your computer
You can test through your browser and here are some examples:
Example of pinging from a linux or a mac with the ping6
command.
ping6 -c 4 ipv6.google.com
PING ipv6.google.com (2a00:1450:400f:801::200e) 56 data bytes
64 bytes from arn09s22-in-x0e.1e100.net (2a00:1450:400f:801::200e): icmp_seq=1 ttl=60 time=9.46 ms
64 bytes from arn09s22-in-x0e.1e100.net (2a00:1450:400f:801::200e): icmp_seq=2 ttl=60 time=24.1 ms
64 bytes from arn09s22-in-x0e.1e100.net (2a00:1450:400f:801::200e): icmp_seq=3 ttl=60 time=39.4 ms
64 bytes from arn09s22-in-x0e.1e100.net (2a00:1450:400f:801::200e): icmp_seq=4 ttl=60 time=32.5 ms
--- ipv6.google.com ping statistics ---
4 packets transmitted, 4 received, 0% packet loss, time 3005ms
rtt min/avg/max/mdev = 9.459/26.360/39.374/11.159 ms
Testing traceroute with the traceroute6
utility
$ traceroute6 nrk.no
traceroute to nrk.no (2a02:26f0:4300::1724:4cf8), 30 hops max, 80 byte packets
1 router.samueljon.tech (2a01:799:192:cafe::1) 0.836 ms 1.164 ms 2.244 ms
2 * * *
3 g2a02-26f0-4300-0000-0000-0000-1724-4cf8.deploy.static.akamaitechnologies.com (2a02:26f0:4300::1724:4cf8) 5.013 ms 5.138 ms 5.489 ms
Delegating /64 subnets from the /56 delegation
Key Points in IPv6 Addressing
- An IPv6 address has 128 bits.
- A /56 prefix means the first 56 bits are fixed, leaving 72 bits available for subnetting and hosts.
- A /64 subnet is standard for most IPv6 configurations, leaving 64 bits for host addressing.
Subnetting Calculation
- To go from a /56 to a /64, you are adding 8 bits to define the subnet.
- With these 8 bits, you can create 2^8 subnets.
- 2^8=256 subnets.
This means you can create 256 unique /64 subnets from a single /56 prefix. Each /64 subnet can then support 2^64−1 unique host addresses.
We can use the ipv6calc
tool to get more insights on the prefix as shown below.
The
ipv6calc
is an open-source software that you can install on your *nix machine with the corresponding package manager. I did this on a Mac OSX machine and did install it via homebrewbrew install ipv6calc
subnetcalc 2a01:799:192:cafe::/56
Address = 2a01:799:192:cafe::
2a01 = 00101010 00000001
0799 = 00000111 10011001
0192 = 00000001 10010010
cafe = 11001010 11111110
0000 = 00000000 00000000
0000 = 00000000 00000000
0000 = 00000000 00000000
0000 = 00000000 00000000
Network = 2a01:799:192:ca00:: / 56
Netmask = ffff:ffff:ffff:ff00::
Wildcard Mask = ::ff:ffff:ffff:ffff:ffff
Hosts Bits = 72
Max. Hosts = 2^72 - 1
Host Range = { 2a01:799:192:ca00::1 - 2a01:799:192:caff:ffff:ffff:ffff:ffff }
Properties =
- 2a01:799:192:cafe:: is a HOST address in 2a01:799:192:ca00::/56
- Global Unicast Properties:
+ Interface ID = 0000:0000:0000:0000
+ Sol. Node MC = ff02::1:ff00:0000
DNS Hostname = (Name or service not known)
Here we can see that the allocation consists of the following range:
2a01:799:192:ca00::1 - 2a01:799:192:caff:ffff:ffff:ffff:ffff
Here are some funny /64 prefixes derived from the 2a01:799:192:cafe::/56 prefix delegation.
2a01:799:192:cafe:babe::/64 # Playful nod to "babe."
2a01:799:192:cafe:b00b::/64 # A cheeky reference with "b00b."
2a01:799:192:cafe:f00d::/64 # Perfect for a foodie subnet, referencing "food."
2a01:799:192:cafe:dead::/64 # For the dark humor crowd: "dead."
2a01:799:192:cafe:beef::/64 # A fun choice, "beef" for tech-savvy carnivores.
2a01:799:192:cafe:c0de::/64 # Nerdy and coding-themed: "code."
2a01:799:192:cafe:baad::/64 # "Bad" in leetspeak for a subnet with a mischievous reputation.
2a01:799:192:cafe:face::/64 # Playful and memorable with "face."
2a01:799:192:cafe:feed::/64 # For an infrastructure feeding data or services: "feed."
2a01:799:192:cafe:cafe::/64 # Classic redundancy and humor: "cafe" in the "cafe" delegation.
2a01:799:192:cafe:bead::/64 # Perfect for a creative arts subnet.
2a01:799:192:cafe:b055::/64 # For the boss: "boss."
2a01:799:192:cafe:b33r::/64 # For the after-hours network: "beer."
2a01:799:192:cafe:d00d::/64 # Friendly and casual: "dude."
If you want to delegate /64 prefixes to other vlans or interfaces you can see some of my previus post on ipv6. You can use the
ipv6
tag in the sidebar on the main page to find relevant articles.
Firewall configuration
It is possible that these rules are already in your router since these are the default ipv6 rules that come as default.
/ipv6 firewall address-list
add address=::/128 comment="defconf: unspecified address" list=bad_ipv6
add address=::1/128 comment="defconf: lo" list=bad_ipv6
add address=fec0::/10 comment="defconf: site-local" list=bad_ipv6
add address=::ffff:0.0.0.0/96 comment="defconf: ipv4-mapped" list=bad_ipv6
add address=::/96 comment="defconf: ipv4 compat" list=bad_ipv6
add address=100::/64 comment="defconf: discard only " list=bad_ipv6
add address=2001:db8::/32 comment="defconf: documentation" list=bad_ipv6
add address=2001:10::/28 comment="defconf: ORCHID" list=bad_ipv6
add address=3ffe::/16 comment="defconf: 6bone" list=bad_ipv6
add address=::224.0.0.0/100 comment="defconf: other" list=bad_ipv6
add address=::127.0.0.0/104 comment="defconf: other" list=bad_ipv6
add address=::/104 comment="defconf: other" list=bad_ipv6
add address=::255.0.0.0/104 comment="defconf: other" list=bad_ipv6
/ipv6 firewall filter
add action=accept chain=input comment="defconf: accept established,related,untracked" connection-state=established,related,untracked
add action=drop chain=input comment="defconf: drop invalid" connection-state=invalid
add action=drop chain=input dst-port=53 in-interface=!LAN protocol=tcp
add action=drop chain=input dst-port=53 in-interface=!LAN protocol=udp
add action=accept chain=input comment="defconf: accept ICMPv6" protocol=icmpv6
add action=accept chain=input comment="defconf: accept UDP traceroute" port=33434-33534 protocol=udp
add action=accept chain=input comment="defconf: accept DHCPv6-Client prefix delegation." dst-port=546 protocol=udp src-address=fe80::/10
add action=accept chain=input comment="defconf: accept IKE" dst-port=500,4500 protocol=udp
add action=accept chain=input comment="defconf: accept ipsec AH" protocol=ipsec-ah
add action=accept chain=input comment="defconf: accept ipsec ESP" protocol=ipsec-esp
add action=accept chain=input comment="defconf: accept all that matches ipsec policy" ipsec-policy=in,ipsec
add action=drop chain=input comment="defconf: drop everything else not coming from LAN" in-interface-list=!LAN
add action=accept chain=forward comment="defconf: accept established,related,untracked" connection-state=established,related,untracked
add action=drop chain=forward comment="defconf: drop invalid" connection-state=invalid
add action=drop chain=forward comment="defconf: drop packets with bad src ipv6" src-address-list=bad_ipv6
add action=drop chain=forward comment="defconf: drop packets with bad dst ipv6" dst-address-list=bad_ipv6
add action=drop chain=forward comment="defconf: rfc4890 drop hop-limit=1" hop-limit=equal:1 protocol=icmpv6
add action=accept chain=forward comment="defconf: accept ICMPv6" protocol=icmpv6
add action=accept chain=forward comment="defconf: accept HIP" protocol=139
add action=accept chain=forward comment="defconf: accept IKE" dst-port=500,4500 protocol=udp
add action=accept chain=forward comment="defconf: accept ipsec AH" protocol=ipsec-ah
add action=accept chain=forward comment="defconf: accept ipsec ESP" protocol=ipsec-esp
add action=accept chain=forward comment="defconf: accept all that matches ipsec policy" ipsec-policy=in,ipsec
add action=drop chain=forward comment="defconf: drop everything else not coming from LAN" in-interface-list=!LAN
Credits
Added 2024.12.01: Post from Nils Norman Haukås on the same topic but using different type of router.
Added 2024.12.28: Github link to trrunde’s routerconfig.
Photo by Christopher Burns on Unsplash