Even though IP is unreliable and doesn't guarantee delivery, it is
important to notify the sender when something goes wrong. The Internet
Control Message Protocol (ICMP) is the mechanism used to give feedback
about network problems that are preventing packet delivery. Upper
protocols, like TCP, will be able to realize that packets aren't getting
through, but ICMP provides a method for discovering more catastrophic
problems, such as "TTL exceeded" and "need more fragments." Infrequent
problems, such as the IP checksum being wrong, will not be reported by
ICMP. The premise is that TCP or other reliable protocols can deal with
this type of packet corruption, and that if we're using an unreliable
protocol like UDP, we shouldn't care about small amounts of loss.
Conversely, problems with the network will be reported immediately.
For example, if the IP TTL is reaching zero, there's probably a routing
loop somewhere and no packets are going to get through. The end system
needs to know about these types of failures. ICMP is a protocol for
sending various messages to report network conditions—it is not ping.
The echo request is one of many messages. Ping can be filtered out, but
the majority of ICMP message types are required for proper operation of
IP, TCP and other protocols. Never let anyone tell you ICMP is evil and
should be blocked.
ICMP itself is quite complex. Each type of ICMP message, called the
"major type," also has "minor codes." ICMP lives just above Layer 3
(IP), so that it can be routed over the Internet. An ICMP packet is
therefore an IP packet with ICMP in the IP data portion. Every ICMP
message will also contain the entire IP header from the original
message, so that the end system will know which packet actually failed.
The first eight bytes of the original IP data will be included as well,
and this is normally the TCP or UDP header.
In summary, the ICMP header contains three fields that never change,
followed by the ICMP data, then the original IP header. The first 8
bytes contain the ICMP type (major type), the second contains the code
(minor code), and the third field is a checksum of the ICMP message.
We need to realize that a few situations exist where ICMP will not
send errors. ICMP errors will never be generated in response to an ICMP
error message. If ICMP messages were sent in response to other ICMP
messages, they would quickly multiply and create a storm of ICMP
packets. ICMP messages will never be sent in response to a broadcast or
multicast addresses either, to prevent broadcast storms.
The most useful ICMP packet is the Destination Unreachable messages,
major type 3. Error messages are typically generated by routers, and
sent to the original source of the packet. Most of the errors are also
forwarded to the application concerned with the packet that was sent. In
this vein, TCP makes extensive use of ICMP, as we'll see shortly.
A few of the most commonly used ICMP types in IPv4 include:
- Echo Reply (0) and Echo Request (8): this is ping.
- Destination Unreachable (3)
- Source Quench (4): An ICMP message used to notify the sender that the router or host is congested, and the sender needs to slow down.
- Redirect (5): a message used to say "use this other router instead" to a host that has access to both routers. We'll talk about this in detail in future routing issues of Networking 101.
- Router Advertisement Reply (9) and Router Solicitation (10)
- Time Exceeded (11): This message has two uses. First, it is used to send an error to the sending system when the IP TTL has been exceeded. Second, it will notify the sending system if a fragmented IP datagram isn't reassembled within a certain time limit.
And of course, there are minor codes within each of the above types.
Type 3, destination unreachable, has 15 minor codes itself. We won't
torture you with the details of everything, but there is one very
important use of ICMP that relies on type 3 messages.
Path MTU (PMTU) discovery is the mechanism that protocols use to
discover the largest supported MTU (maximum transmit unit) along the
path, in hopes of avoiding fragmentation. The largest possible size is
determined by the sender beginning with the MTU size of its local
interface, and then simply shipping the data with the DF (don't
fragment) bit set in the IP header. Everything will work as expected, or
the sender will get back a type 3 ICMP error, with the code for
"Fragmentation Required but the DF Flag is Set." When this happens, the
sender knows that it must reduce the size of the data it is sending. If
an error doesn't return, it assumes that the MTU is fine.
The main problem with PMTU discovery is that people block ICMP,
preventing the error from reaching the sending host. Many times it takes
place at the remote site you're trying to reach. Imagine that you're
sending a request to a web server, but a blank page keeps loading.
People on VPN connections see this effect more frequently, since their
MTU is a bit smaller than the normal amount, due to extra headers for
the VPN encapsulation. When the remote web server tries to send the VPN
user the website it requested, the last router hop before the user will
need to fragment the data, if it's too large. With the DF bit set, all
it can do is notify the sender that it must send smaller packets, but
the sender is blocking ICMP because it was deemed "evil" by policy
makers. The website never loads. The good news is that most TCP
implementations are a bit smarter. If they never get an ACK for the data
sent, they should retransmit with a smaller segment size, but this
doesn't always happen with certain popular, easy-to-use operating
systems.
In short, blocking ICMP is detrimental to the successful operation of
networks. It will break more than just ping; in fact, many protocols
will be neutered if ICMP isn't working.
No comments:
Post a Comment