bug-gnulib
[Top][All Lists]
Advanced

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

[PATCH] af_alg: avoid gotos


From: Paul Eggert
Subject: [PATCH] af_alg: avoid gotos
Date: Wed, 9 May 2018 11:53:55 -0700

* lib/af_alg.c (afalg_buffer, afalg_stream): Rewrite to avoid
gotos, as they were a source of unreliability and made the code a
bit harder to follow.
---
 ChangeLog    |  5 ++++
 lib/af_alg.c | 76 ++++++++++++++++++++++------------------------------
 2 files changed, 37 insertions(+), 44 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 818d3a602..9c40bd672 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,10 @@
 2018-05-09  Paul Eggert  <address@hidden>
 
+       af_alg: avoid gotos
+       * lib/af_alg.c (afalg_buffer, afalg_stream): Rewrite to avoid
+       gotos, as they were a source of unreliability and made the code a
+       bit harder to follow.
+
        af_alg: don’t leak file descriptors into children
        * lib/af_alg.c (alg_socket): Use SOCK_CLOEXEC when creating sockets.
        This code should be compiled only on recent GNU/Linux platforms
diff --git a/lib/af_alg.c b/lib/af_alg.c
index c85140a33..64bde8d74 100644
--- a/lib/af_alg.c
+++ b/lib/af_alg.c
@@ -74,25 +74,23 @@ afalg_buffer (const char *buffer, size_t len, const char 
*alg,
 
   int result;
 
-  do
+  for (;;)
     {
       ssize_t size = (len > BLOCKSIZE ? BLOCKSIZE : len);
       if (send (ofd, buffer, size, MSG_MORE) != size)
         {
           result = -EIO;
-          goto out_ofd;
+          break;
         }
       buffer += size;
       len -= size;
+      if (len == 0)
+        {
+          result = read (ofd, resblock, hashlen) == hashlen ? -EIO: 0;
+          break;
+        }
     }
-  while (len > 0);
-
-  if (read (ofd, resblock, hashlen) != hashlen)
-    result = -EIO;
-  else
-    result = 0;
 
-out_ofd:
   close (ofd);
   return result;
 }
@@ -107,7 +105,7 @@ afalg_stream (FILE *stream, const char *alg,
 
   /* if file is a regular file, attempt sendfile to pipe the data.  */
   int fd = fileno (stream);
-  int result;
+  int result = 0;
   struct stat st;
   if (fstat (fd, &st) == 0
       && (S_ISREG (st.st_mode) || S_TYPEISSHM (&st) || S_TYPEISTMO (&st))
@@ -124,58 +122,48 @@ afalg_stream (FILE *stream, const char *alg,
 #else
           result = -errno;
 #endif
-          goto out_ofd;
         }
-
-      off_t nbytes = st.st_size - lseek (fd, 0, SEEK_CUR);
-      /* On Linux < 4.9, the value for an empty stream is wrong (all zeroes).
-         See <https://patchwork.kernel.org/patch/9308641/>.  */
-      if (nbytes <= 0)
+      else
         {
-          result = -EAFNOSUPPORT;
-          goto out_ofd;
-        }
-      if (sendfile (ofd, fd, NULL, nbytes) != nbytes)
-        {
-          result = -EIO;
-          goto out_ofd;
+          off_t nbytes = st.st_size - lseek (fd, 0, SEEK_CUR);
+          /* On Linux < 4.9, the value for an empty stream is wrong (all 0).
+             See <https://patchwork.kernel.org/patch/9308641/>.  */
+          if (nbytes <= 0)
+            result = -EAFNOSUPPORT;
+          else if (sendfile (ofd, fd, NULL, nbytes) != nbytes)
+            result = -EIO;
         }
     }
   else
     {
       /* sendfile not possible, do a classic read-write loop.  */
       int non_empty = 0;
-      ssize_t size;
-      char buf[BLOCKSIZE];
-      while ((size = fread (buf, 1, sizeof buf, stream)))
+      for (;;)
         {
+          char buf[BLOCKSIZE];
+          ssize_t size = fread (buf, 1, sizeof buf, stream);
+          if (size == 0)
+            {
+              /* On Linux < 4.9, the value for an empty stream is wrong (all 
0).
+                 See <https://patchwork.kernel.org/patch/9308641/>.  */
+              if (!non_empty)
+                result = -EAFNOSUPPORT;
+
+              if (ferror (stream))
+                result = -EIO;
+              break;
+            }
           non_empty = 1;
           if (send (ofd, buf, size, MSG_MORE) != size)
             {
               result = -EIO;
-              goto out_ofd;
+              break;
             }
         }
-      if (ferror (stream))
-        {
-          result = -EIO;
-          goto out_ofd;
-        }
-      /* On Linux < 4.9, the value for an empty stream is wrong (all zeroes).
-         See <https://patchwork.kernel.org/patch/9308641/>.  */
-      if (!non_empty)
-        {
-          result = -EAFNOSUPPORT;
-          goto out_ofd;
-        }
     }
 
-  if (read (ofd, resblock, hashlen) != hashlen)
+  if (result == 0 && read (ofd, resblock, hashlen) != hashlen)
     result = -EIO;
-  else
-    result = 0;
-
-out_ofd:
   close (ofd);
   return result;
 }
-- 
2.17.0




reply via email to

[Prev in Thread] Current Thread [Next in Thread]