NAT64/DNS64 Explained: Bridging IPv6-Only Networks to IPv4 Services

Overview

NAT64 and DNS64 are complementary IPv6 transition mechanisms that enable IPv6-only clients to communicate with IPv4-only servers. As networks increasingly adopt IPv6-only architectures to avoid the complexities of dual-stack deployments, NAT64/DNS64 provides a critical bridge to maintain backward compatibility with the legacy IPv4 internet.

Key RFC specifications:

These mechanisms work together seamlessly: DNS64 synthesizes IPv6 addresses for IPv4 destinations, while NAT64 performs the actual protocol translation, allowing IPv6-only networks to access the vast IPv4 internet without requiring IPv6 support from destination servers.


NAT64: Protocol Translation Gateway

What is NAT64?

NAT64 is a stateful network address and protocol translation mechanism that converts IPv6 packets to IPv4 and vice versa. It operates as a gateway device positioned at the network edge, translating between the two protocol families.

Primary function: Enable IPv6-only clients to initiate connections to IPv4-only servers using standard protocols (TCP, UDP, ICMPv6).

Translation method: Stateful NAT64 maintains connection state tables, mapping IPv6 client addresses to IPv4 addresses dynamically. This allows bidirectional communication while preserving application-layer protocols.

How NAT64 Translation Works

IPv6-to-IPv4 Translation Process

[IPv6 Client] → [NAT64 Gateway] → [IPv4 Server]

Step 1: IPv6 client sends packet to 64:ff9b::192.0.2.10
        Source: 2001:db8::1234
        Destination: 64:ff9b::192.0.2.10

Step 2: NAT64 gateway receives packet
        - Allocates IPv4 address from pool (e.g., 203.0.113.5)
        - Extracts IPv4 destination from lower 32 bits
        - Creates state table entry

Step 3: NAT64 translates and forwards to IPv4
        Source: 203.0.113.5 (NAT64 pool)
        Destination: 192.0.2.10 (extracted from IPv6)

IPv4-to-IPv6 Translation Process (Return Path)

[IPv4 Server] → [NAT64 Gateway] → [IPv6 Client]

Step 1: IPv4 server responds
        Source: 192.0.2.10
        Destination: 203.0.113.5

Step 2: NAT64 looks up state table
        - Finds mapping: 203.0.113.5 → 2001:db8::1234
        - Prepends NAT64 prefix to source IPv4

Step 3: NAT64 translates and forwards to IPv6
        Source: 64:ff9b::192.0.2.10
        Destination: 2001:db8::1234

NAT64 Translation Modes

Stateful NAT64 (RFC 6146):

Stateless NAT64 (RFC 7915):


DNS64: Address Synthesis Mechanism

What is DNS64?

DNS64 is a DNS server extension that synthesizes AAAA records (IPv6 addresses) from A records (IPv4 addresses) when no native IPv6 address exists for a domain. It acts as a DNS proxy that intercepts queries and manufactures IPv6 addresses pointing to the NAT64 gateway.

Primary function: Provide IPv6 addresses to clients even when destination servers only support IPv4.

Synthesis algorithm: DNS64 combines a configured IPv6 prefix (typically 64:ff9b::/96) with the IPv4 address found in A records, creating a synthetic AAAA record.

DNS64 Query Resolution Process

[IPv6 Client] → [DNS64 Server] → [Authoritative DNS] → [DNS64 Server] → [IPv6 Client]

Step 1: Client queries for www.example.com AAAA record
        Query: "What is the IPv6 address for www.example.com?"

Step 2: DNS64 forwards query to authoritative DNS
        - Checks for native AAAA record first
        - If AAAA exists: returns it directly (no synthesis)
        - If no AAAA: queries for A record

Step 3: Authoritative DNS returns A record only
        Response: www.example.com → 192.0.2.10 (A record)

Step 4: DNS64 synthesizes AAAA record
        - Takes NAT64 prefix: 64:ff9b::/96
        - Embeds IPv4 address in lower 32 bits
        - Creates synthetic AAAA: 64:ff9b::192.0.2.10

