← Back to Blog

Private IP Address Ranges: RFC 1918 Complete Guide

Every time you configure a home router, design an AWS VPC, or set up a Kubernetes cluster, you are working with private IP address ranges. Understanding RFC 1918 - the standard that defines these ranges - is fundamental networking knowledge every developer and DevOps engineer needs.

The Problem: Not Enough Public IP Addresses

IPv4 uses 32-bit addresses, which gives roughly 4.3 billion unique addresses. Sounds like a lot - until you consider there are 8 billion people on Earth, each with multiple devices, plus billions of servers, cloud instances, and IoT devices. The internet would have run out of IP addresses in the early 1990s if engineers had not acted.

The solution was RFC 1918, published in 1996 by the IETF. It reserved three blocks of IPv4 address space exclusively for private networks. These addresses are never routed on the public internet. Millions of private networks can reuse the same private IP ranges without conflict, because packets carrying private source addresses are dropped at internet routers.

This works because of Network Address Translation (NAT): your router holds one public IP address, and it rewrites private source addresses to that public IP as traffic leaves your network. The internet only ever sees your router's public IP.

The Three RFC 1918 Private Ranges

RFC 1918 defines exactly three blocks of private address space:

Range              CIDR          First Address     Last Address       Total Addresses
-----------------------------------------------------------------------------------------------
Class A block      10.0.0.0/8    10.0.0.0          10.255.255.255     16,777,216  (~16.7M)
Class B block      172.16.0.0/12 172.16.0.0         172.31.255.255     1,048,576   (~1M)
Class C block      192.168.0.0/16 192.168.0.0       192.168.255.255    65,536      (~65K)

10.0.0.0/8 - The Large Enterprise Block

This is the biggest private range, offering over 16 million addresses. The /8 prefix means only the first octet (10) is fixed. Everything from 10.0.0.1 to 10.255.255.254 is fair game. This range is the standard choice for:

  • Large enterprise networks with thousands of hosts
  • Cloud VPCs (AWS, GCP, Azure all default to 10.x.x.x ranges)
  • Kubernetes pod CIDR blocks (e.g., 10.244.0.0/16 for Flannel)
  • VPN tunnels connecting multiple offices

The 10.0.0.0/8 block is further subnetted in practice. You would never use it as a single flat network. Instead, you carve it into smaller subnets like 10.0.1.0/24, 10.0.2.0/24, etc.

172.16.0.0/12 - The Middle Block

This block covers 172.16.0.0 through 172.31.255.255. The /12 mask means the first 12 bits are fixed (172.16 to 172.31 in the second octet). It provides about 1 million addresses. This range is less commonly seen in small networks but is heavily used in:

  • Docker's default bridge network (172.17.0.0/16)
  • AWS default VPC (172.31.0.0/16)
  • Mid-size corporate networks

One common source of confusion: people mistake 172.168.x.x for a private address. It is not. Only 172.16.0.0 through 172.31.255.255 are private. 172.168.x.x is a public address range.

192.168.0.0/16 - The Home Network Range

This is the range everyone has seen. Your home router is almost certainly 192.168.1.1 or 192.168.0.1. With 65,536 addresses, it is more than enough for any home or small office network. Common default gateway addresses include:

  • 192.168.1.1 - Linksys, Netgear, many consumer routers
  • 192.168.0.1 - D-Link, TP-Link
  • 192.168.2.1 - Cisco home routers
  • 192.168.100.1 - Some ISP-provided modems

CIDR Notation Explained

Every range above is expressed in CIDR (Classless Inter-Domain Routing) notation: an IP address followed by a slash and a prefix length. The prefix length tells you how many bits are the network portion. The remaining bits are host bits.

192.168.1.0/24

Binary: 11000000.10101000.00000001.00000000
Mask:   11111111.11111111.11111111.00000000
                                   ^^^^^^^^
                                   8 host bits = 256 addresses (254 usable)

Network address:   192.168.1.0    (first address, not assignable)
Broadcast address: 192.168.1.255  (last address, not assignable)
Usable range:      192.168.1.1 - 192.168.1.254

