00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #ifndef __INET_TCPCONNECTION_H
00020 #define __INET_TCPCONNECTION_H
00021
00022 #include <omnetpp.h>
00023 #include "INETDefs.h"
00024 #include "IPvXAddress.h"
00025 #include "TCP.h"
00026 #include "TCPSegment.h"
00027
00028 class TCPSegment;
00029 class TCPCommand;
00030 class TCPOpenCommand;
00031 class TCPSendQueue;
00032 class TCPSACKRexmitQueue;
00033 class TCPReceiveQueue;
00034 class TCPAlgorithm;
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057 enum TcpState
00058 {
00059 TCP_S_INIT = 0,
00060 TCP_S_CLOSED = FSM_Steady(1),
00061 TCP_S_LISTEN = FSM_Steady(2),
00062 TCP_S_SYN_SENT = FSM_Steady(3),
00063 TCP_S_SYN_RCVD = FSM_Steady(4),
00064 TCP_S_ESTABLISHED = FSM_Steady(5),
00065 TCP_S_CLOSE_WAIT = FSM_Steady(6),
00066 TCP_S_LAST_ACK = FSM_Steady(7),
00067 TCP_S_FIN_WAIT_1 = FSM_Steady(8),
00068 TCP_S_FIN_WAIT_2 = FSM_Steady(9),
00069 TCP_S_CLOSING = FSM_Steady(10),
00070 TCP_S_TIME_WAIT = FSM_Steady(11)
00071 };
00072
00073
00074
00075
00076
00077
00078 enum TCPEventCode
00079 {
00080 TCP_E_IGNORE,
00081
00082
00083
00084 TCP_E_OPEN_ACTIVE,
00085 TCP_E_OPEN_PASSIVE,
00086 TCP_E_SEND,
00087 TCP_E_CLOSE,
00088 TCP_E_ABORT,
00089 TCP_E_STATUS,
00090
00091
00092 TCP_E_RCV_DATA,
00093 TCP_E_RCV_ACK,
00094 TCP_E_RCV_SYN,
00095 TCP_E_RCV_SYN_ACK,
00096 TCP_E_RCV_FIN,
00097 TCP_E_RCV_FIN_ACK,
00098 TCP_E_RCV_RST,
00099
00100 TCP_E_RCV_UNEXP_SYN,
00101
00102
00103 TCP_E_TIMEOUT_2MSL,
00104 TCP_E_TIMEOUT_CONN_ESTAB,
00105 TCP_E_TIMEOUT_FIN_WAIT_2,
00106
00107
00108
00109 };
00110
00111
00114 #define TCP_TIMEOUT_CONN_ESTAB 75 // 75 seconds
00115 #define TCP_TIMEOUT_FIN_WAIT_2 600 // 10 minutes
00116 #define TCP_TIMEOUT_2MSL 240 // 2 * 2 minutes
00117 #define TCP_TIMEOUT_SYN_REXMIT 3 // initially 3 seconds
00118 #define TCP_TIMEOUT_SYN_REXMIT_MAX 240 // 4 mins (will only be used with SYN+ACK: with SYN CONN_ESTAB occurs sooner)
00119
00120
00121 #define MAX_SYN_REXMIT_COUNT 12 // will only be used with SYN+ACK: with SYN CONN_ESTAB occurs sooner
00122
00123 #define MAX_SACK_BLOCKS 60 // will only be used with SACK
00124 #define DUPTHRESH 3 // used for TCPTahoe, TCPReno and SACK (RFC 3517)
00125
00126 #define TCP_MAX_WIN 65535 // largest value (16 bit) for (unscaled) window size
00127
00128 #define PAWS_IDLE_TIME_THRESH 24*24*3600 // 24 days in seconds (RFC 1323)
00129
00130 #define TCP_OPTION_TS_SIZE 12
00131
00144 class INET_API TCPStateVariables : public cPolymorphic
00145 {
00146 public:
00147 TCPStateVariables();
00148 virtual std::string info() const;
00149 virtual std::string detailedInfo() const;
00150 public:
00151 bool active;
00152 bool fork;
00153
00154 uint32 snd_mss;
00155
00156
00157
00158
00159 uint32 snd_una;
00160 uint32 snd_nxt;
00161 uint32 snd_max;
00162 uint32 snd_wnd;
00163 uint32 snd_up;
00164 uint32 snd_wl1;
00165 uint32 snd_wl2;
00166 uint32 iss;
00167
00168
00169 uint32 rcv_nxt;
00170 uint32 rcv_wnd;
00171 uint32 rcv_up;
00172 uint32 irs;
00173 uint32 rcv_adv;
00174
00175
00176
00177 int syn_rexmit_count;
00178 simtime_t syn_rexmit_timeout;
00179
00180
00181
00182
00183 bool fin_ack_rcvd;
00184
00185 bool send_fin;
00186 uint32 snd_fin_seq;
00187
00188 bool fin_rcvd;
00189 uint32 rcv_fin_seq;
00190
00191 uint32 sentBytes;
00192
00193 bool nagle_enabled;
00194 bool delayed_acks_enabled;
00195 bool limited_transmit_enabled;
00196 bool increased_IW_enabled;
00197
00198 uint32 full_sized_segment_counter;
00199 bool ack_now;
00200
00201
00202
00203
00204
00205
00206
00207
00208 bool afterRto;
00209
00210
00211 bool ws_support;
00212 bool ws_enabled;
00213 bool snd_ws;
00214 bool rcv_ws;
00215 uint rcv_wnd_scale;
00216 uint snd_wnd_scale;
00217
00218
00219 bool ts_support;
00220 bool ts_enabled;
00221 bool snd_initial_ts;
00222 bool rcv_initial_ts;
00223 uint32 ts_recent;
00224 uint32 last_ack_sent;
00225 simtime_t time_last_data_sent;
00226
00227
00228 bool sack_support;
00229 bool sack_enabled;
00230 bool snd_sack_perm;
00231 bool rcv_sack_perm;
00232 uint32 start_seqno;
00233 uint32 end_seqno;
00234 bool snd_sack;
00235 bool snd_dsack;
00236 Sack sacks_array[MAX_SACK_BLOCKS];
00237 uint32 highRxt;
00238 uint32 pipe;
00239 uint32 recoveryPoint;
00240 uint32 sackedBytes;
00241 uint32 sackedBytes_old;
00242 bool lossRecovery;
00243
00244
00245 uint32 dupacks;
00246 uint32 snd_sacks;
00247 uint32 rcv_sacks;
00248 uint32 rcv_oooseg;
00249
00250
00251 uint32 maxRcvBuffer;
00252 uint32 usedRcvBuffer;
00253 uint32 freeRcvBuffer;
00254 uint32 tcpRcvQueueDrops;
00255 };
00256
00257
00258
00307 class INET_API TCPConnection
00308 {
00309 public:
00310
00311 int appGateIndex;
00312 int connId;
00313
00314
00315 IPvXAddress localAddr;
00316 IPvXAddress remoteAddr;
00317 int localPort;
00318 int remotePort;
00319
00320 protected:
00321 TCP *tcpMain;
00322
00323
00324 cFSM fsm;
00325
00326
00327 TCPStateVariables *state;
00328
00329
00330 TCPSendQueue *sendQueue;
00331 TCPReceiveQueue *receiveQueue;
00332 public:
00333
00334 TCPSACKRexmitQueue *rexmitQueue;
00335
00336 protected:
00337
00338 TCPAlgorithm *tcpAlgorithm;
00339
00340
00341 cMessage *the2MSLTimer;
00342 cMessage *connEstabTimer;
00343 cMessage *finWait2Timer;
00344 cMessage *synRexmitTimer;
00345
00346
00347 cOutVector *sndWndVector;
00348 cOutVector *rcvWndVector;
00349 cOutVector *rcvAdvVector;
00350 cOutVector *sndNxtVector;
00351 cOutVector *sndAckVector;
00352 cOutVector *rcvSeqVector;
00353 cOutVector *rcvAckVector;
00354 cOutVector *unackedVector;
00355
00356 cOutVector *dupAcksVector;
00357 cOutVector *pipeVector;
00358 cOutVector *sndSacksVector;
00359 cOutVector *rcvSacksVector;
00360 cOutVector *rcvOooSegVector;
00361
00362 cOutVector *sackedBytesVector;
00363 cOutVector *tcpRcvQueueBytesVector;
00364 cOutVector *tcpRcvQueueDropsVector;
00365
00366 protected:
00370 virtual TCPEventCode preanalyseAppCommandEvent(int commandCode);
00372 virtual bool performStateTransition(const TCPEventCode& event);
00374 virtual void stateEntered(int state);
00376
00379 virtual void process_OPEN_ACTIVE(TCPEventCode& event, TCPCommand *tcpCommand, cMessage *msg);
00380 virtual void process_OPEN_PASSIVE(TCPEventCode& event, TCPCommand *tcpCommand, cMessage *msg);
00381 virtual void process_SEND(TCPEventCode& event, TCPCommand *tcpCommand, cMessage *msg);
00382 virtual void process_CLOSE(TCPEventCode& event, TCPCommand *tcpCommand, cMessage *msg);
00383 virtual void process_ABORT(TCPEventCode& event, TCPCommand *tcpCommand, cMessage *msg);
00384 virtual void process_STATUS(TCPEventCode& event, TCPCommand *tcpCommand, cMessage *msg);
00386
00393 virtual bool tryFastRoute(TCPSegment *tcpseg);
00398 virtual TCPEventCode process_RCV_SEGMENT(TCPSegment *tcpseg, IPvXAddress src, IPvXAddress dest);
00399 virtual TCPEventCode processSegmentInListen(TCPSegment *tcpseg, IPvXAddress src, IPvXAddress dest);
00400 virtual TCPEventCode processSegmentInSynSent(TCPSegment *tcpseg, IPvXAddress src, IPvXAddress dest);
00401 virtual TCPEventCode processSegment1stThru8th(TCPSegment *tcpseg);
00402 virtual TCPEventCode processRstInSynReceived(TCPSegment *tcpseg);
00403 virtual bool processAckInEstabEtc(TCPSegment *tcpseg);
00405
00408 virtual bool processMSSOption(TCPSegment *tcpseg, const TCPOption& option);
00409 virtual bool processWSOption(TCPSegment *tcpseg, const TCPOption& option);
00410 virtual bool processSACKPermittedOption(TCPSegment *tcpseg, const TCPOption& option);
00411 virtual bool processSACKOption(TCPSegment *tcpseg, const TCPOption& option);
00412 virtual bool processTSOption(TCPSegment *tcpseg, const TCPOption& option);
00414
00417 virtual void process_TIMEOUT_2MSL();
00418 virtual void process_TIMEOUT_CONN_ESTAB();
00419 virtual void process_TIMEOUT_FIN_WAIT_2();
00420 virtual void process_TIMEOUT_SYN_REXMIT(TCPEventCode& event);
00422
00424 virtual TCPConnection *cloneListeningConnection();
00425
00427 virtual void initConnection(TCPOpenCommand *openCmd);
00428
00430 virtual void configureStateVariables();
00431
00433 virtual void selectInitialSeqNum();
00434
00436 virtual bool isSegmentAcceptable(TCPSegment *tcpseg);
00437
00439 virtual void sendSyn();
00440
00442 virtual void sendSynAck();
00443
00445 virtual void readHeaderOptions(TCPSegment *tcpseg);
00446
00448 virtual TCPSegment writeHeaderOptions(TCPSegment *tcpseg);
00449
00451 virtual TCPSegment addSacks(TCPSegment *tcpseg);
00452
00454 virtual uint32 getTSval(TCPSegment *tcpseg);
00455
00457 virtual uint32 getTSecr(TCPSegment *tcpseg);
00458 public:
00460 virtual void sendAck();
00461
00467 virtual bool sendData(bool fullSegmentsOnly, uint32 congestionWindow);
00468
00470 virtual bool sendProbe();
00471
00473 virtual void retransmitOneSegment(bool called_at_rto);
00474
00476 virtual void retransmitData();
00477
00479 virtual void sendRst(uint32 seqNo);
00481 virtual void sendRst(uint32 seq, IPvXAddress src, IPvXAddress dest, int srcPort, int destPort);
00483 virtual void sendRstAck(uint32 seq, uint32 ack, IPvXAddress src, IPvXAddress dest, int srcPort, int destPort);
00484
00486 virtual void sendFin();
00487
00492 virtual void sendSegment(uint32 bytes);
00493
00495 virtual void sendToIP(TCPSegment *tcpseg);
00496
00501 virtual TCPSegment *createTCPSegment(const char *name);
00502
00504 virtual void startSynRexmitTimer();
00505
00507 virtual void signalConnectionTimeout();
00508
00510 void scheduleTimeout(cMessage *msg, simtime_t timeout)
00511 {tcpMain->scheduleAt(simTime()+timeout, msg);}
00512
00513 protected:
00515 cMessage *cancelEvent(cMessage *msg) {return tcpMain->cancelEvent(msg);}
00516
00518 static void sendToIP(TCPSegment *tcpseg, IPvXAddress src, IPvXAddress dest);
00519
00521 virtual void sendToApp(cMessage *msg);
00522
00524 virtual void sendIndicationToApp(int code);
00525
00527 virtual void sendEstabIndicationToApp();
00528
00529 public:
00531 virtual void printConnBrief();
00533 static void printSegmentBrief(TCPSegment *tcpseg);
00535 static const char *stateName(int state);
00537 static const char *eventName(int event);
00539 static const char *indicationName(int code);
00541 static const char *optionName(int option);
00543 virtual void updateRcvQueueVars();
00544
00548 virtual unsigned short updateRcvWnd();
00549
00551 virtual void updateWndInfo(TCPSegment *tcpseg, bool doAlways=false);
00552
00553 public:
00557 TCPConnection(TCP *mod, int appGateIndex, int connId);
00558
00563 TCPConnection();
00564
00568 virtual ~TCPConnection();
00569
00576 virtual void segmentArrivalWhileClosed(TCPSegment *tcpseg, IPvXAddress src, IPvXAddress dest);
00577
00580 int getFsmState() const {return fsm.getState();}
00581 TCPStateVariables *getState() {return state;}
00582 TCPSendQueue *getSendQueue() {return sendQueue;}
00583 TCPSACKRexmitQueue *getRexmitQueue() {return rexmitQueue;}
00584 TCPReceiveQueue *getReceiveQueue() {return receiveQueue;}
00585 TCPAlgorithm *getTcpAlgorithm() {return tcpAlgorithm;}
00586 TCP *getTcpMain() {return tcpMain;}
00588
00594 virtual bool processTimer(cMessage *msg);
00595
00601 virtual bool processTCPSegment(TCPSegment *tcpSeg, IPvXAddress srcAddr, IPvXAddress destAddr);
00602
00608 virtual bool processAppCommand(cMessage *msg);
00609
00618 virtual bool isLost(uint32 seqNum);
00619
00626 virtual void setPipe();
00627
00636 virtual uint32 nextSeg();
00637
00641 virtual void sendDataDuringLossRecoveryPhase(uint32 congestionWindow);
00642
00646 virtual void sendSegmentDuringLossRecoveryPhase(uint32 seqNum);
00647
00651 virtual void sendOneNewSegment(bool fullSegmentsOnly, uint32 congestionWindow);
00652
00656 virtual uint32 convertSimtimeToTS(simtime_t simtime);
00657
00661 virtual simtime_t convertTSToSimtime(uint32 timestamp);
00662
00666 virtual bool isSendQueueEmpty();
00667
00668 };
00669
00670 #endif