Step 5: DNS64 returns synthetic AAAA to client
        Response: www.example.com → 64:ff9b::192.0.2.10 (AAAA)

DNS64 Behavior Logic

Query for domain AAAA record:
│
├─ Native AAAA exists?
│  ├─ YES → Return native AAAA (no synthesis)
│  └─ NO → Continue to A record lookup
│
├─ A record exists?
│  ├─ YES → Synthesize AAAA from A record
│  │         (Prefix + IPv4 → IPv6 address)
│  └─ NO → Return NXDOMAIN (no records found)
│
└─ Return synthetic AAAA to client

Important: DNS64 always prioritizes native IPv6 addresses. Synthesis only occurs when a domain has A records but no AAAA records.


The Well-Known Prefix: 64:ff9b::/96

Prefix Structure and Purpose

The well-known prefix (WKP) 64:ff9b::/96 is reserved by RFC 6052 specifically for NAT64/DNS64 deployments. This standardized prefix allows clients and network equipment to recognize NAT64-synthesized addresses globally.

Prefix breakdown:

64:ff9b:: /96
│
├─ 96 bits: NAT64 prefix (fixed)
└─ 32 bits: Embedded IPv4 address (variable)

Example:
64:ff9b::192.0.2.10
│       └─ IPv4: 192.0.2.10 embedded in lower 32 bits
└─ Prefix: 64:ff9b::/96

IPv4 Address Embedding

IPv4 addresses are embedded in the lower 32 bits of the synthetic IPv6 address:

IPv4 Address:     192.0.2.10
Hexadecimal:      C0 00 02 0A
IPv6 Embedding:   64:ff9b::C000:020A
Expanded form:    64:ff9b::192.0.2.10

Well-Known Prefix vs. Network-Specific Prefix (NSP)

Well-Known Prefix (64:ff9b::/96):

Network-Specific Prefix (Custom /96):

Example NSP usage:

NSP: 2001:db8:64::/96
IPv4: 10.0.1.50 (private RFC 1918)
Synthetic IPv6: 2001:db8:64::10.0.1.50

NAT64/DNS64 Integration Architecture

Complete Communication Flow

┌─────────────────────────────────────────────────────────────────────┐
│                        IPv6-Only Network                             │
│                                                                       │
│  ┌──────────────┐                                                   │
│  │ IPv6 Client  │                                                   │
│  │2001:db8::1234│                                                   │
│  └──────┬───────┘                                                   │
│         │ 1. DNS query: www.ipv4only.com AAAA?                      │
│         ↓                                                            │
│  ┌──────────────┐                                                   │
│  │ DNS64 Server │                                                   │
│  │              │←──2. Query authoritative DNS for AAAA             │
│  │              │←──3. Receive A record: 192.0.2.10                 │
│  │              │   4. Synthesize: 64:ff9b::192.0.2.10              │
│  └──────┬───────┘                                                   │
│         │ 5. Return AAAA: 64:ff9b::192.0.2.10                       │
│         ↓                                                            │
│  ┌──────────────┐                                                   │
│  │ IPv6 Client  │                                                   │
│  │              │                                                   │
│  └──────┬───────┘                                                   │
│         │ 6. HTTP GET to 64:ff9b::192.0.2.10                        │
│         │    Src: 2001:db8::1234                                    │
│         │    Dst: 64:ff9b::192.0.2.10                               │
│         ↓                                                            │
│  ┌──────────────────────┐                                           │
│  │  NAT64 Gateway       │                                           │
│  │  IPv6: 64:ff9b::/96  │                                           │
│  │  IPv4 pool: x.x.x.x  │                                           │
│  └──────┬───────────────┘                                           │
│         │ 7. Translate to IPv4                                      │
└─────────┼─────────────────────────────────────────────────────────┘
          │    Src: 203.0.113.5 (from NAT64 pool)
          │    Dst: 192.0.2.10 (extracted from IPv6)
          ↓
