Skip to main content
RunBook Academy

VyOSXI · IPv6IPv6

IPv6 addressing — global unicast, ULA, link-local, multicast, anycast, prefix delegation

Foundation⏱ ~18 minset interfaces ethernet eth0 ipv6 addressshow ipv6ip -6 addr showip -6 route showvyos

What you'll learn

  • Distinguish global unicast, ULA, link-local, multicast, and anycast by prefix
  • Allocate a /48 site prefix and carve /64 subnets for production VLANs
  • Configure global unicast and link-local on a VyOS interface
  • Recognise the address-type errors that surface as routing incidents

Prerequisites

Verified against VyOS 1.5.x LTS (circinus) · VyOS 1.4.x (sagitta) — legacy · FRRouting 10.x (VyOS 1.5) · Linux kernel 6.6 LTS (VyOS 1.5 base) · strongSwan 5.9.x (IPsec) · WireGuard 1.0.x (kernel module + userspace tooling) · 2026-08-15

Not yet marked complete on this device.

IPv6 addressing — global unicast, ULA, link-local, multicast, anycast, prefix delegation

A production IPv6 deployment uses every address type the protocol defines, each for a specific job. Global unicast carries public traffic. ULA (Unique Local Addresses) numbers internal infrastructure without colliding with the public internet. Link-local addresses are the on-wire identifiers every interface needs. Multicast replaces broadcast and reaches specific scopes. Anycast picks the nearest of a set of receivers. Prefix delegation lets the upstream hand the downstream a block to subnet.

A routing engineer who treats IPv6 as “bigger IPv4 with /64 everywhere” misses the structure. Each address type has rules about where it can be routed, where it can be the source or destination of a packet, and how it interacts with firewall and NAT policy.

The IPv6 address space at a glance

flowchart TB
  subgraph ALL["::/0 - the entire IPv6 space"]
    direction LR
    GLB["2000::/3<br/>Global Unicast<br/>public, globally routable"]
    ULA["fc00::/7<br/>Unique Local<br/>fc00::/8 + fd00::/8<br/>internal, not routed on the public internet"]
    LL["fe80::/10<br/>Link-Local<br/>on-link only, never routed"]
    MC["ff00::/8<br/>Multicast<br/>one-to-many or many-to-many"]
    LG["::/3 - ::/4<br/>Reserved / Unallocated"]
  end

The rest of the space — everything outside these blocks — is reserved, unallocated, or used for special purposes (loopback ::1/128, unspecified ::/128, documentation prefixes 2001:db8::/32, IPv4-mapped ::ffff:0:0/96, discard 100::/64).

Global Unicast in a production estate

flowchart LR
  A[IANA<br/>allocates] --> B[RIR<br/>e.g. RIPE]
  B --> C[LIR / ISP<br/>/32 or /48]
  C --> D[Enterprise site<br/>/48]
  D --> E[VLAN 10<br/>2001:db8:1::/64]
  D --> F[VLAN 20<br/>2001:db8:2::/64]
  D --> G[VLAN 30<br/>2001:db8:3::/64]

A site gets a /48 from its upstream. Inside the /48, the operator carves /64s — one per subnet, one per VLAN. The /64 is the natural unit of IPv6 subnetting because SLAAC and most IPv6 autoconfiguration mechanisms depend on the interface ID being 64 bits wide.

A /48 contains 65536 /64s. That is enough subnets for any realistic production estate without further summarisation.

set interfaces ethernet eth0 ipv6 address '2001:db8:1::1/64'
set interfaces ethernet eth1 ipv6 address '2001:db8:2::1/64'
set interfaces ethernet eth2 ipv6 address '2001:db8:3::1/64'
commit
save

Unique Local Addresses (ULA) — internal numbering

ULA is the right answer when the operator wants stable internal addresses that do not depend on the upstream prefix. If the operator changes ISP, the public prefix changes but the ULA prefix stays. Internal services keep their URLs.

flowchart LR
  A[Generate /48 with random global ID] --> B[fd00:1234:5678::/48]
  B --> C[Server farm /64<br/>fd00:1234:5678:1::/64]
  B --> D[Management /64<br/>fd00:1234:5678:2::/64]
  B --> E[Lab /64<br/>fd00:1234:5678:3::/64]

The global ID is a random 40-bit value that makes a ULA /48 collision-free in practice. A common generator:

python3 -c "import random; print('fd' + ''.join(random.choice('0123456789abcdef') for _ in range(10)))"

This produces a candidate global ID. Real generators that implement RFC 4193 use /dev/urandom and produce a fd followed by 10 hex characters.

