Connection Oriented Vs. Connectionless
TCP and UDP are protocols that live up at layer 4. Quick recap, down at layer 2, our data link layer is where our MAC addresses live and protocols like ARP. Layer 3 is the network layer, it’s where our Internet Protocol lives and we use IP addresses. Layer 4 is the transport layer, here is where TCP and UDP live.
TCP is the Transmission Control Protocol. UDP is the User Datagram Protocol. The big difference between the two, TCP is described as connection oriented, whereas UDP is connectionless.
Since TCP is connection oriented, it includes a mechanism for validating that there is reliable communication between the two endpoints before it actually starts transmitting any real data. This is accomplished through the 3-way handshake.
The 3-way handshake consists of 3 packets. The initiator of the TCP session first sends an empty TCP packet with the SYN, or synchronize, flag set. The receiver then responds to the synchronize request with an acknowledgement of receiving the synchronize request, setting the ACK, or acknowledge, flag and also setting the SYN flag to request its own synchronization. This packet is the SYN-ACK step. The initiator receives the SYN-ACK response, recognizes that its synchronization request is acknowledged, and finally sends an ACK to the receiver, to acknowledge its synchronize request.
In this manner, both parties can now be sure there is reliable communication at this moment between the two devices. The TCP session is established, and payload data may now be exchanged.
Acknowledgements are sent for each segment. This allows TCP to continuously validate successful and reliable communication between the parties, throughout the duration of the session.
The TCP header is 20 to 60 bytes long. TCP, as well as UDP, use port numbers for an ‘address’. The source port and destination port are 16 bit sections of the header. All port numbers are valid except for 0, so this allows for a total number of ports of 2^16 – 1 = 65535.
The TCP header includes a sequence number that is randomly generated by the transmitter at the start of a session. The primary thing that makes TCP connection oriented is that it includes an acknowledgement number to acknowledge that a particular sequence number is received. TCP requires the other side to acknowledge that it did indeed receive the previous segment or window. The individual sequence numbers are acknowledged in this manner, so TCP may be aware if any pieces were not received.
The URG flag, along with the urgent pointer, is telling the receiver to process this packet right away, do not wait for the full segment to buffer.
The ACK flag is set, along with the acknowledgement number to acknowledge a sequence number was received.
The PSH flag, called push, is very similar to URG, as it’s telling the higher level protocol to process this packet right away and don’t wait for the others. Where this differs from URG is that URG is for the network stack, where PSH is for the higher level protocols.
The RST, or reset flag, is resetting the connection. This causes TCP to assume there is no longer reliable communication and a new 3-way handshake must take place before data transmission may occur again.
SYN flag, as we discussed above, is used in the 3-way handshake for initiating a TCP session and establishing that two way communication is possible.
The FIN, or finished flag goes at the very end of the conversation to say we are finished and this session is being closed. This has a similar effect to RST, where a new 3-way handshake is required to start transmitting again. However, where RST assumes another 3-way handshake is expected immediately, FIN assumes the communication is finished with.
Now for Window Size. You may be thinking that acknowledging each and every packet seems inefficient and potentially a huge performance impact on higher latency connections. You’d be absolutely correct! TCP has a mechanism called windowing, which allows for the transmission of a lot of data without necessarily having to give an acknowledgement back. At the agreed upon window size, the transmitter will send a window of data, and then at that point, at that agreed upon size, the receiver will send an acknowledgement back for the sequences received. TCP does have a sliding window, such that if one of these sequences are missed, then it will significantly shrink that window size and only send a smaller amount of data. That window will slowly get larger and larger, such that it can take advantage of your link’s reliability and not have to have the overhead of sending acknowledgements back and forth.
The header for the user datagram protocol is only 8 bytes. It’s a far more simple protocol, just in the header size alone there’s substantial overhead savings, at least 12 bytes per packet! Being that UDP is so much more simple, it’s also far less robust.
So what goes into an 8 byte header? Well, UDP uses source and destination port number just like TCP, so that’s 2 bytes each for the source port and destination port address. Then we have a field indicating the total length of the UDP packet with the data, which is another 2 bytes. Finally, we have a 2 byte checksum field to validate the data was transmitted without degradation, and that’s it!
We don’t have anything else in the UDP header, no flags or anything. UDP is really just an absolutely minimally sized header to be able to send a datagram, to send data out there and stream it. See, since UDP doesn’t include any acknowledgement or sequence flags of any kind in its header, it has no method of validating 2-way communication. That’s not to say we can’t do 2-way communication with UDP, we just can’t confirm it was reliable.
UDP has very little overhead, and that’s really where you would want to use UDP, is if you don’t really care about the reliability of that stream. In some cases, such as VoIP and video conference, it doesn’t matter if we detect that a packet was lost. The reason being, once we detect it was lost, there’s no point in requesting it again because the time for that packet to be useful has already passed.