The number of usable host addresses in a subnet is 2^(32 - prefix) - 2. The minus 2 accounts for the network address and broadcast address.

How NAT Makes Private IPs Work

Private IPs cannot be routed on the public internet. So how does your laptop with IP 192.168.1.100 reach a server at 142.250.80.46 (google.com)? Through NAT:

  1. Your laptop sends a packet: source 192.168.1.100:54321 → destination 142.250.80.46:443
  2. Your router rewrites the source to its public IP: 203.0.113.5:54321142.250.80.46:443
  3. The router records this mapping in a NAT table
  4. Google's server responds to 203.0.113.5:54321
  5. Your router looks up the NAT table, rewrites the destination back to 192.168.1.100:54321, and forwards the packet

This process is transparent to applications. NAT is why IPv4 has survived this long despite address exhaustion - one public IP can serve hundreds of private devices simultaneously.

Private IP Ranges in Cloud Networking

Cloud providers use RFC 1918 ranges extensively for Virtual Private Clouds (VPCs). Here is how different providers use them by default:

AWS VPC

Default VPC CIDR:  172.31.0.0/16
Common custom VPC: 10.0.0.0/16    (recommended for new deployments)

Subnet examples for multi-AZ design:
  10.0.1.0/24   -- us-east-1a public subnet
  10.0.2.0/24   -- us-east-1b public subnet
  10.0.11.0/24  -- us-east-1a private subnet
  10.0.12.0/24  -- us-east-1b private subnet

AWS recommends using 10.0.0.0/8 for VPCs, especially when you anticipate VPC peering, because overlapping CIDRs cannot be peered. If VPC A uses 10.0.0.0/16 and VPC B also uses 10.0.0.0/16, peering is impossible.

Docker Networking

Default bridge:  172.17.0.0/16
docker0 gateway: 172.17.0.1
First container: 172.17.0.2

Custom networks:
  docker network create --subnet=10.5.0.0/16 mynet

Kubernetes

Flannel pod CIDR:    10.244.0.0/16
Calico pod CIDR:     192.168.0.0/16
Service CIDR:        10.96.0.0/12
Node CIDR example:   10.244.1.0/24 (per node)

Calculate Subnets Instantly

Enter any IP range and get the network address, broadcast, usable hosts, and subnet breakdown. Free, runs entirely in your browser.

Open Subnet Calculator →

Step-by-Step: Designing a VPC CIDR

When designing a VPC or office network from scratch, follow this process:

  1. Choose a parent block. Use 10.0.0.0/8 as your root. Pick a /16 slice per region or environment (e.g., 10.0.0.0/16 for prod-us, 10.1.0.0/16 for prod-eu, 10.2.0.0/16 for staging).
  2. Avoid overlap. List all existing VPCs, on-premise networks, and VPN tunnels. Make sure your chosen CIDR does not overlap with any of them. Overlapping CIDRs break peering and routing.
  3. Plan subnet tiers. Within your /16, allocate /24 subnets per availability zone and tier (public, private, data). Leave gaps for future growth.
  4. Reserve space. AWS reserves 5 IPs per subnet (first 4 + last). Always use /24 or larger for subnets in production - avoid /28 subnets (11 usable IPs) in load-balanced environments.
  5. Document everything. Use an IP Address Management (IPAM) tool or even a spreadsheet. Undocumented allocations cause conflicts when teams grow.

Other Special-Purpose IP Ranges

RFC 1918 is not the only source of non-routable addresses. Other ranges you will encounter:

  • 127.0.0.0/8 - Loopback (localhost). 127.0.0.1 is the most famous, but the entire /8 is loopback.
  • 169.254.0.0/16 - Link-local (APIPA). Used when DHCP fails. Also used by AWS EC2 instance metadata service at 169.254.169.254.
  • 100.64.0.0/10 - Shared address space (RFC 6598). Used by ISPs for carrier-grade NAT between their infrastructure and customers.
  • 0.0.0.0/8 - This network. Used as a source address when a host does not yet know its IP (e.g., during DHCP discovery).
  • 255.255.255.255/32 - Limited broadcast. Sent to all hosts on the local network.

