LinuxQuestions.org
Visit Jeremy's Blog.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Linux Forums > Linux - Networking
User Name
Password
Linux - Networking This forum is for any issue related to networks or networking.
Routing, network cards, OSI, etc. Anything is fair game.

Notices


Reply
  Search this Thread
Old 05-17-2007, 10:37 PM   #1
rendition
LQ Newbie
 
Registered: May 2007
Posts: 3

Rep: Reputation: 0
Random number of reads from a socket


Hi,

I'm just following the Steven's seminal networking programming book and bounced into something which I cannot make sense of.

From a simple TCP server, I'm writing a string (which is about 20 chars) one byte at a time and I read it from a client program to a string consisting of 100 chars, again under a loop. And I'm counting the number of reads.

Each time I run the client I get completely random number of reads. Sometimes the count is one, so the entire string is read on a iteration. Sometimes it takes about five, three, four or six iterations.

If anyone could point me to a direction to get more info regarding this would greatly be appreciated.

Thanks in advance.
 
Old 05-18-2007, 07:51 PM   #2
osor
HCL Maintainer
 
Registered: Jan 2006
Distribution: (H)LFS, Gentoo
Posts: 2,450

Rep: Reputation: 78
Could you post some code?
 
Old 05-21-2007, 02:36 AM   #3
rendition
LQ Newbie
 
Registered: May 2007
Posts: 3

Original Poster
Rep: Reputation: 0
Sure.

Here's the part of the client code where it reads the server reply.

Code:
        count = 0;
        while ( (n = read(sockfd, recvline, MAXLINE)) > 0) {
                recvline[n] = 0;        /* null terminate */
                count++;
                if (fputs(recvline, stdout) == EOF)
                        err_sys("fputs error");
        }
        printf("count = %d\n", count);
And here's the server code,

Code:
        
        snprintf(buff, sizeof(buff), "%.24s\r\n", ctime(&ticks));

        for (i = 0; i < strlen(buff); i++) {
                Write(connfd, &(buff[i]), 1);
        }
 
Old 05-21-2007, 07:34 PM   #4
osor
HCL Maintainer
 
Registered: Jan 2006
Distribution: (H)LFS, Gentoo
Posts: 2,450

Rep: Reputation: 78
I don’t see the problem…

What you’re describing (i.e., the variable count being different each time you run client) is typical of network programming. In fact, this is why you use a loop in the first place (you are not guaranteed that a single read() will read the full amount of data). With a normal call to read(), the function waits for any data to be available (unless you made your socket “nonblocking”), and it delivers data as soon as it becomes available. Since you mentioned Steven’s book, I thought I might quote a small section (under fair use, of course) to elucidate the situation:
Quote:
Originally Posted by UNIX® Network Programming Volume 1, Third Edition: The Sockets Networking API, Chapter 1, Section 2: A Simple Daytime Client
We read the server's reply and display the result using the standard I/O fputs function. We must be careful when using TCP because it is a byte-stream protocol with no record boundaries. The server's reply is normally a 26-byte string of the form
Code:
Mon May 26 20 : 58 : 40 2003\r\n
where \r is the ASCII carriage return and \n is the ASCII linefeed. With a byte-stream protocol, these 26 bytes can be returned in numerous ways: a single TCP segment containing all 26 bytes of data, in 26 TCP segments each containing 1 byte of data, or any other combination that totals to 26 bytes. Normally, a single segment containing all 26 bytes of data is returned, but with larger data sizes, we cannot assume that the server's reply will be returned by a single read. Therefore, when reading from a TCP socket, we always need to code the read in a loop and terminate the loop when either read returns 0 (i.e., the other end closed the connection) or a value less than 0 (an error).
If you want to read the data all at once, you might use the standard function recv() instead of read(). A call to read() is internally translated to a call to recv() with no flags. You can, however, use recv() directly, and specify the standard flag MSG_WAITALL. From the standard:
Quote:
Originally Posted by IEEE Std 1003.1 — recv() manual
MSG_WAITALL
On SOCK_STREAM sockets this requests that the function block until the full amount of data can be returned. The function may return the smaller amount of data if the socket is a message-based socket, if a signal is caught, if the connection is terminated, if MSG_PEEK was specified, or if an error is pending for the socket.
Hope that helps.
 
Old 05-21-2007, 08:03 PM   #5
rendition
LQ Newbie
 
Registered: May 2007
Posts: 3

Original Poster
Rep: Reputation: 0
Ah right. That cleared up all the doubts. Thanks heaps osor!
 
  


Reply



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
random java number?!?!?! trscookie Programming 2 07-18-2006 12:10 PM
Random number generation jacques83 Programming 5 02-04-2006 12:38 PM
Generate random number with C++ TruongAn Programming 5 11-09-2005 12:01 AM
Running out of entropy & /dev/random reads are blocking slacky Linux - General 1 06-15-2005 09:53 PM
I need random number in C ... purpleburple Programming 4 10-28-2002 04:37 AM

LinuxQuestions.org > Forums > Linux Forums > Linux - Networking

All times are GMT -5. The time now is 05:07 AM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration