Ali Ahmed
Ali Ahmed

Reputation: 1839

Receive packet by packet data from TCP socket?

I have a TCP socket on which I receive video stream. I want to receive data as packet by packet from socket so that I could remove the packet header and keep the only stream data. How can I do this??

Any help will be appreciated.

Upvotes: 13

Views: 16623

Answers (4)

Zuljin
Zuljin

Reputation: 2640

TCP is a stream protocol and it doesn't guarantee that when you call socket read function you will receive one, complete packet. UDP or SCTP are packet oriented protocols and guarantee this. For TCP you can get part of the packet or few packet at once. You have to build your own application protocol on top of TCP and fragment/defragment messages manually.

Upvotes: 3

Mark Tolonen
Mark Tolonen

Reputation: 177674

TCP is a streaming protocol. You get bytes with no message boundaries. The solution is to buffer all your reads and extract/process full video packets from the buffer.

Algorithm:

  1. Initialize an empty buffer.
  2. Examine buffer for a complete packet.
  3. If found, remove complete packet from beginning of buffer and process it.
  4. If not found, append data from a recv() to the buffer and go to #2.

What a "complete packet" contains should be defined by the video streaming protocol.

Upvotes: 5

doron
doron

Reputation: 28892

As others have mentioned, TCP is a streaming protocol. This means from an API point of view, there is no concept of "packet". As a user, all you can expect is a stream of data.

Internally, TCP will break the stream into segments that can be placed into IP packets. These packets will be sent along with control data, over IP, to the remote end. The remote end will receive these IP packets. It may discard certain IP packets (in the case of duplicates), reorder the packets or withhold data until earlier packets have arrived. All this is internal to TCP meaning the concept of a "TCP packet" is meaningless.

You might be able to use raw sockets to receive the raw IP packets but this will mean you will have to reimplement much of the TCP stack (like sending ACKs and adjusting window size) to get the remote end to perform correctly. You do not want to do this.

UDP, on the other hand, is a datagram protocol. This means that the user is made aware of how the data is sent over the network. If the concept of packets or datagrams are important to you, you will need to build your own protocol on top of UDP.

Upvotes: 7

cnicutar
cnicutar

Reputation: 182639

You can't. TCP doesn't work with packets / messages etc. TCP works with bytes. You get a stream of bytes. The problem is that there's no guarantee reagarding the number of bytes you'll get each time you read from a socket. The usual way to handle this:

  • When you want to send a "packet" include as the first thing a length
  • When you read stuff from a socket make sure you read at least that length

Your message could be:

|Message Length:4bytes|Additional header Information:whatever1|Message Data:whatever2|

What you'll then have to do is read 4 bytes and then read as much as those 4 bytes tell you. Then you'll be able to strip the header and get the data.

Upvotes: 21

Related Questions