set interfaces ethernet eth0 ipv6 address 'fd00:1234:5678:1::1/64'
set interfaces ethernet eth1 ipv6 address 'fd00:1234:5678:2::1/64'
commit
save

ULA must not be advertised to the public internet. A common mistake is to redistribute a ULA prefix into BGP and have it leak upstream; the upstream’s prefix-list blocks /32 of fc00::/8 and the operator’s traffic blackholes.

Every IPv6 interface automatically assigns itself a link-local address from fe80::/10. The interface identifier is built from the MAC (EUI-64) or from a random number (addrgenmode=random, default in modern kernels for privacy).

vyos@vyos:~$ show ipv6
  Interface        Address
  ---------        -------
  eth0             2001:db8:1::1/64
  eth0             fe80::5054:ff:fe12:3456/64

The VyOS operator rarely sets a link-local explicitly. It is always present. The exception is when the operator needs a stable link-local for a routing-protocol configuration — in which case the operator sets a “router-advert” link-local or overrides EUI-64:

set interfaces ethernet eth0 ipv6 address 'fe80::1/64'
commit
save

The fe80::/64 notation is allowed; the operator is choosing the interface ID ::1 instead of letting EUI-64 generate one. This is the typical pattern for the VyOS box that wants its upstream router to learn a predictable next-hop.

Multicast — replacing broadcast

IPv6 has no broadcast. Every “send to everyone” use case is expressed as a multicast to a well-known group. Multicast addresses start with ff.

flowchart TB
  subgraph M["ff00::/8 - Multicast"]
    F1["ff02::1<br/>All nodes (link-local)"]
    F2["ff02::2<br/>All routers (link-local)"]
    F3["ff02::1:ffXX:XXXX<br/>Solicited-node<br/>last 24 bits of target unicast"]
    F4["ff05::2<br/>All routers (site-local)"]
    F5["ff0e::/16<br/>Global multicast<br/>e.g. NTP, mDNS"]
  end

A host joins the solicited-node multicast group for every unicast address it has. Joining means the kernel installs a multicast filter on the NIC, so the host only processes packets destined for groups it has joined. When Host A wants the MAC for 2001:db8:1::5, Host A sends the NS to ff02::1:ff00:5; only the host whose address ends in ::5 listens to that group, and only that host processes the NS.

Multicast scope is encoded in the second-lowest-order nibble:

  • ff01 — interface-local (loopback only)
  • ff02 — link-local (the segment)
  • ff05 — site-local (the routing domain)
  • ff0e — global (the internet)

VyOS subscribes to the relevant scopes for each protocol it runs. OSPFv3 joins ff02::5 (all-OSPF-routers) and ff02::6 (all-OSPF-designated-routers). BGP does not use multicast (it uses TCP over a unicast destination).

Anycast — one-to-nearest

Anycast addresses are syntactically identical to unicast addresses but are advertised by multiple routers. The network delivers the packet to the nearest instance (by routing metric). Use cases:

  • DNS root servers (each root is 2001:503:ba3e::2:30 from anycast)
  • DNS resolvers (an ISP anycasts its resolver across the globe)
  • Service discovery (an internal anycast VIP for the closest proxy)
set interfaces ethernet eth0 ipv6 address '2001:db8:99::1/64'
set protocols static route '2001:db8:99::1/128' interface eth0

The operator advertises the /128 from multiple routers. BGP selects the nearest. The operator must advertise only the /128 and not a covering prefix that would attract traffic for hosts that are not part of the anycast service.

Prefix Delegation — handing subnets to downstream

sequenceDiagram
  autonumber
  participant ISP as ISP router
  participant CPE as Customer VyOS
  participant LAN as LAN hosts

  ISP->>CPE: RA with prefix 2001:db8:abcd::/48
  CPE->>ISP: DHCPv6 Solicit with IA_PD
  ISP-->>CPE: DHCPv6 Advertise with IA_PD 2001:db8:abcd::/48
  CPE->>ISP: DHCPv6 Request
  ISP-->>CPE: DHCPv6 Reply
  Note over CPE: assigns 2001:db8:abcd:0::/64 to LAN1<br/>2001:db8:abcd:1::/64 to LAN2
  LAN->>CPE: SLAAC or DHCPv6 to learn address

Prefix delegation (PD) is how the upstream hands the downstream a block to subnet. The downstream asks for a prefix via DHCPv6 IA_PD (Identity Association for Prefix Delegation), receives a /48 (typical) or a /56 (smaller sites), and carves /64s for its LANs.