┌─────────────────────────────────────────────────────────────────────┐
│                         IPv4 Internet                                │
│                                                                       │
│  ┌────────────────────┐                                             │
│  │  IPv4-Only Server  │                                             │
│  │   192.0.2.10       │                                             │
│  │ www.ipv4only.com   │                                             │
│  └────────────────────┘                                             │
│         │ 8. HTTP response                                          │
│         │    Src: 192.0.2.10                                        │
│         │    Dst: 203.0.113.5                                       │
└─────────┼─────────────────────────────────────────────────────────┘
          ↓
          │ 9. NAT64 translates back to IPv6
          │    Src: 64:ff9b::192.0.2.10
          │    Dst: 2001:db8::1234
          ↓
     [IPv6 Client receives response]

Packet Translation Details

IPv6 Packet (Client → NAT64):

IPv6 Header:
  Source: 2001:db8::1234
  Destination: 64:ff9b::192.0.2.10
  Next Header: TCP

TCP Payload:
  GET / HTTP/1.1
  Host: www.ipv4only.com

Translated IPv4 Packet (NAT64 → Server):

IPv4 Header:
  Source: 203.0.113.5 (NAT64 pool address)
  Destination: 192.0.2.10 (extracted from IPv6)
  Protocol: TCP

TCP Payload:
  GET / HTTP/1.1
  Host: www.ipv4only.com
  (unchanged application data)

IPv6-Only Network Deployment Scenarios

Enterprise Network Migration

Organizations transitioning to IPv6-only networks deploy NAT64/DNS64 to maintain access to IPv4-only internet services while eliminating dual-stack complexity.

Architecture:

Internal IPv6-Only Network (2001:db8::/32)
  │
  ├─ Workstations ([SLAAC](slaac-explained) addressing)
  ├─ Servers (static IPv6)
  ├─ Internal DNS64 server
  │  └─ Configured with NSP: 2001:db8:64::/96
  │
  └─ Border NAT64 gateway
     ├─ IPv6 interface: 2001:db8:64::1
     ├─ IPv4 pool: 203.0.113.0/24
     └─ Internet uplink

Benefits:

Mobile Carrier Networks (464XLAT)

Mobile operators deploy IPv6-only radio access networks with NAT64/DNS64 combined with CLAT (Customer-Side Translator) in devices—known as 464XLAT (RFC 6877).

Architecture:

┌─────────────────┐
│ Mobile Device   │
│ (IPv6-only RAN) │
│                 │
│ ┌─────────────┐ │
│ │ CLAT        │ │  ← Client-side IPv4→IPv6 translation
│ │ (464XLAT)   │ │     Presents virtual IPv4 to apps
│ └─────────────┘ │
└────────┬────────┘
         │ IPv6 packets
         ↓
┌────────────────────┐
│ Carrier Network    │
│ (IPv6-only core)   │
│                    │
│ ┌────────────────┐ │
│ │ PLAT (NAT64)   │ │  ← Provider-side IPv6→IPv4 translation
│ └────────────────┘ │
└────────┬───────────┘
         │ IPv4 packets
         ↓
    IPv4 Internet

Advantages:

Cloud Platform IPv6-Only Instances

Cloud providers (AWS, Google Cloud, Azure) offer IPv6-only instance options with managed NAT64/DNS64 services.

Google Cloud example:

VPC Subnet: 2001:db8:1::/64 (IPv6-only)
  │
  ├─ Cloud DNS64 policy configured
  ├─ NAT Gateway with NAT64 enabled
  │  └─ Uses well-known prefix 64:ff9b::/96
  │
  └─ Compute instances (IPv6-only)
     └─ Can reach IPv4 internet via NAT64

AWS VPC example:

VPC with IPv6 CIDR: 2600:1f14::/56
  │
  ├─ Egress-only Internet Gateway (IPv6)
  ├─ NAT Gateway with DNS64/NAT64
  │  └─ Subnet-level enablement
  │
  └─ EC2 instances (IPv6-only)
     └─ Automatic DNS64 synthesis

