changeset 14736:d715ba4337c0

getcwd-lgpl: relax test for FreeBSD getcwd(NULL, 1) mallocs a larger buffer on BSD, rather than failing with ERANGE as on glibc. This behavior difference is not worth coding around, as it is an uncommon use of getcwd in the first place. * doc/posix-functions/getcwd.texi (getcwd): Document portability issue. * tests/test-getcwd-lgpl.c (main): Relax test. Reported by Matthias Bolte. Signed-off-by: Eric Blake <eblake@redhat.com>
author Eric Blake <eblake@redhat.com>
date Fri, 13 May 2011 10:26:08 -0600
parents b8c290caf664
children e91d05814c25
files ChangeLog doc/posix-functions/getcwd.texi tests/test-getcwd-lgpl.c
diffstat 3 files changed, 33 insertions(+), 4 deletions(-) [+]
line wrap: on
line diff
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,11 @@
+2011-05-13  Eric Blake  <eblake@redhat.com>
+
+	getcwd-lgpl: relax test for FreeBSD
+	* doc/posix-functions/getcwd.texi (getcwd): Document portability
+	issue.
+	* tests/test-getcwd-lgpl.c (main): Relax test.
+	Reported by Matthias Bolte.
+
 2011-05-11  Eric Blake  <eblake@redhat.com>
 
 	test-fflush: silence compiler warning
--- a/doc/posix-functions/getcwd.texi
+++ b/doc/posix-functions/getcwd.texi
@@ -11,8 +11,7 @@
 @itemize
 @item
 On glibc platforms, @code{getcwd (NULL, n)} allocates memory for the result.
-On some other platforms, this call is not allowed.  Conversely, mingw fails
-to honor non-zero @code{n}.
+On some other platforms, this call is not allowed.
 @item
 On some platforms, the prototype for @code{getcwd} uses @code{int}
 instead of @code{size_t} for the size argument:
@@ -30,4 +29,11 @@
 
 Portability problems not fixed by Gnulib:
 @itemize
+@item
+When using @code{getcwd(NULL, nonzero)}, some platforms, such as glibc
+or cygwin, allocate exactly @code{nonzero} bytes and fail with
+@code{ERANGE} if it was not big enough, while other platforms, such as
+FreeBSD or mingw, ignore the size argument and allocate whatever size
+is necessary.  If this call succeeds, an application cannot portably
+access beyond the string length of the result.
 @end itemize
--- a/tests/test-getcwd-lgpl.c
+++ b/tests/test-getcwd-lgpl.c
@@ -65,12 +65,22 @@
     pwd2 = malloc (len + 2);
     for ( ; i <= len; i++)
       {
+        char *tmp;
         errno = 0;
         ASSERT (getcwd (pwd2, i) == NULL);
         ASSERT (errno == ERANGE);
+        /* Allow either glibc or BSD behavior, since POSIX allows both.  */
         errno = 0;
-        ASSERT (getcwd (NULL, i) == NULL);
-        ASSERT (errno == ERANGE);
+        tmp = getcwd (NULL, i);
+        if (tmp)
+          {
+            ASSERT (strcmp (pwd1, tmp) == 0);
+            free (tmp);
+          }
+        else
+          {
+            ASSERT (errno == ERANGE);
+          }
       }
     ASSERT (getcwd (pwd2, len + 1) == pwd2);
     pwd2[len] = '/';
@@ -80,6 +90,11 @@
   ASSERT (strstr (pwd2, "/../") == NULL);
   ASSERT (strstr (pwd2 + 1 + (pwd2[1] == '/'), "//") == NULL);
 
+  /* Validate a POSIX requirement on size.  */
+  errno = 0;
+  ASSERT (getcwd(pwd2, 0) == NULL);
+  ASSERT (errno == EINVAL);
+
   free (pwd1);
   free (pwd2);