NetBSD-Users archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

Re: minimum write size of SOCK_STREAM?



Sender

        int sock = cloexec_socket(AF_UNIX, SOCK_STREAM, 0);
        if (sock < 0) { ...
        }
        if (connect(sock, (struct sockaddr *)&ctl_addr,
                    offsetof(struct sockaddr_un, sun_path) +
strlen(ctl_addr.sun_path)) < 0) { ...
        }
        /* Send message */
#if 0 // NetBSD hack
        const ssize_t min = 856;
        if (len < min) {
                llog(ERROR_STREAM, logger, "bumping up buffer from %td to %td",
                     len, min);
                len = min;      /* this just writes pat of the string
                                 * buffer */
        }
#endif
        if (write(sock, msg, len) != len) { ...

where cloexec* is:

int cloexec_socket(int domain, int type, int protocol)
{
#ifdef SOCK_CLOEXEC
        return socket(domain, type|SOCK_CLOEXEC, protocol);
#else

receiver:

        delete_ctl_socket();    /* preventative medicine */
        ctl_fd = cloexec_socket(AF_UNIX, SOCK_STREAM, 0);
        if (ctl_fd == -1) { ...
        }
        /* to keep control socket secure, use umask */
#ifdef PLUTO_GROUP_CTL
        mode_t ou = umask(~(S_IRWXU | S_IRWXG));
#else
        mode_t ou = umask(~S_IRWXU);
#endif
        if (bind(ctl_fd, (struct sockaddr *)&ctl_addr,
                 offsetof(struct sockaddr_un, sun_path) +
                 strlen(ctl_addr.sun_path)) < 0) { ...
        }
        umask(ou);
#ifdef PLUTO_GROUP_CTL
       // some code never enabled
#endif
        /*
         * 5 (five) is a haphazardly chosen limit for the backlog.
         * Rumour has it that this is the max on BSD systems.
         */
        if (listen(ctl_fd, 5) < 0) { ...
        }
        ....
       feed ctl_fd into libevent with EV_READ|EV_PERSIST
       ....
        struct whack_message msg = {0};
        ssize_t n = fd_read(whackfd, &msg, sizeof(msg));
       // aka  ssize_t s = read(fd->fd, buf, nbytes);
        if (n <= 0) {
                llog_errno(ERROR_STREAM, whack_logger, -(int)n,
                           "read() failed in whack_handle(): ");
                return;
        }
        static uintmax_t msgnum;
        ldbgf(DBG_TMI, whack_logger, "whack message %ju; size=%zd",
msgnum++, n);

| struct fd: newref @0x6fe4fb574c68(0->1) (whack_handle_cb() +617
programs/pluto/rcv_whack.c)
| fd_accept: new fd@0x6fe4fb574c68 (whack_handle_cb() +617
programs/pluto/rcv_whack.c)
| whack message 1; size=400


On Fri, 31 Oct 2025 at 04:06, RVP <rvp%sdf.org@localhost> wrote:
>
> On Thu, 30 Oct 2025, Andrew Cagney wrote:
>
> > I've what I thought was some stock (if somewhat old) code that used a
> > SOCK_STREAM for communication between a daemon and its control
> > program.
> >
>
> What domain? AF_LOCAL or AF_INET{,6}?
>
> > Because the messages were all below the socket's buffer size (8K
> > according to getsockopt()), my understanding is partial reads
> > shouldn't happen.
> >
>
> With SOCK_STREAM, partial reads can always happen. If you want whole-packet
> reads (< MTU size) you'll have to use SOCK_DGRAM or SOCK_SEQPACKET; or send
> the message size too, so that the server can loop until it gets the whole
> packet.

yea, might be time to update to SOCK_SEQPACKET

> Let's see your code.
>
> -RVP


Home | Main Index | Thread Index | Old Index