Implementation Examples

Public DNS64 Services

Google Public DNS64:

Resolver addresses:
  2001:4860:4860::6464
  2001:4860:4860::64

Configuration:
  - Uses well-known prefix 64:ff9b::/96
  - Global anycast service
  - Automatic synthesis for IPv6-only clients

Client configuration (Linux):

# /etc/resolv.conf
nameserver 2001:4860:4860::6464
nameserver 2001:4860:4860::64

Testing DNS64:

# Query IPv4-only domain
dig AAAA www.example.com @2001:4860:4860::6464

# Expected response:
# www.example.com. 300 IN AAAA 64:ff9b::93e5:70b
#                                    └─ Synthesized from 147.229.7.11

Router Configuration (Cisco)

NAT64 stateful pool:

ipv6 unicast-routing

! Define NAT64 prefix
ipv6 nat prefix 64:ff9b::/96

! Configure NAT64 pool
ipv6 nat v4-pool NAT64_POOL 203.0.113.1 203.0.113.254

! Apply NAT64 to interfaces
interface GigabitEthernet0/0
 description IPv6 side
 ipv6 address 2001:db8::1/64
 ipv6 nat

interface GigabitEthernet0/1
 description IPv4 side
 ip address 203.0.113.1 255.255.255.0
 ipv6 nat

DNS64 configuration:

! Enable DNS64
ipv6 nat prefix 64:ff9b::/96
ipv6 dns64 enable

! DNS64 server configuration
ipv6 dns64 server 2001:db8::53

Linux NAT64 (Jool)

Jool NAT64 deployment:

# Install Jool kernel module
sudo apt-get install linux-modules-extra-$(uname -r)
sudo modprobe jool

# Configure NAT64 instance
sudo jool instance add "example" --netfilter --pool6 64:ff9b::/96

# Add IPv4 pool
sudo jool -i "example" pool4 add --tcp 203.0.113.1 61001-65535
sudo jool -i "example" pool4 add --udp 203.0.113.1 61001-65535
sudo jool -i "example" pool4 add --icmp 203.0.113.1 61001-65535

# Enable IPv6 forwarding
sudo sysctl -w net.ipv6.conf.all.forwarding=1

BIND9 DNS64 (named.conf):

options {
    dns64 64:ff9b::/96 {
        clients { any; };
        mapped { !2001:db8::/32; any; };
        exclude { ::ffff:0000:0000/96; 64:ff9b::/96; };
        recursive-only yes;
    };
};

Client Discovery (PREF64)

464XLAT clients discover NAT64 prefix via Router Advertisements:

# Router Advertisement with PREF64 option (RFC 8781)
radvd.conf:

interface eth0 {
    AdvSendAdvert on;
    prefix 2001:db8::/64 { };

    # PREF64 option for NAT64 prefix discovery
    PREF64 64:ff9b::/96 { };
};

Client verification (Linux):

# Check received PREF64
ip -6 route show | grep pref64

# Expected output:
# pref64 64:ff9b::/96 dev eth0 metric 1024 pref medium

Limitations and Considerations

Protocol Compatibility Issues

IPv4 literal addresses embedded in application data:

Workaround: Application Layer Gateway (ALG) modules or 464XLAT CLAT for client-side translation.

DNS Security (DNSSEC) Complications

Problem: DNS64 synthesis breaks DNSSEC validation chain.

Authoritative DNS:
  example.com A 192.0.2.10 (signed with DNSSEC)

DNS64 synthesis:
  example.com AAAA 64:ff9b::192.0.2.10 (NOT signed by domain owner)

Validation result: FAIL (signature mismatch)

Mitigation strategies:

  1. DNS64 server validates A records before synthesis
  2. DNS64 operates as trusted recursive resolver (validation before synthesis)
  3. Clients trust DNS64 resolver (disable DNSSEC validation for synthesized records)

Best practice: Deploy DNS64 as part of trusted recursive DNS infrastructure within the network perimeter.

