Subject: Re: sendto() and ENOBUFS question..
To: Jonathan Stone <jonathan@DSG.Stanford.EDU>
From: sudog <sudog@sudog.com>
List: tech-net
Date: 05/14/2002 17:18:48
On Tuesday 14 May 2002 14:20, Jonathan Stone wrote:
>
> You could use setsockopt() juggle the low watermark once you decide
> you've sent "too much".
> 
> See man 4 setsockopt, SO_SNDLOWAT, SO_RCVLOWAT.

Looks like this didn't work. The following:

getsockopt(mysock, SOL_SOCKET, SO_SNDLOWAT, (void *)&counter, (socklen_t 
*)&counter2);
printf("getsockopt counter returned: %ld\n", counter);

Shows that the default amount is 2048. I tried setting it to 4096 
(successfully, if the getsockopt() was any indication) and I tried shrinking 
the size of the packet I was sending with sendto() but I was still flooded 
with ENOBUFS.

So, off to spelunk inside the kernel. Looks like there's a relevant macro..

in: sys/socketvar.h

#define sowriteable(so) \
        ((sbspace(&(so)->so_snd) >= (so)->so_snd.sb_lowat && \
            (((so)->so_state&SS_ISCONNECTED) || \
              ((so)->so_proto->pr_flags&PR_CONNREQUIRED)==0)) || \
         ((so)->so_state & SS_CANTSENDMORE) || \
         (so)->so_error)

This is the only place I can find that references the low watermark, and it 
looks like it's geared for streamed sockets.

Further, it looks like that stuff is only called by soo_poll, which I can't 
seem to find anywhere but attached to the poll(2) command. Let's see..

I converted it to use poll(2) but the same result happened.
So is the low water mark only used with streaming sockets then?

Thanks for your help; I'll look at this some more than I get home.

-Marc Tooley