Checking If an IP Is Private

In code, you often need to determine whether an IP is private. Here is how to do it in different languages:

// JavaScript
function isPrivateIP(ip) {
  const parts = ip.split('.').map(Number);
  return (
    parts[0] === 10 ||
    (parts[0] === 172 && parts[1] >= 16 && parts[1] <= 31) ||
    (parts[0] === 192 && parts[1] === 168) ||
    parts[0] === 127
  );
}

// Python
import ipaddress
def is_private(ip):
    return ipaddress.ip_address(ip).is_private

# Shell (check if IP is in 10.0.0.0/8)
ipcalc -n 10.45.23.1/8  # or use iproute2 tools

Frequently Asked Questions

What is the difference between private and public IP addresses?

Public IP addresses are globally unique and routable on the internet. Private IP addresses (RFC 1918) are only meaningful within a private network and are never forwarded by internet routers. Multiple organizations can use the same private IP ranges simultaneously without conflict, because they are isolated behind NAT.

Can two devices on different networks have the same private IP?

Yes, and this is by design. Your home router at 192.168.1.1 and your office router at 192.168.1.1 do not conflict because they are on separate, isolated networks. Problems only arise if you try to connect the two networks (via VPN or peering) without first resolving the address overlap.

Why does AWS recommend not using 172.16.0.0/12 for VPCs?

AWS does not explicitly prohibit it, but many corporate networks and the Docker default bridge (172.17.0.0/16) use that range. If you ever need to connect an AWS VPC to an on-premise network via Direct Connect or VPN, overlapping CIDRs will cause routing failures. Using 10.0.0.0/8 with per-environment allocations is safer because you have full control of that space.

What is the difference between /8, /16, and /24 subnets?

The number after the slash (prefix length) tells you how many bits are the network portion. A /8 fixes 8 bits, leaving 24 bits for hosts (16.7M addresses). A /16 fixes 16 bits, leaving 16 bits for hosts (65,536 addresses). A /24 fixes 24 bits, leaving 8 bits for hosts (256 addresses, 254 usable). Shorter prefixes mean bigger networks; longer prefixes mean smaller, more specific subnets.

Is 172.168.x.x a private IP address?

No. This is a common misconception. Only 172.16.0.0 through 172.31.255.255 are private per RFC 1918. The address 172.168.x.x falls outside that range and is a public IP. If you are trying to access 172.168.x.x and it is not working, that is why: it is a public address, not a local one.

What happens if two VPCs have overlapping CIDRs?

You cannot create a VPC peering connection or AWS Transit Gateway attachment between two VPCs with overlapping CIDRs. The AWS VPC router cannot determine which VPC to forward a packet to. The only solution is to re-IP one of the VPCs - a painful, disruptive operation in production. Always plan your CIDR allocations before deploying.

The Bottom Line

RFC 1918 private IP ranges - 10.0.0.0/8, 172.16.0.0/12, and 192.168.0.0/16 - are the backbone of every private network, from your home Wi-Fi to multi-region cloud architectures. Understanding these ranges, how CIDR notation works, and how NAT makes them function is essential knowledge for any engineer working with networks, cloud infrastructure, or containers.

The most important practical advice: plan your CIDR allocations before you deploy, not after. Changing IP ranges in production networks is expensive and error-prone. Use a /16 per environment, allocate /24 subnets per AZ and tier, and document every allocation.

Use our free tool here → Subnet Calculator to instantly calculate network addresses, broadcast addresses, usable host ranges, and subnet masks for any CIDR block.

UK
Written by Usman Khan
DevOps Engineer | MSc Cybersecurity | CEH | AWS Solutions Architect

Usman has 10+ years of experience securing enterprise infrastructure, managing high-traffic servers, and building zero-knowledge security tools. Read more about the author.