Things that NATs break
This is an attempt to concisely document the various things that NATs
break. Not all of these are major, and it doesn't readily translate into
a list of applications that NATs break. I wrote this list because I got
tired of refuting comments of the form ``NATs only break applications that
send addresses around''. As you can see, it's a bit worse than that.
This is also not to say that some of these things aren't also broken
by firewalls or proxies. But NATs break these things even in the presence
of firewalls and proxies, because even if you fix the firewall or proxy,
you still have to fix the NAT.
- Global addressibility
- NATs break the ability to use a single, unambiguous, address to identify,
or communicate with, a host or a service from anywhere in the network.
- examples of apps or services that uses IP address as identifier: rlogin/rsh,
Kerberos, IPsec, ONC RPC/NFS. Note that these cannot all be dismissed
as being too insecure to be worth keeping.
- examples of apps or services that use IP address as routable identifier: almost
any distributed or ``cluster computing'' system, including PVM and
MPI.
- NATs break the ability for cooperating processes to exchange host/service
addresses, independent of where they are in the network.
- NATs break the ability of hosts to know their own addresses as viewed
from outside the NAT. Even if they knew their own addresses, they would
not know in which contexts those addresses were valid.
- NATs degrade the ability to use IP addresses to debug problems
in the network, or to work around problems with DNS, i.e. to use an application
in spite of DNS failure.
- NOTE: DNS names don't work as good substitutes for IP addresses
because many sites do not maintain DNS for local hosts, because DNS
often gets out of sync with reality, and because many hosts don't know their
own DNS names. DNS lookups slow things down, and DNS is considerably
less reliable than IP routing. Note also that once you lose
the ability to use IP addresses as globally-routable identifiers,
any ``external'' solution will have most of the same problems as DNS. You
cannot solve these problems without changes to the hosts themselves.
- Global uniqueness
- NATs break the ability of applications to use IP address as a
globally-unique token, or in constructing a globally-unique token (message-id,
UUID-like things).
- NATs break the ability of an application to associate per-host state
with that host's IP address
For instance, I once built a name resolution service
that used MD5, timestamps, nonces, and shared secrets for authentication.
Because replay attacks and packet duplication were both possible, and some
requests were not idempotent, I needed a way to detect duplicate requests.
So I kept a record of the last such request issued by any particular
IP address. This technique would break in the presence of NATs. (since
this service was only intended for ``always connected'' hosts, dynamic
IP assignment was not an issue)
(note that global uniqueness can still be useful even when addresses
are recycled, as happens with dialup hosts and dynamic IP address
assignment, because an IP address plus a reasonably precise timestamp is
still globally unique)
- NATs break the utility of IP addresses for logging
- Persistence of host-to-address binding
- Since a NAT cannot be aware of an application's assumptions regarding
the persistence of a host or service address, a NAT's heuristics for deciding
when to terminate the binding between an internal and external address
will break some applications. In other words, if a ``session'' is the amount
of time during which a set of cooperating processes expect that the bindings
between those processes and their IP addresses will be stable, an
application's idea of a ``session'' may differ from a NAT's heuristic guess,
and the NAT will break the application. (Even for TCP-based applications,
the duration of a session cannot be reliabily determined by watching for
SYNs and FINs)
- Address structure
- NAPTs break applications that assume that two different ports with
the same host address are located at the same host. For instance, an application
that attempted to ``fail over'' from one service to another (IMAP to
POP, SUBMISSION to SMTP, krlogin to rlogin), or an application that
needs to associate multiple services on the same host (e.g. NFS and
mountd, any application using RPC's portmapper or other ``dynamic port
assignment'' facility, any application using a ``load average'' service
to help in load balancing) would not work properly through a NAPT.
- NAPTs can break applications that expect traffic to come from particular
port numbers.
- Deployability of new applications
- In general, NATs will break any application that wants to run
as a server behind the NAT, or any distributed application that
wants to distribute IP addresses and port numbers around between
processes. There are exceptions - some NATs do static mapping
of some number of external addresses to the same number of
internal addresses, some can be statically configured to hardwire
an address mapping a small number of external addresses and ports
to a small number of application servers on the inside of the NAT,
and some NATs play games with DNS to try to make it look like
the servers on the inside have visible external IP addresses.
But these hacks don't always solve the problem, and sometimes,
they confuse things even more.
- For applications that do not work through NAT, an ALG (application
level gateway), specific to that application, must be installed on the
NAT. Sometimes the problem cannot be solved at all, even with an ALG.
This means that new applications that aren't NAT-friendly (especially
distributed applications and applications that need a server to reside
behind a NAT) face a greater barrier to deployment. It's not enough
to deploy application code on the user's workstation; the NAT must
also be upgraded to support each new application (if this is even
possible).
- NATs frustrate attempts to experiment with new kinds of services, especially
those that rely on knowledge of network topology information. e.g. new
kinds of multicast, and proximity-estimation services like SONAR. For similar
reasons, NATs make it difficult to deploy such services.
- Reliability
- It is difficult to have redundant NATs - i.e. to connect networks using
NATs so that the NATs are not single points of failure.
- NATs can severely complicate the design of new protocols, either because
they must go to great lengths to work around NAT's limitations, or because
they require ALGs and the additional complexity therby obtained, or because
the new protocol must be layered on top of something (like HTTP) that
the NAT already supports (whether or not it is suitable as a substrate
for the new application).
- Scalability
- Since most NATs have a limited number of external addresses,
the NAT might not be able to supply external addresses for
all of the internal hosts that need on at any given time.
This creates additional sources of failure as compared to a
non-NATed network - the NAT will either drop packets until
a mapping can be established or it will reuse an external
address that may still be in use by an internal host.
-
Similarly, the state maintained by a NAT (especially a NAPT
or a NAT which performs pairwise mappings based on source and
destination address) can be exhausted, causing much the same problem.
- Private address spaces and VPNs
- VPNs and private address spaces don't mix well. If you need to access
services on each of multiple private nets (where those nets use private
address space) from a single host or encrypting router, there is a good
chance that the address spaces used by those private nets overlap. If
this is the case there is no good way for the encrypting host or router
to know which security credentials to use for which destination addresses.