set interfaces ethernet eth0 dhcpv6-options parameters 1
set interfaces ethernet eth0 dhcpv6-options pd 0 length 56
set interfaces ethernet eth0 dhcpv6-options pd 0 interface eth1 prefix ::1/64
set interfaces ethernet eth0 dhcpv6-options pd 0 interface eth2 prefix ::1/64
commit
save

The VyOS asks for a /56 prefix delegation, then assigns ::1/64 from that prefix to LAN interfaces eth1 and eth2. The lesson vyos-xi-04-dhcpv6 covers PD in depth.

How the address configuration is applied

configure
set interfaces ethernet eth0 ipv6 address '2001:db8:1::1/64'
set interfaces ethernet eth0 ipv6 address 'fd00:1234:5678:1::1/64'
set interfaces ethernet eth1 ipv6 address '2001:db8:2::1/64'
set interfaces ethernet eth1 ipv6 address 'fe80::1/64'
commit
save

A single interface can have multiple IPv6 addresses. The kernel and FRR treat each as a separate source. The operator typically configures:

  • A GUA on every interface that needs to be reachable from the public internet
  • A ULA on internal-only interfaces
  • An explicit or auto link-local on every interface

How the result is validated

show ipv6
show interfaces ethernet eth0
ip -6 addr show
ip -6 route show
ping6 2001:db8:1::1
ping6 fd00:1234:5678:1::1
traceroute6 2001:db8:1::1

The first command shows all IPv6 addresses on all interfaces. The second shows the per-interface details. The third and fourth are the Linux kernel view. The fifth and sixth prove reachability to specific addresses. The seventh proves the forwarding path.

How it fails

The production failure modes the engineer must recognise:

  • ULA advertised upstream. A route-map that does not filter fc00::/7 lets ULA into BGP. Upstream providers reject, but the local IGP carries the prefix and traffic stays inside the local AS — unless redistribution sends it further.
  • GUA mistaken for ULA in firewall rules. A rule that matches fc00::/7 allows only ULA. A service that should be reachable from the public internet on a GUA is blocked.
  • Solicited-node multicast filtered. A firewall that does not understand NDP drops the multicast NS. Neighbour resolution fails and unicast traffic fails.
  • Wrong prefix length on a downstream interface. A /65 defeats SLAAC (which assumes /64) and breaks PMTUD on some implementations. VyOS 1.5 accepts /65 but warns; operators must use /64 for host subnets.
  • /127 used where /64 expected. Some operators use /127 on point-to-point links (RFC 6164). VyOS supports this, but a number of hosts assume /64 for SLAAC and fail to configure their addresses correctly.

Rollback

The recovery from a bad IPv6 address configuration:

  • Wrong address: delete interfaces ethernet eth0 ipv6 address '...' and re-add the correct one before commit; save.
  • Wrong prefix length: set interfaces ethernet eth0 ipv6 address '2001:db8:1::1/64' with the correct /64.
  • ULA advertised: add route-map FILTER-ULA deny 10 match ipv6 address prefix-list BLOCK-ULA and apply to the BGP outbound policy.

Production discipline

Cross-course references

The Linux course’s XIX-Linux-NetFoundations covers the kernel IPv6 address model and the addrgenmode knobs. The Proxmox course’s XXIX-Proxmox-Networking covers the host-side IPv6 allocation in the hypervisor. The OPNsense course’s I-OPNsense-NetFoundations covers the firewall-side equivalent. The VyOS lesson vyos-xi-01-ipv6-fundamentals covers the header and ICMPv6 that this lesson assumes.

Quiz

Knowledge check · 4 questions

  1. Q1. Which prefix is the IANA-allocated block for Global Unicast Addresses?

  2. Q2. A /48 site prefix contains 65536 /64 subnets.

  3. Q3. An operator configures a /65 prefix on a customer LAN interface. Hosts that rely on SLAAC fail to autoconfigure their addresses. Why?

    SLAAC depends on the subnet prefix being exactly /64 so the interface identifier is 64 bits wide. A /65 splits the address differently and most SLAAC implementations either refuse or compute the wrong identifier.

  4. Q4. An operator generates a ULA prefix and redistributes it into BGP. The upstream provider's prefix-list blocks it, but the operator's own IGP advertises it across the local AS. What is the operational risk?

    ULA prefixes are meant for internal use. If they leak into the public BGP, operators on the internet would see traffic for an address space that is not globally routable and would drop it. Even when blocked upstream, internal leakage means internal services are reachable on their ULA addresses from across the corporate AS but not from outside - which is intended, but the operator must ensure no service relies on the ULA being reachable from outside.

Passing score: 75%. Answers are checked in this browser.