Patch (was: tough locale bug) - Mailing list pgsql-hackers

From Goran Thyni
Subject Patch (was: tough locale bug)
Date
Msg-id 36B47C47.86D4CCAC@kirra.net
Whole thread Raw
In response to Re: [HACKERS] Postgres Speed or lack thereof  (Tom Lane <tgl@sss.pgh.pa.us>)
Responses Re: [HACKERS] Patch (was: tough locale bug)
Re: [HACKERS] Patch (was: tough locale bug)
List pgsql-hackers
Goran Thyni wrote:
> 3. text_lt('G','G\0xFF') this is not correct!
>
> Case 3 work not work with strcoll(), in varstr_cmp().
> If I change it to strcoll() to strncmp() it works as expected,
> but it probably breaks sorting etc big time.

Here is a hack which solves the problem without breaking sorting AFAIK.
I have read a lot of code, but has not found any cleaner way to fix
this.
A cleaner solution would be to find the highest char in locale charset
but I found no portable way to do that, any pointers appriciated.

It is not a beauty but it works.
Please apply to -current since it fixes the bug,
unless someone has a better suggestion.

    best regards,
--
-----------------
Göran Thyni
This is Penguin Country. On a quiet night you can hear Windows NT
reboot!diff -cr cvs/pgsql/src/backend/utils/adt/varlena.c cvswork/pgsql/src/backend/utils/adt/varlena.c
*** cvs/pgsql/src/backend/utils/adt/varlena.c    Mon Dec 14 07:01:37 1998
--- cvswork/pgsql/src/backend/utils/adt/varlena.c    Sun Jan 31 16:32:52 1999
***************
*** 496,528 ****
  varstr_cmp(char *arg1, int len1, char *arg2, int len2)
  {
      int            result;
!     char       *a1p,
!                *a2p;
!
  #ifdef USE_LOCALE
!     a1p = (unsigned char *) palloc(len1 + 1);
!     a2p = (unsigned char *) palloc(len2 + 1);
!
!     memcpy(a1p, arg1, len1);
!     *(a1p + len1) = '\0';
!     memcpy(a2p, arg2, len2);
!     *(a2p + len2) = '\0';
!
!     result = strcoll(a1p, a2p);
!
!     pfree(a1p);
!     pfree(a2p);
!
! #else
!
!     a1p = arg1;
!     a2p = arg2;
!
!     result = strncmp(a1p, a2p, Min(len1, len2));
!     if ((result == 0) && (len1 != len2))
!         result = (len1 < len2) ? -1 : 1;
  #endif
!
      return result;
  }    /* varstr_cmp() */

--- 496,524 ----
  varstr_cmp(char *arg1, int len1, char *arg2, int len2)
  {
      int            result;
!     char       *a1p, *a2p;
  #ifdef USE_LOCALE
!     if ((int)arg2[len2 - 1] != -1)
!       {
!         a1p = (unsigned char *) palloc(len1 + 1);
!         a2p = (unsigned char *) palloc(len2 + 1);
!         memcpy(a1p, arg1, len1);
!         *(a1p + len1) = '\0';
!         memcpy(a2p, arg2, len2);
!         *(a2p + len2) = '\0';
!         result = strcoll(a1p, a2p);
!         pfree(a1p);
!         pfree(a2p);
!       }
!     else
  #endif
!       {
!         a1p = arg1;
!         a2p = arg2;
!         result = strncmp(a1p, a2p, Min(len1, len2));
!         if ((result == 0) && (len1 != len2))
!         result = (len1 < len2) ? -1 : 1;
!       }
      return result;
  }    /* varstr_cmp() */


pgsql-hackers by date:

Previous
From: "D'Arcy" "J.M." Cain
Date:
Subject: Re: [HACKERS] Patches
Next
From: Tom Lane
Date:
Subject: Re: [HACKERS] Re: vacuumdb?