]> Savannah Git Hosting - gnulib.git/commitdiff
errno-tests: port to GNU/Hurd
authorPaul Eggert <eggert@cs.ucla.edu>
Wed, 7 Aug 2024 14:23:51 +0000 (07:23 -0700)
committerPaul Eggert <eggert@cs.ucla.edu>
Wed, 7 Aug 2024 14:24:17 +0000 (07:24 -0700)
Test for errno distinctness dynamically rather than statically,
since the static test blows up the compiler on Hurd.
Problem reported by Bruno Haible in:
https://lists.gnu.org/r/bug-gnulib/2024-08/msg00039.html
Also, test that errno values can all be used in #if,
and improve diagnostics.
* tests/test-errno.c: Include stdio.h, stdlib.h, string.h.
(USABLE_IN_IF): New macro.  Use it to check errno values in #if.
(ERRTAB): New macro.
(struct nameval): New type.
(errtab): New global variable.
(errtab_cmp): New function.
(main): Test for errno distinctness dynamically not statically.
Diagnose lack of distinctness better.

ChangeLog
tests/test-errno.c

index 8e0896f1274ce510778829bf31079b420bfbf8c6..df710ddfa6f292216d105e08c2d96f9a5bbd3194 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,21 @@
+2024-08-07  Paul Eggert  <eggert@cs.ucla.edu>
+
+       errno-tests: port to GNU/Hurd
+       Test for errno distinctness dynamically rather than statically,
+       since the static test blows up the compiler on Hurd.
+       Problem reported by Bruno Haible in:
+       https://lists.gnu.org/r/bug-gnulib/2024-08/msg00039.html
+       Also, test that errno values can all be used in #if,
+       and improve diagnostics.
+       * tests/test-errno.c: Include stdio.h, stdlib.h, string.h.
+       (USABLE_IN_IF): New macro.  Use it to check errno values in #if.
+       (ERRTAB): New macro.
+       (struct nameval): New type.
+       (errtab): New global variable.
+       (errtab_cmp): New function.
+       (main): Test for errno distinctness dynamically not statically.
+       Diagnose lack of distinctness better.
+
 2024-08-07  Bruno Haible  <bruno@clisp.org>
 
        fchmodat: Fix cross-compilation guess.
index 7403ee14324587b3179efc3defded993d8b39c22..acd07ab95b34b6f1f9c482dd8e6f37f674ff359f 100644 (file)
 
 #include <errno.h>
 
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
 /* Check all POSIX-defined errno values, using M (v) to check value v.  */
 #define CHECK_POSIX_ERRNOS(m) \
   m (E2BIG) \
 #define POSITIVE_INTEGER_CONSTANT_EXPRESSION(e) static_assert (0 < (e) << 0);
 CHECK_POSIX_ERRNOS (POSITIVE_INTEGER_CONSTANT_EXPRESSION)
 
+/* Verify that errno values can all be used in #if.  */
+#define USABLE_IN_IF(e) ^ e
+#if 0 CHECK_POSIX_ERRNOS (USABLE_IN_IF)
+#endif
+
+/* Check that errno values all differ, except possibly for
+   EWOULDBLOCK == EAGAIN and ENOTSUP == EOPNOTSUPP.  */
+#define ERRTAB(e) { #e, e },
+static struct nameval { char const *name; int value; }
+  errtab[] = { CHECK_POSIX_ERRNOS (ERRTAB) };
+
+static int
+errtab_cmp (void const *va, void const *vb)
+{
+  struct nameval const *a = va, *b = vb;
+
+  /* Sort by value first, then by name (to simplify later tests).
+     Subtraction cannot overflow as both are positive.  */
+  int diff = a->value - b->value;
+  return diff ? diff : strcmp (a->name, b->name);
+}
+
 int
 main ()
 {
+  int test_exit_status = EXIT_SUCCESS;
+
   /* Verify that errno can be assigned.  */
   errno = EOVERFLOW;
 
   /* Check that errno values all differ, except possibly for
-     EWOULDBLOCK == EAGAIN and ENOTSUP == EOPNOTSUPP.  */
-  #define INDEXED_BY_ERRNO(e) [e] = 1,
-  #define ERRNO_COUNT(e) 0,
-  static char const
-    indexed_by_errno[] = { CHECK_POSIX_ERRNOS (INDEXED_BY_ERRNO) },
-    errno_count[] = { CHECK_POSIX_ERRNOS (ERRNO_COUNT) };
-  int distinct_errnos = 0;
-  for (int i = 0; i < sizeof indexed_by_errno; i++)
-    distinct_errnos += indexed_by_errno[i];
-  return ((sizeof errno_count
-           - (EWOULDBLOCK == EAGAIN)
-           - (ENOTSUP == EOPNOTSUPP))
-          != distinct_errnos);
+     EAGAIN == EWOULDBLOCK and ENOTSUP == EOPNOTSUPP.  */
+  int nerrtab = sizeof errtab / sizeof *errtab;
+  qsort (errtab, nerrtab, sizeof *errtab, errtab_cmp);
+  for (int i = 1; i < nerrtab; i++)
+    if (errtab[i - 1].value == errtab[i].value)
+      {
+        fprintf (stderr, "%s == %s == %d\n",
+                 errtab[i - 1].name, errtab[i].name, errtab[i].value);
+        if (! ((strcmp ("EAGAIN", errtab[i - 1].name) == 0
+                && strcmp ("EWOULDBLOCK", errtab[i].name) == 0)
+               || (strcmp ("ENOTSUP", errtab[i - 1].name) == 0
+                   && strcmp ("EOPNOTSUPP", errtab[i].name) == 0)))
+          test_exit_status = EXIT_FAILURE;
+      }
+
+  return test_exit_status;
 }