-
Notifications
You must be signed in to change notification settings - Fork 0
TCP Protocol
TCP (Transmission Control Protocol) with full state machine implementation.
TCP provides reliable, ordered, error-checked delivery of data between processes on different hosts in JNode's network stack. It is a connection-oriented protocol built on top of IP, implementing a complex state machine to manage connection lifecycle, flow control, and reliable data transfer. JNode's TCP implementation follows RFC 793 closely, with support for the standard TCP states: CLOSED, LISTEN, SYN_SENT, SYN_RECV, ESTABLISHED, FIN_WAIT_1, FIN_WAIT_2, CLOSING, TIME_WAIT, CLOSE_WAIT, and LAST_ACK.
The TCP layer sits above the IPv4 layer and below the socket abstraction. When a segment arrives, TCPProtocol receives it, validates the checksum, looks up the corresponding TCPControlBlock (or creates one for a listening socket), and processes the segment according to the current connection state. The implementation uses TCPTimer for retransmission and timeout handling, and maintains separate TCPInChannel and TCPOutChannel objects for each connection to handle data flow.
| Class / File | Role |
|---|---|
net/src/net/org/jnode/net/ipv4/tcp/TCPProtocol.java |
Main TCP protocol handler; implements IPv4Protocol interface; manages control blocks, timers, and socket factory |
net/src/net/org/jnode/net/ipv4/tcp/TCPHeader.java |
TCP header parsing and construction; handles flags (SYN, ACK, FIN, RST, PSH, URG), sequence/ack numbers, window size |
net/src/net/org/jnode/net/ipv4/tcp/TCPControlBlock.java |
Connection state machine; manages per-connection state, receive/send channels, timeouts |
net/src/net/org/jnode/net/ipv4/tcp/TCPConstants.java |
TCP constants: flags, state values, timeouts, buffer sizes |
net/src/net/org/jnode/net/ipv4/tcp/TCPInChannel.java |
Incoming data handling; sequence number validation, reassembly, receive buffer |
net/src/net/org/jnode/net/ipv4/tcp/TCPOutChannel.java |
Outgoing data handling; segment transmission, retransmission, acknowledgment processing |
net/src/net/org/jnode/net/ipv4/tcp/TCPTimer.java |
Timer for retransmission timeouts, keep-alive, and connection state transitions |
net/src/net/org/jnode/net/ipv4/tcp/TCPSocketImpl.java |
Bridge between java.net.Socket API and TCPControlBlock |
TCP connections are established via a three-way handshake:
-
Client sends SYN: Client calls
appConnect(), which sends a SYN segment with an initial sequence number (ISN) from TCPOutChannel, transitioning state to SYN_SENT - Server responds with SYN-ACK: Server's listening TCPControlBlock receives SYN, creates a child connection, sends SYN-ACK, and transitions to SYN_RECV
- Client sends ACK: Client receives SYN-ACK, transitions to ESTABLISHED; server receives ACK and also transitions to ESTABLISHED
In JNode, this is implemented in TCPControlBlock:
- Active open:
appConnect()sends SYN and waits for ESTABLISHED state (with TCP_MAXCONNECT retries) - Passive open:
appListen()sets state to LISTEN;receiveListen()creates child control blocks on SYN receipt
Once ESTABLISHED, data flows bidirectionally:
-
appSendData()breaks data into chunks (up to MSS), creates TCP headers with current sequence/ack numbers, and sends via TCPOutChannel -
appRead()reads from TCPInChannel receive buffer, blocking until data is available - Each segment carries a sequence number; received data is acknowledged via ACK segments
- Flow control uses the window size field: receiver advertises available buffer space
Connection closure uses a four-way handshake:
-
Active closer sends FIN:
appClose()sends FIN, transitions to FIN_WAIT_1 (or LAST_ACK if in CLOSE_WAIT) - Peer acknowledges FIN: Peer sends ACK; active closer transitions to FIN_WAIT_2
- Peer sends FIN: After its application closes, peer sends FIN
- Active closer acknowledges FIN: Sends final ACK, transitions to TIME_WAIT for 2MSL (2 * Maximum Segment Lifetime), then to CLOSED
In JNode, receiveEstablished(), receiveFinWait1(), receiveFinWait2() handle incoming FIN segments and state transitions. The TIME_WAIT state waits 400ms (simulating 2MSL) before closing.
TCPHeader parses the 20-byte (minimum) TCP header from SocketBuffer:
- Source/destination ports (16-bit each)
- Sequence and acknowledgment numbers (32-bit each)
- Flags: URG, ACK, PSH, RST, SYN, FIN (6 bits)
- Window size (16-bit): flow control advertisement
- Checksum (16-bit): covers pseudo-header + TCP header + data
- Urgent pointer (16-bit)
The checksum uses a pseudo-header derived from the IPv4 header (source/destination addresses, protocol, TCP length).
-
State machine complexity: The 11 TCP states and their transitions are complex; incorrect segment handling can leave connections in inconsistent states. JNode handles most RFC 793 cases but some edge cases may behave unexpectedly.
-
Retransmission timing: TCPTimer runs every 500ms (TCP_TIMER_PERIOD); retransmission timeout is critical for performance. Too aggressive retransmission causes unnecessary traffic; too conservative causes delays.
-
Window size: Default TCP_MAXWIN is 1024 bytes, which is quite small compared to modern networks. This limits throughput on high-bandwidth connections.
-
No congestion control: The current implementation does not implement sophisticated congestion control (slow start, congestion avoidance). It uses a simple retransmission model without CWND management.
-
Maximum Segment Size: Default TCP_DEFAULT_MSS is 536 bytes, limiting single-send chunk sizes. Actual MSS may be limited by underlying network MTU.
-
Checksum validation: TCPHeader validates the checksum on receive; invalid segments are dropped and stat.badsum incremented. The checksum uses IPv4 pseudo-header.
-
Reset handling: RST segments can arrive at any time;
receiveProcessReset()handles state-specific responses (notifying connection refused/reset to waiting threads). -
Blocking operations: appConnect(), appAccept(), appRead(), appSendData() can block; timeout is TCP_DEFAULT_TIMEOUT (10 seconds).
- Network-Stack — Parent network subsystem documentation
- Network-Layers — Protocol layering architecture including TransportLayer
- UDP-Protocol — Alternative transport protocol (connectionless, unreliable)
- Sockets-Implementation — Bridge between java.net API and TCP stack
- Socket-Buffer — Packet container used throughout network stack