tcp.h

Go to the documentation of this file.
00001 #ifndef _GPXE_TCP_H
00002 #define _GPXE_TCP_H
00003 
00004 /** @file
00005  *
00006  * TCP protocol
00007  *
00008  * This file defines the gPXE TCP API.
00009  *
00010  */
00011 
00012 FILE_LICENCE ( GPL2_OR_LATER );
00013 
00014 #include <gpxe/tcpip.h>
00015 
00016 /**
00017  * A TCP header
00018  */
00019 struct tcp_header {
00020         uint16_t src;           /* Source port */
00021         uint16_t dest;          /* Destination port */
00022         uint32_t seq;           /* Sequence number */
00023         uint32_t ack;           /* Acknowledgement number */
00024         uint8_t hlen;           /* Header length (4), Reserved (4) */
00025         uint8_t flags;          /* Reserved (2), Flags (6) */
00026         uint16_t win;           /* Advertised window */
00027         uint16_t csum;          /* Checksum */
00028         uint16_t urg;           /* Urgent pointer */
00029 };
00030 
00031 /** @defgroup tcpopts TCP options
00032  * @{
00033  */
00034 
00035 /** End of TCP options list */
00036 #define TCP_OPTION_END 0
00037 
00038 /** TCP option pad */
00039 #define TCP_OPTION_NOP 1
00040 
00041 /** Generic TCP option */
00042 struct tcp_option {
00043         uint8_t kind;
00044         uint8_t length;
00045 } __attribute__ (( packed ));
00046 
00047 /** TCP MSS option */
00048 struct tcp_mss_option {
00049         uint8_t kind;
00050         uint8_t length;
00051         uint16_t mss;
00052 } __attribute__ (( packed ));
00053 
00054 /** Code for the TCP MSS option */
00055 #define TCP_OPTION_MSS 2
00056 
00057 /** TCP timestamp option */
00058 struct tcp_timestamp_option {
00059         uint8_t kind;
00060         uint8_t length;
00061         uint32_t tsval;
00062         uint32_t tsecr;
00063 } __attribute__ (( packed ));
00064 
00065 /** Padded TCP timestamp option (used for sending) */
00066 struct tcp_timestamp_padded_option {
00067         uint8_t nop[2];
00068         struct tcp_timestamp_option tsopt;
00069 } __attribute__ (( packed ));
00070 
00071 /** Code for the TCP timestamp option */
00072 #define TCP_OPTION_TS 8
00073 
00074 /** Parsed TCP options */
00075 struct tcp_options {
00076         /** MSS option, if present */
00077         const struct tcp_mss_option *mssopt;
00078         /** Timestampe option, if present */
00079         const struct tcp_timestamp_option *tsopt;
00080 };
00081 
00082 /** @} */
00083 
00084 /*
00085  * TCP flags
00086  */
00087 #define TCP_CWR         0x80
00088 #define TCP_ECE         0x40
00089 #define TCP_URG         0x20
00090 #define TCP_ACK         0x10
00091 #define TCP_PSH         0x08
00092 #define TCP_RST         0x04
00093 #define TCP_SYN         0x02
00094 #define TCP_FIN         0x01
00095 
00096 /**
00097 * @defgroup tcpstates TCP states
00098 *
00099 * The TCP state is defined by a combination of the flags that have
00100 * been sent to the peer, the flags that have been acknowledged by the
00101 * peer, and the flags that have been received from the peer.
00102 *
00103 * @{
00104 */
00105 
00106 /** TCP flags that have been sent in outgoing packets */
00107 #define TCP_STATE_SENT(flags) ( (flags) << 0 )
00108 #define TCP_FLAGS_SENT(state) ( ( (state) >> 0 ) & 0xff )
00109 
00110 /** TCP flags that have been acknowledged by the peer
00111  *
00112  * Note that this applies only to SYN and FIN.
00113  */
00114 #define TCP_STATE_ACKED(flags) ( (flags) << 8 )
00115 #define TCP_FLAGS_ACKED(state) ( ( (state) >> 8 ) & 0xff )
00116 
00117 /** TCP flags that have been received from the peer
00118  *
00119  * Note that this applies only to SYN and FIN, and that once SYN has
00120  * been received, we should always be sending ACK.
00121  */
00122 #define TCP_STATE_RCVD(flags) ( (flags) << 16 )
00123 #define TCP_FLAGS_RCVD(state) ( ( (state) >> 16 ) & 0xff )
00124 
00125 /** TCP flags that are currently being sent in outgoing packets */
00126 #define TCP_FLAGS_SENDING(state) \
00127         ( TCP_FLAGS_SENT ( state ) & ~TCP_FLAGS_ACKED ( state ) )
00128 
00129 /** CLOSED
00130  *
00131  * The connection has not yet been used for anything.
00132  */
00133 #define TCP_CLOSED TCP_RST
00134 
00135 /** LISTEN
00136  *
00137  * Not currently used as a state; we have no support for listening
00138  * connections.  Given a unique value to avoid compiler warnings.
00139  */
00140 #define TCP_LISTEN 0
00141 
00142 /** SYN_SENT
00143  *
00144  * SYN has been sent, nothing has yet been received or acknowledged.
00145  */
00146 #define TCP_SYN_SENT    ( TCP_STATE_SENT ( TCP_SYN ) )
00147 
00148 /** SYN_RCVD
00149  *
00150  * SYN has been sent but not acknowledged, SYN has been received.
00151  */
00152 #define TCP_SYN_RCVD    ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK ) |            \
00153                           TCP_STATE_RCVD ( TCP_SYN ) )
00154 
00155 /** ESTABLISHED
00156  *
00157  * SYN has been sent and acknowledged, SYN has been received.
00158  */
00159 #define TCP_ESTABLISHED ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK ) |            \
00160                           TCP_STATE_ACKED ( TCP_SYN ) |                     \
00161                           TCP_STATE_RCVD ( TCP_SYN ) )
00162 
00163 /** FIN_WAIT_1
00164  *
00165  * SYN has been sent and acknowledged, SYN has been received, FIN has
00166  * been sent but not acknowledged, FIN has not been received.
00167  *
00168  * RFC 793 shows that we can enter FIN_WAIT_1 without have had SYN
00169  * acknowledged, i.e. if the application closes the connection after
00170  * sending and receiving SYN, but before having had SYN acknowledged.
00171  * However, we have to *pretend* that SYN has been acknowledged
00172  * anyway, otherwise we end up sending SYN and FIN in the same
00173  * sequence number slot.  Therefore, when we transition from SYN_RCVD
00174  * to FIN_WAIT_1, we have to remember to set TCP_STATE_ACKED(TCP_SYN)
00175  * and increment our sequence number.
00176  */
00177 #define TCP_FIN_WAIT_1  ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK | TCP_FIN ) |  \
00178                           TCP_STATE_ACKED ( TCP_SYN ) |                     \
00179                           TCP_STATE_RCVD ( TCP_SYN ) )
00180 
00181 /** FIN_WAIT_2
00182  *
00183  * SYN has been sent and acknowledged, SYN has been received, FIN has
00184  * been sent and acknowledged, FIN ha not been received.
00185  */
00186 #define TCP_FIN_WAIT_2  ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK | TCP_FIN ) |  \
00187                           TCP_STATE_ACKED ( TCP_SYN | TCP_FIN ) |           \
00188                           TCP_STATE_RCVD ( TCP_SYN ) )
00189 
00190 /** CLOSING / LAST_ACK
00191  *
00192  * SYN has been sent and acknowledged, SYN has been received, FIN has
00193  * been sent but not acknowledged, FIN has been received.
00194  *
00195  * This state actually encompasses both CLOSING and LAST_ACK; they are
00196  * identical with the definition of state that we use.  I don't
00197  * *believe* that they need to be distinguished.
00198  */
00199 #define TCP_CLOSING_OR_LAST_ACK                                             \
00200                         ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK | TCP_FIN ) |  \
00201                           TCP_STATE_ACKED ( TCP_SYN ) |                     \
00202                           TCP_STATE_RCVD ( TCP_SYN | TCP_FIN ) )
00203 
00204 /** TIME_WAIT
00205  *
00206  * SYN has been sent and acknowledged, SYN has been received, FIN has
00207  * been sent and acknowledged, FIN has been received.
00208  */
00209 #define TCP_TIME_WAIT   ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK | TCP_FIN ) |  \
00210                           TCP_STATE_ACKED ( TCP_SYN | TCP_FIN ) |           \
00211                           TCP_STATE_RCVD ( TCP_SYN | TCP_FIN ) )
00212 
00213 /** CLOSE_WAIT
00214  *
00215  * SYN has been sent and acknowledged, SYN has been received, FIN has
00216  * been received.
00217  */
00218 #define TCP_CLOSE_WAIT  ( TCP_STATE_SENT ( TCP_SYN | TCP_ACK ) |            \
00219                           TCP_STATE_ACKED ( TCP_SYN ) |                     \
00220                           TCP_STATE_RCVD ( TCP_SYN | TCP_FIN ) )
00221 
00222 /** Can send data in current state
00223  *
00224  * We can send data if and only if we have had our SYN acked and we
00225  * have not yet sent our FIN.
00226  */
00227 #define TCP_CAN_SEND_DATA(state)                                            \
00228         ( ( (state) & ( TCP_STATE_ACKED ( TCP_SYN ) |                       \
00229                         TCP_STATE_SENT ( TCP_FIN ) ) )                      \
00230           == TCP_STATE_ACKED ( TCP_SYN ) )
00231 
00232 /** Have ever been fully established
00233  *
00234  * We have been fully established if we have both received a SYN and
00235  * had our own SYN acked.
00236  */
00237 #define TCP_HAS_BEEN_ESTABLISHED(state)                                     \
00238         ( ( (state) & ( TCP_STATE_ACKED ( TCP_SYN ) |                       \
00239                         TCP_STATE_RCVD ( TCP_SYN ) ) )                      \
00240           == ( TCP_STATE_ACKED ( TCP_SYN ) | TCP_STATE_RCVD ( TCP_SYN ) ) )
00241 
00242 /** Have closed gracefully
00243  *
00244  * We have closed gracefully if we have both received a FIN and had
00245  * our own FIN acked.
00246  */
00247 #define TCP_CLOSED_GRACEFULLY(state)                                        \
00248         ( ( (state) & ( TCP_STATE_ACKED ( TCP_FIN ) |                       \
00249                         TCP_STATE_RCVD ( TCP_FIN ) ) )                      \
00250           == ( TCP_STATE_ACKED ( TCP_FIN ) | TCP_STATE_RCVD ( TCP_FIN ) ) )
00251 
00252 /** @} */
00253 
00254 /** Mask for TCP header length field */
00255 #define TCP_MASK_HLEN   0xf0
00256 
00257 /** Smallest port number on which a TCP connection can listen */
00258 #define TCP_MIN_PORT 1
00259 
00260 /* Some IOB constants */
00261 #define MAX_HDR_LEN     100
00262 #define MAX_IOB_LEN     1500
00263 #define MIN_IOB_LEN     MAX_HDR_LEN + 100 /* To account for padding by LL */
00264 
00265 /**
00266  * Maxmimum advertised TCP window size
00267  *
00268  * We estimate the TCP window size as the amount of free memory we
00269  * have.  This is not strictly accurate (since it ignores any space
00270  * already allocated as RX buffers), but it will do for now.
00271  *
00272  * Since we don't store out-of-order received packets, the
00273  * retransmission penalty is that the whole window contents must be
00274  * resent.  This suggests keeping the window size small, but bear in
00275  * mind that the maximum bandwidth on any link is limited to
00276  *
00277  *    max_bandwidth = ( tcp_window / round_trip_time )
00278  *
00279  * With a 48kB window, which probably accurately reflects our amount
00280  * of free memory, and a WAN RTT of say 200ms, this gives a maximum
00281  * bandwidth of 240kB/s.  This is sufficiently close to realistic that
00282  * we will need to be careful that our advertised window doesn't end
00283  * up limiting WAN download speeds.
00284  *
00285  * Finally, since the window goes into a 16-bit field and we cannot
00286  * actually use 65536, we use a window size of (65536-4) to ensure
00287  * that payloads remain dword-aligned.
00288  */
00289 //#define TCP_MAX_WINDOW_SIZE   ( 65536 - 4 )
00290 #define TCP_MAX_WINDOW_SIZE     4096
00291 
00292 /**
00293  * Path MTU
00294  *
00295  * We really ought to implement Path MTU discovery.  Until we do,
00296  * anything with a path MTU greater than this may fail.
00297  */
00298 #define TCP_PATH_MTU 1460
00299 
00300 /**
00301  * Advertised TCP MSS
00302  *
00303  * We currently hardcode this to a reasonable value and hope that the
00304  * sender uses path MTU discovery.  The alternative is breaking the
00305  * abstraction layer so that we can find out the MTU from the IP layer
00306  * (which would have to find out from the net device layer).
00307  */
00308 #define TCP_MSS 1460
00309 
00310 /** TCP maximum segment lifetime
00311  *
00312  * Currently set to 2 minutes, as per RFC 793.
00313  */
00314 #define TCP_MSL ( 2 * 60 * TICKS_PER_SEC )
00315 
00316 extern struct tcpip_protocol tcp_protocol;
00317 
00318 #endif /* _GPXE_TCP_H */

Generated on Tue Apr 6 20:01:09 2010 for gPXE by  doxygen 1.5.7.1