Performance Considerations

Latency overhead:

Research findings:

Optimization:

Scalability and High Availability

Single point of failure: NAT64 gateway failure breaks IPv4 connectivity for entire IPv6-only network.

High-availability deployment:

        IPv6-Only Network
              │
    ┌─────────┴─────────┐
    │                   │
┌───▼────┐         ┌────▼───┐
│ NAT64  │         │ NAT64  │
│Gateway1│◄───────►│Gateway2│
│(Active)│  VRRP   │(Standby)│
└───┬────┘         └────┬───┘
    │                   │
    └─────────┬─────────┘
              ↓
         IPv4 Internet

Load distribution:

IPv4 Address Pool Management

Stateful NAT64 efficiency:

Pool exhaustion risks:

Monitoring:

# Jool NAT64 pool statistics
sudo jool -i "example" stats display

# Watch for:
# - Active sessions / pool capacity
# - Port exhaustion warnings
# - Dropped packets due to pool exhaustion

IPv6-Only Application Compatibility

Applications requiring special handling:

  1. Hard-coded IPv4 literals: Applications connecting directly to IPv4 addresses bypass DNS64 entirely.

    • Solution: 464XLAT CLAT or application modification
  2. IPv4-only APIs: Some services lack IPv6 endpoints and require IPv4 connectivity.

    • Solution: NAT64 required (no alternative)
  3. Peer-to-peer protocols: NAT64 stateful translation complicates NAT traversal (STUN/TURN).

    • Solution: IPv6-native P2P protocols or ALG support
  4. Network diagnostics: Tools like traceroute require ICMP support through NAT64.

    • NAT64 must translate ICMPv6 ↔ ICMPv4 (RFC 6145)

Verification and Testing

Testing NAT64 Connectivity

From IPv6-only client:

# Test DNS64 synthesis
dig AAAA ipv4.test-ipv6.run

# Expected: Synthesized AAAA with 64:ff9b:: prefix

# Test NAT64 translation
curl -6 -v http://ipv4.test-ipv6.run/

# Expected: Successful HTTP response via NAT64

# Verify packet translation
traceroute -6 ipv4.test-ipv6.run

# Expected: Path shows 64:ff9b:: addresses

Comprehensive connectivity testing: Visit test-ipv6.run for automated NAT64/DNS64 detection:

Monitoring NAT64 Gateway

Key metrics:

# Connection state table usage
sudo jool -i "example" stats display | grep "Current"

# Translation success rate
sudo jool -i "example" stats display | grep "Successful"

# Pool4 utilization
sudo jool -i "example" pool4 display

Traffic analysis:

# Capture NAT64 translated traffic
sudo tcpdump -i eth0 -n 'ip6 dst 64:ff9b::/96'

# Monitor IPv4 side translations
sudo tcpdump -i eth1 -n 'src net 203.0.113.0/24'

Deployment Best Practices

1. Prefer Native IPv6 Over NAT64

NAT64/DNS64 is a transition mechanism, not an end goal. Always prioritize native IPv6 connectivity:

2. Use Well-Known Prefix for Public Internet

For internet-facing NAT64:

For internal/private NAT64:

3. Deploy High-Availability Architecture

4. Integrate with Network Operations

5. Educate Users and Developers


Conclusion

NAT64 and DNS64 provide an elegant solution for IPv6-only networks to maintain backward compatibility with the IPv4 internet. By combining DNS64's address synthesis with NAT64's stateful protocol translation, organizations can deploy IPv6-only infrastructures while seamlessly accessing IPv4-only services.

Key takeaways:

As the internet continues its transition to IPv6, NAT64/DNS64 will remain a critical bridge technology—enabling IPv6-only deployments without sacrificing connectivity to the legacy IPv4 world. However, the ultimate goal remains native IPv6 everywhere, eliminating the need for translation altogether.

Test your network's IPv6 readiness: Visit test-ipv6.run to detect NAT64 deployment, measure connectivity, and receive a comprehensive IPv6 readiness score.


Further Reading