Date: Fri, 15 Nov 1996 13:58:03 -0700 (MST) From: Terry Lambert <terry@lambert.org> To: fenner@parc.xerox.com (Bill Fenner) Cc: terry@lambert.org, fenner@parc.xerox.com, scrappy@ki.net, jdp@polstra.com, hackers@freebsd.org Subject: Re: Sockets question... Message-ID: <199611152058.NAA26903@phaeton.artisoft.com> In-Reply-To: <96Nov15.113305pst.177557@crevenia.parc.xerox.com> from "Bill Fenner" at Nov 15, 96 11:32:55 am
next in thread | previous in thread | raw e-mail | index | archive | help
> >So at the "read" interface, you *can* count on it arriving in the > >same sized chunks as you wrote it > > No, you can *never* count on that, since non-blocking reads from a stream > socket return as much data as is available, which could be less than you > asked for. See soo_read() (or soo_rw() in earlier BSD's) and soreceive(). By default, the sockets are blocking. You have to go out of your way to make them non-blocking (ie: loading the gun before you can shoot yourself in the foot). > 4.4BSD introduced the MSG_WAITALL flag, so if you use recv() or any of its > friends you can ask for your whole request to be performed. This is, of > course, not portable, and MSG_WAITALL won't even do the trick if your > request is larger than the socket's high water mark (e.g. SO_RECVBUF). This makes sense. But on a blocking socket, it doesn't make sense to have to issue multiple system calls to read chunks of a whole message when you aren't going to do anything with it until all the reads have been satisfied? It makes sense to do it on the server, if you have a server getting messaged from a bunch of sources, but that's just moving the packet assembly into user space. You'd expect the server to have a higher premium on interleaving operations than on atomicity of transactions. Even so, this only becomes a problem if you send "outrageously large" packets in a single write. You'd think that you could move it back down into kernel space by the select not coming true until all frags had been reassembled. I could see SO_RECVBUF putting a limit on your biggest message size in that case. The MSG_WAITALL seems like, even without the flag, it would be the default behaviour for the read. The alternative is to push the "frag" assembly ("frags" in this case being buffers larger than SO_RECVBUF cut into SO_RECVBUF) up into the user program, an dictate to the user how he must code a state machine in user space in order to use the interface. Ugh, copy overhead. Bleah. 8-(. I suppose one very real possibility is that he's trying to send huge packets... most of the drivers don't support them, and the DEC driver supports them only with a couple of patches that Matt and Amancio beat out between them a while back... If it's huge packets, he's probably SOL, and needs to redesign his stream formatting. Anyway, let's wait and see what clarifications he has to offer before we speculate ourselves to death. 8-). Terry Lambert terry@lambert.org --- Any opinions in this posting are my own and not those of my present or previous employers.
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199611152058.NAA26903>