On Wed, Sep 18, 2024 at 08:05:26AM +0200, Markus Armbruster wrote: > David Gibson writes: > > > write(2) might not write all the data it is given. Add a write_all_buf() > > helper to keep calling it until all the given data is written, or we get an > > error. > > > > Currently we use write_remainder() to do this operation in pcap_frame(). > > That's a little awkward since it requires constructing an iovec, and future > > changes we want to make to write_remainder() will be easier in terms of > > this single buffer helper. > > > > Signed-off-by: David Gibson > > --- > > pcap.c | 3 +-- > > util.c | 25 +++++++++++++++++++++++++ > > util.h | 1 + > > 3 files changed, 27 insertions(+), 2 deletions(-) > > > > diff --git a/pcap.c b/pcap.c > > index 46cc4b0d..e6b5ced4 100644 > > --- a/pcap.c > > +++ b/pcap.c > > @@ -86,9 +86,8 @@ static void pcap_frame(const struct iovec *iov, size_t iovcnt, > > .caplen = l2len, > > .len = l2len > > }; > > - struct iovec hiov = { &h, sizeof(h) }; > > > > - if (write_remainder(pcap_fd, &hiov, 1, 0) < 0 || > > + if (write_all_buf(pcap_fd, &h, sizeof(h)) < 0 || > > write_remainder(pcap_fd, iov, iovcnt, offset) < 0) > > debug_perror("Cannot log packet, length %zu", l2len); > > } > > diff --git a/util.c b/util.c > > index eede4e58..7db7c2e7 100644 > > --- a/util.c > > +++ b/util.c > > @@ -582,6 +582,31 @@ int do_clone(int (*fn)(void *), char *stack_area, size_t stack_size, int flags, > > #endif > > } > > > > +/* write_all_buf() - write all of a buffer to an fd > > + * @fd: File descriptor > > + * @buf: Pointer to base of buffer > > + * @len: Length of buffer > > + * > > + * Return: 0 on success, -1 on error (with errno set) > > + * > > + * #syscalls write > > + */ > > +int write_all_buf(int fd, const void *buf, size_t len) > > I'd call it write_all(), but that's strictly a matter of taste. I usually would too, but given we work pretty heavily with both plain buffers and iovs, I thought it was worth emphasising that this works on the former. > > +{ > > + const char *p = buf; > > + size_t left = len; > > + > > + while (left) { > > + ssize_t rc = write(fd, p, left); > > + > > + if (rc < 0) > > + return -1; > > Loop when errno == EINTR? Oh, good idea. -- David Gibson (he or they) | I'll have my music baroque, and my code david AT gibson.dropbear.id.au | minimalist, thank you, not the other way | around. http://www.ozlabs.org/~dgibson