Protocol Data Units (PDUs)
--------------------------

The send_network command's main mantra is that all PDUs, be them
IPv4, IPv6, TCP, UDP, ICMP, etc., have basically the same high-level
structure: a PDU header, PDU options that obviously may or may not be
present, and a PDU payload:

				+-------------+
				|             |
				| PDU header  |
				|             |
				+-------------+
				|             |
				| PDU options |
				|             |
				+-------------+
				|             |
				| PDU payload |
				|             |
				+-------------+

A key principle is that a PDU payload can be yet another PDU! For
instance, an IP packet can carry a TCP segment. This TCP segment is a
whole PDU embedded into the original PDU (the IP packet.) Graphically,
this looks like:

                +-------------+
                |             |
     PDU #0 hdr | IP header   |
                |             |
                +-------------+   +-------------+
                |             |  /|             |
    PDU #0 opts | IP options  | / |  TCP header | PDU #1 hdr
                |             |/  |             |
                +-------------+   +-------------+
                |             |   |             |
 PDU #0 payload | IP payload  |   |  TCP opts.  | PDU #1 opts
                |             |   |             |
                +-------------+   +-------------+
                               \  |             |
                                \ | TCP payload | PDU #1 payload
                                 \|             |
                                  +-------------+

This view of PDUs is simple, and very obvious, yet at the same time very
powerful.

When building packets or PDUs, creating a framework that divides the PDU
into these three components makes it very easy to create, develop and
maintain PDUs.

The send_network command is built around such framework. It works by
creating high level PDU structures representing the PDU header, options
and payload. Each of these high level structures contains "builders"
that put in place the PDU header, options and payload respectively,
based on parameters specified by the user.

Attacking the problem of PDU creation in this way makes it very easy
to write PDU builders since the developer only needs to focus on small
tasks at a time, instead of focusing on the "big picture". The "big
picture" is taken care of by the framework. As an example, the function
that builds a PDU in the send_network command is very small. The
function works by calling a header builder, options builders for each
option, and then calling a second-pass header builder that usually does
post-build things like calculating a checksum.

