bug-gnulib
[Top][All Lists]
Advanced

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

Re: [PATCH] strerror_r: fix on newer cygwin


From: Bruno Haible
Subject: Re: [PATCH] strerror_r: fix on newer cygwin
Date: Thu, 19 May 2011 22:51:13 +0200
User-agent: KMail/1.9.9

Hi Eric,

> in the process of adding
> __xpg_sterror_r, the original strerror_r was fixed to align more closely
> to glibc behavior.  Thus, it was changed so that strerror_r(EACCES, buf,
> 2) no longer overwrites buf with a (truncated) message to buf, so the
> caller instead has to manually copy the static string result over to buf.
> 
> When testing at commit d118714, I got:
> 
> ../../gltests/test-strerror_r.c:82: assertion failed
> /bin/sh: line 5:  2060 Aborted                 (core dumped)
> EXEEXT='.exe' srcdir='../../gltests' MAKE='make' ${dir}$tst
> FAIL: test-strerror_r.exe
> 
> at that point, line 82 was:
> 
> 82                ASSERT ((strcmp (buf, "BADFACE") == 0) == (i == 0));
> 
> with i at 1.

Thanks for explaining. But that means that a binary built with Cygwin
1.7.5 will still fail when run on Cygwin >= 1.7.9. The complete fix
ought to look something like this, I guess?


2011-05-19  Bruno Haible  <address@hidden>

        strerror_r: Work around strerror_r() change in Cygwin 1.7.9.
        * lib/strerror_r.c (strerror_r) [CYGWIN]: Recognize when the system's
        strerror_r() returned without filling the buffer.
        Reported by Eric Blake.

--- lib/strerror_r.c.orig       Thu May 19 22:48:15 2011
+++ lib/strerror_r.c    Thu May 19 22:48:05 2011
@@ -456,10 +456,34 @@
         ret = strerror_r (errnum, buf, buflen);
     }
 # elif defined __CYGWIN__
-    /* Cygwin 1.7.8 only provides the glibc interface, is thread-safe, and
-       always succeeds (although it may truncate). */
-    strerror_r (errnum, buf, buflen);
-    ret = 0;
+    /* Cygwin <= 1.7.8 only provides the glibc interface, is thread-safe, and
+       always succeeds (although it may truncate).  In Cygwin >= 1.7.9, instead
+       of truncating, it leaves the buffer untouched.  */
+    {
+      char stackbuf[256];
+
+      if (buflen < sizeof (stackbuf))
+        {
+          size_t len;
+
+          stackbuf[0] = '\0'; /* in case strerror_r does nothing */
+          strerror_r (errnum, stackbuf, sizeof (stackbuf));
+          len = strlen (stackbuf);
+          if (len < buflen)
+            {
+              memcpy (buf, stackbuf, len + 1);
+              ret = 0;
+            }
+          else
+            ret = ERANGE;
+        }
+      else
+        {
+          buf[0] = '\0'; /* in case strerror_r does nothing */
+          strerror_r (errnum, buf, buflen);
+          ret = 0;
+        }
+    }
 # else
     ret = strerror_r (errnum, buf, buflen);
 # endif

-- 
In memoriam Anne Boleyn <http://en.wikipedia.org/wiki/Anne_Boleyn>



reply via email to

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