bug-gnulib
[Top][All Lists]
Advanced

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

Re: [Bug-gnulib] use of strcoll


From: Paul Eggert
Subject: Re: [Bug-gnulib] use of strcoll
Date: Tue, 31 Dec 2002 14:18:21 -0800

> Date: Tue, 31 Dec 2002 14:00:00 +0100 (CET)
> From: Bruno Haible <address@hidden>
> 
> The autoconf manual says that there are broken implementations of
> strcoll() around.

I think that's referring to implementations that were old 10 years
ago, so it's not urgent to avoid them now.  coreutils has used strcoll
since at least 1999 without anybody complaining.

As it happens, though, I had some code handy in diffutils which did
something similar in a faster way, so it was easy for me to install
this further patch to incorporate it.


2002-12-31  Paul Eggert  <address@hidden>

        * lib/memcoll.c (memcoll): Fall back on a simple algorithm using
        memcmp if strcoll doesn't work.
        * m4/memcoll.m4 (gl_MEMCOLL): Require AC_FUNC_MEMCMP.

--- lib/memcoll.c       31 Dec 2002 13:01:56 -0000      1.7
+++ lib/memcoll.c       31 Dec 2002 22:11:34 -0000      1.8
@@ -1,5 +1,5 @@
 /* Locale-specific memory comparison.
-   Copyright 1999, 2002 Free Software Foundation, Inc.
+   Copyright (C) 1999, 2002 Free Software Foundation, Inc.
 
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
@@ -32,29 +32,25 @@ extern int errno;
 # include <string.h>
 #endif
 
-/* Use strcoll() only if it really works.  */
-#if HAVE_STRCOLL
-# define STRCOLL strcoll
-#else
-# define STRCOLL strcmp
-#endif
-
 /* Compare S1 (with length S1LEN) and S2 (with length S2LEN) according
    to the LC_COLLATE locale.  S1 and S2 do not overlap, and are not
-   adjacent.  Temporarily modify the bytes after S1 and S2, but
-   restore their original contents before returning.  Set errno to an
+   adjacent.  Perhaps temporarily modify the bytes after S1 and S2,
+   but restore their original contents before returning.  Set errno to an
    error number if there is an error, and to zero otherwise.  */
 int
 memcoll (char *s1, size_t s1len, char *s2, size_t s2len)
 {
   int diff;
+
+#if HAVE_STRCOLL
+
   char n1 = s1[s1len];
   char n2 = s2[s2len];
 
   s1[s1len++] = '\0';
   s2[s2len++] = '\0';
 
-  while (! (errno = 0, (diff = STRCOLL (s1, s2)) || errno))
+  while (! (errno = 0, (diff = strcoll (s1, s2)) || errno))
     {
       /* strcoll found no difference, but perhaps it was fooled by NUL
         characters in the data.  Work around this problem by advancing
@@ -81,6 +77,14 @@ memcoll (char *s1, size_t s1len, char *s
 
   s1[s1len - 1] = n1;
   s2[s2len - 1] = n2;
+
+#else
+
+  diff = memcmp (s1, s2, s1len < s2len ? s1len : s2len);
+  if (! diff)
+    diff = s1len < s2len ? -1 : s1len != s2len;
+
+#endif
 
   return diff;
 }
--- m4/memcoll.m4       31 Dec 2002 13:42:07 -0000      1.1
+++ m4/memcoll.m4       31 Dec 2002 22:11:51 -0000      1.2
@@ -1,4 +1,4 @@
-# memcoll.m4 serial 1
+# memcoll.m4 serial 2
 dnl Copyright (C) 2002 Free Software Foundation, Inc.
 dnl This file is free software, distributed under the terms of the GNU
 dnl General Public License.  As a special exception to the GNU General
@@ -9,6 +9,7 @@ dnl the same distribution terms as the r
 AC_DEFUN([gl_MEMCOLL],
 [
   dnl Prerequisites of lib/memcoll.c.
+  AC_REQUIRE([AC_FUNC_MEMCMP])
   AC_CHECK_HEADERS_ONCE(string.h)
   AC_FUNC_STRCOLL
 ])



reply via email to

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