Add a sshbuf_read() that attempts to read(2) directly in to a
authordjm <djm@openbsd.org>
Sat, 22 Jan 2022 00:43:43 +0000 (00:43 +0000)
committerdjm <djm@openbsd.org>
Sat, 22 Jan 2022 00:43:43 +0000 (00:43 +0000)
sshbuf; ok markus@

usr.bin/ssh/sshbuf-misc.c
usr.bin/ssh/sshbuf.h

index 38567b3..e30fac5 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: sshbuf-misc.c,v 1.17 2021/08/11 05:21:32 djm Exp $    */
+/*     $OpenBSD: sshbuf-misc.c,v 1.18 2022/01/22 00:43:43 djm Exp $    */
 /*
  * Copyright (c) 2011 Damien Miller
  *
@@ -26,6 +26,7 @@
 #include <string.h>
 #include <resolv.h>
 #include <ctype.h>
+#include <unistd.h>
 
 #include "ssherr.h"
 #define SSHBUF_INTERNAL
@@ -265,3 +266,39 @@ sshbuf_find(const struct sshbuf *b, size_t start_offset,
                *offsetp = (const u_char *)p - sshbuf_ptr(b);
        return 0;
 }
+
+int
+sshbuf_read(int fd, struct sshbuf *buf, size_t maxlen, size_t *rlen)
+{
+       int r, oerrno;
+       size_t adjust;
+       ssize_t rr;
+       u_char *d;
+
+       if (rlen != NULL)
+               *rlen = 0;
+       if ((r = sshbuf_reserve(buf, maxlen, &d)) != 0)
+               return r;
+       rr = read(fd, d, maxlen);
+       oerrno = errno;
+
+       /* Adjust the buffer to include only what was actually read */
+       if ((adjust = maxlen - (rr > 0 ? rr : 0)) != 0) {
+               if ((r = sshbuf_consume_end(buf, adjust)) != 0) {
+                       /* avoid returning uninitialised data to caller */
+                       memset(d + rr, '\0', adjust);
+                       return SSH_ERR_INTERNAL_ERROR; /* shouldn't happen */
+               }
+       }
+       if (rr < 0) {
+               errno = oerrno;
+               return SSH_ERR_SYSTEM_ERROR;
+       } else if (rr == 0) {
+               errno = EPIPE;
+               return SSH_ERR_SYSTEM_ERROR;
+       }
+       /* success */
+       if (rlen != NULL)
+               *rlen = (size_t)rr;
+       return 0;
+}
index 4ff529a..9624c43 100644 (file)
@@ -1,4 +1,4 @@
-/*     $OpenBSD: sshbuf.h,v 1.24 2022/01/01 05:55:06 jsg Exp $ */
+/*     $OpenBSD: sshbuf.h,v 1.25 2022/01/22 00:43:43 djm Exp $ */
 /*
  * Copyright (c) 2011 Damien Miller
  *
@@ -310,6 +310,10 @@ int sshbuf_load_file(const char *, struct sshbuf **)
 int sshbuf_write_file(const char *path, struct sshbuf *buf)
     __attribute__((__nonnull__ (2)));
 
+/* Read up to maxlen bytes from a fd directly to a buffer */
+int sshbuf_read(int, struct sshbuf *, size_t, size_t *)
+    __attribute__((__nonnull__ (2)));
+
 /* Macros for decoding/encoding integers */
 #define PEEK_U64(p) \
        (((u_int64_t)(((const u_char *)(p))[0]) << 56) | \