|
Home > Archive > Unix Programming > January 2004 > sending images over a socket
You are viewing an archived Text-only version of the thread.
To view this thread in it's original format and/or if you want to reply to
this thread please [click here]
| Author |
sending images over a socket
|
|
| Joaquin López 2004-01-23, 5:07 pm |
| Hello, I'm writing a program for sending images over a socket.
The size of the image is 640x480 pixels in pgm format.
The problem is that when the client sends the image to the server (307200
bytes) the server only receives 65533.
The thing is, is there any limits on the information sent from one point
(send) to another (recv)?.
In such case, how is the way I have to send one image of 640x480 pixels?
Perhaps in two times?
Thank you for your attention,
Joaquin.
| |
| Fletcher Glenn 2004-01-23, 5:07 pm |
|
Joaquin López wrote:quote:
> Hello, I'm writing a program for sending images over a socket.
>
> The size of the image is 640x480 pixels in pgm format.
>
> The problem is that when the client sends the image to the server (307200
> bytes) the server only receives 65533.
>
> The thing is, is there any limits on the information sent from one point
> (send) to another (recv)?.
> In such case, how is the way I have to send one image of 640x480 pixels?
> Perhaps in two times?
>
> Thank you for your attention,
> Joaquin.
>
>
Let me guess: you wrote the image to the socket with a single write
statement? And now you expect to read the image with a single read??
That's now how it is done. The transport (the stuff behind the socket)
cannot handle messages of that size, and it breaks up the message into
pieces which are then sent to the receiving socket. When you read, you
will only get part of the message, and so you must repeatedly read the
socket until you get all of the expected data. How, you ask, do you
know when you have all of the data?? You know because you sent the
length of the message before you sent the message.
--
Fletcher Glenn
| |
| Lew Pitcher 2004-01-23, 5:07 pm |
| On Mon, 8 Dec 2003 17:14:30 +0100, "Joaquin López" <lsanchez@lsi.uji.es> wrote:
quote:
>Hello, I'm writing a program for sending images over a socket.
>
>The size of the image is 640x480 pixels in pgm format.
>
>The problem is that when the client sends the image to the server (307200
>bytes) the server only receives 65533.
>
>The thing is, is there any limits on the information sent from one point
>(send) to another (recv)?.
>
>In such case, how is the way I have to send one image of 640x480 pixels?
>Perhaps in two times?
It is likely that you don't understand TCP communications and/or stream sockets.
A recv() call only returns the data received up to that point. There is no
synchronization between the data sent and the data received. That is to say that
although you may /send/ massive amounts of data in one call, the corresponding
recv() call does not have to (and usually won't) receive the data in one recv()
call. This is the nature of TCP/IP, and is not a flaw in the sockets
implementation, or anything else.
It appears that your /first/ recv() gets 64k of the data sent. You need to
continue issueing recv() calls (and appending the results together) until you
receive all the data you sent. How you determine that you have received /all/
the data depends on your sending program:
- It may close it's sending socket when it has sent all the data; the receiver
will detect this as an end-of-file on the receiving socket, or
- It may send the length of the data as a data item prior to the data itself;
the receiver must fetch this length first, then recv() until the length has
been exhausted, or
- It may send a sentinal in the data stream to mark the end of the data; the
receiver must be sensitive to this sentinal and trim it's recv()d data
according to the placement of the sentinal, or
- The sender and receiver always know exactly how much data is transferred as
the sender always sends a fixed amount of data, and the receiver knows what
that fixed amount is; both sender and receiver must agree on what this amount
is prior to the transmission of the data.
In all cases, both sender application and receiver application must agree upon
the strategy to be used to detect end of data, and both applications must be
coded to enact that strategy.
--
Lew Pitcher
IT Consultant, Enterprise Technology Solutions
Toronto Dominion Bank Financial Group
(Opinions expressed are my own, not my employers')
| |
| Joseph Dionne 2004-01-23, 5:07 pm |
| I stand corrected, Lew, any of the alternatives you have suggested will
work just fine, except perhaps disconnect which might be delivered OOB,
causing a less than full read.
However, a "common" practice for binary data transmission is the use a
length bytes, two or four bytes (I recommend NBO -- network byte order)
to eliminate the need for concern over Endian differences between client
and server.
HTML, one of the most popular STREAMs over sockets is token, and "line",
delimited, but a "sentinel" in a binary stream would require one to use
transparency to allow the "end sentinel" appearing in the image being sent.
Just a thought. I find lengths bytes serve two purposes; 1) the
receiver knows how much data to perhaps malloc() a buffer, 2) restores
message structure to the TCP STREAM if one plans to use the connection
multiple times.
Just a thought.
Lew Pitcher wrote:quote:
> On Mon, 08 Dec 2003 17:48:46 GMT, Joseph Dionne <jdionne@sdcnov1.sdcweb.net>
> wrote:
>
>
>
>
> by whom?
>
>
>
>
> Or any one of the alternate strategies, like
> - having the source send a sentinal value at the end of the data, or
> - having the source close it's outbound data stream after it has written
> the last byte of data, or
> - having the source and receiver programs agree that the transferred data will
> always be a specific, fixed number of octets. The source sends exactly that
> number of octets, and the receiver reads exactly that number of octets
> preprogrammed.
>
>
>
> [snip]
>
| |
| Joaquin =?ISO-8859-15?Q?L=F3pez?= 2004-01-23, 5:08 pm |
| Lew Pitcher wrote:
quote:
> On Mon, 8 Dec 2003 17:14:30 +0100, "Joaquin López" <lsanchez@lsi.uji.es>
> wrote:
>
>
> It is likely that you don't understand TCP communications and/or stream
> sockets.
>
> A recv() call only returns the data received up to that point. There is no
> synchronization between the data sent and the data received. That is to
> say that although you may /send/ massive amounts of data in one call, the
> corresponding recv() call does not have to (and usually won't) receive the
> data in one recv() call. This is the nature of TCP/IP, and is not a flaw
> in the sockets implementation, or anything else.
>
> It appears that your /first/ recv() gets 64k of the data sent. You need to
> continue issueing recv() calls (and appending the results together) until
> you receive all the data you sent. How you determine that you have
> received /all/ the data depends on your sending program:
> - It may close it's sending socket when it has sent all the data; the
> receiver
> will detect this as an end-of-file on the receiving socket, or
> - It may send the length of the data as a data item prior to the data
> itself;
> the receiver must fetch this length first, then recv() until the length
> has been exhausted, or
> - It may send a sentinal in the data stream to mark the end of the data;
> the
> receiver must be sensitive to this sentinal and trim it's recv()d data
> according to the placement of the sentinal, or
> - The sender and receiver always know exactly how much data is transferred
> as
> the sender always sends a fixed amount of data, and the receiver knows
> what that fixed amount is; both sender and receiver must agree on what
> this amount is prior to the transmission of the data.
>
> In all cases, both sender application and receiver application must agree
> upon the strategy to be used to detect end of data, and both applications
> must be coded to enact that strategy.
>
>
Thank you to all of us for helping me. The problem was exactly this, I
expected recv() will get all the data in only one call. It was my fault.
|
|
|
|
|