Pádraig Brady wrote:
xalloc is
included into the coreutils compilation units and so
needs this guard.

That's a problem in coreutils, not in gnulib. Please don't give much weight to those particular compiler warnings. They're often false alarms, as these were. There is nothing wrong when a compiler can reason about integer overflow to generate better code. Conversely, it is often helpful for an application to use signed integer types so that a checking implementation can report integer overflow when the appliction is buggy, which means we shouldn't blindly substitute unsigned for signed types merely to stop GCC from bleating in this way.

I reverted the gnulib change, and installed the attached coreutils patches to pacify 32-bit GCC in a better way. If these sorts of warnings continue to be a hassle in coreutils, perhaps we should disable the warnings there too.
From b7667556ce531f72cb863b5a04e3910f131e83cb Mon Sep 17 00:00:00 2001
From: Paul Eggert <[email protected]>
Date: Sat, 3 Oct 2015 00:24:43 -0700
Subject: [PATCH 1/2] build: Pacify GCC 5 on 32-bit hosts

This pacifies GCC 5 in a better way, without disabling diagnostics.
* src/df.c (main): Tell compiler that optind is positive.
* src/shred.c (known): New function.
(dopass): Go back to off_t for file sizes.
Avoid integer overflow if we run off the end of the file.
Tell compiler that a write cannot write more bytes than requested.
---
 src/df.c    |  2 ++
 src/shred.c | 38 ++++++++++++++++++++++++--------------
 2 files changed, 26 insertions(+), 14 deletions(-)

diff --git a/src/df.c b/src/df.c
index 17a2de4..507a0f7 100644
--- a/src/df.c
+++ b/src/df.c
@@ -1650,6 +1650,8 @@ main (int argc, char **argv)
       return EXIT_FAILURE;
   }
 
+  assume (0 < optind);
+
   if (optind < argc)
     {
       int i;
diff --git a/src/shred.c b/src/shred.c
index 5bb0d17..2857835 100644
--- a/src/shred.c
+++ b/src/shred.c
@@ -408,6 +408,14 @@ dorewind (int fd, struct stat const *st)
   return offset == 0;
 }
 
+/* By convention, negative sizes represent unknown values.  */
+
+static bool
+known (off_t size)
+{
+  return 0 <= size;
+}
+
 /*
  * Do pass number K of N, writing *SIZEP bytes of the given pattern TYPE
  * to the file descriptor FD.  K and N are passed in only for verbose
@@ -423,9 +431,8 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
         int type, struct randread_source *s,
         unsigned long int k, unsigned long int n)
 {
-  uintmax_t size = MAX (0, *sizep);
-  bool known_size = 0 <= *sizep;
-  uintmax_t offset;            /* Current file position */
+  off_t size = *sizep;
+  off_t offset;                        /* Current file posiiton */
   time_t thresh IF_LINT ( = 0);        /* Time to maybe print next status 
update */
   time_t now = 0;              /* Current time */
   size_t lim;                  /* Amount of data to try writing */
@@ -470,7 +477,7 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
   /* Constant fill patterns need only be set up once. */
   if (type >= 0)
     {
-      lim = (known_size && size < FILLPATTERN_SIZE ? size : FILLPATTERN_SIZE);
+      lim = known (size) && size < FILLPATTERN_SIZE ? size : FILLPATTERN_SIZE;
       fillpattern (type, pbuf, lim);
       passname (pbuf, pass_string);
     }
@@ -492,7 +499,7 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
     {
       /* How much to write this time? */
       lim = output_size;
-      if (known_size && size - offset < output_size)
+      if (known (size) && size - offset < output_size)
         {
           if (size < offset)
             break;
@@ -506,13 +513,15 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
       for (soff = 0; soff < lim; soff += ssize)
         {
           ssize = write (fd, pbuf + soff, lim - soff);
-          if (ssize <= 0)
+          if (0 < ssize)
+            assume (ssize <= lim - soff);
+          else
             {
-              if (! known_size && (ssize == 0 || errno == ENOSPC))
+              if (! known (size) && (ssize == 0 || errno == ENOSPC))
                 {
-                  /* We have found the end of the file */
-                  *sizep = size = offset + soff;
-                  known_size = true;
+                  /* We have found the end of the file.  */
+                  if (soff <= OFF_T_MAX - offset)
+                    *sizep = size = offset + soff;
                   break;
                 }
               else
@@ -541,7 +550,8 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
                      also enables direct I/O on some (file) systems.  */
                   verify (PERIODIC_OUTPUT_SIZE % SECTOR_SIZE == 0);
                   verify (NONPERIODIC_OUTPUT_SIZE % SECTOR_SIZE == 0);
-                  if (errnum == EIO && known_size && (soff | SECTOR_MASK) < 
lim)
+                  if (errnum == EIO && known (size)
+                      && (soff | SECTOR_MASK) < lim)
                     {
                       size_t soff1 = (soff | SECTOR_MASK) + 1;
                       if (lseek (fd, offset + soff1, SEEK_SET) != -1)
@@ -561,7 +571,7 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
 
       /* Okay, we have written "soff" bytes. */
 
-      if (offset > OFF_T_MAX - (off_t) soff)
+      if (OFF_T_MAX - offset < soff)
         {
           error (0, 0, _("%s: file too large"), qname);
           other_error = true;
@@ -570,7 +580,7 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
 
       offset += soff;
 
-      bool done = (! known_size) || offset == size;
+      bool done = offset == size;
 
       /* Time to print progress? */
       if (n && ((done && *previous_human_offset)
@@ -586,7 +596,7 @@ dopass (int fd, struct stat const *st, char const *qname, 
off_t *sizep,
 
           if (done || !STREQ (previous_human_offset, human_offset))
             {
-              if (! known_size)
+              if (! known (size))
                 error (0, 0, _("%s: pass %lu/%lu (%s)...%s"),
                        qname, k, n, pass_string, human_offset);
               else
-- 
2.1.0

From 7e32c35ce24118c8839a3ce07e028912e3bcc74d Mon Sep 17 00:00:00 2001
From: Paul Eggert <[email protected]>
Date: Sat, 3 Oct 2015 00:25:27 -0700
Subject: [PATCH 2/2] build: update gnulib submodule to latest

---
 gnulib | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/gnulib b/gnulib
index 213d554..8be4b46 160000
--- a/gnulib
+++ b/gnulib
@@ -1 +1 @@
-Subproject commit 213d5545f67d726ccffa13842577be47aca93d8d
+Subproject commit 8be4b46b01cbcf7407b720571e5f455ed9fe7253
-- 
2.1.0

Reply via email to