@@ -92,27 +92,12 @@ extern char *get_collation_actual_version_builtin(const char *collcollate);
92
92
/* pg_locale_icu.c */
93
93
#ifdef USE_ICU
94
94
extern UCollator * pg_ucol_open (const char * loc_str );
95
- extern int strncoll_icu (const char * arg1 , ssize_t len1 ,
96
- const char * arg2 , ssize_t len2 ,
97
- pg_locale_t locale );
98
- extern size_t strnxfrm_icu (char * dest , size_t destsize ,
99
- const char * src , ssize_t srclen ,
100
- pg_locale_t locale );
101
- extern size_t strnxfrm_prefix_icu (char * dest , size_t destsize ,
102
- const char * src , ssize_t srclen ,
103
- pg_locale_t locale );
104
95
extern char * get_collation_actual_version_icu (const char * collcollate );
105
96
#endif
106
97
extern pg_locale_t create_pg_locale_icu (Oid collid , MemoryContext context );
107
98
108
99
/* pg_locale_libc.c */
109
100
extern pg_locale_t create_pg_locale_libc (Oid collid , MemoryContext context );
110
- extern int strncoll_libc (const char * arg1 , ssize_t len1 ,
111
- const char * arg2 , ssize_t len2 ,
112
- pg_locale_t locale );
113
- extern size_t strnxfrm_libc (char * dest , size_t destsize ,
114
- const char * src , ssize_t srclen ,
115
- pg_locale_t locale );
116
101
extern char * get_collation_actual_version_libc (const char * collcollate );
117
102
118
103
extern size_t strlower_builtin (char * dst , size_t dstsize , const char * src ,
@@ -1244,6 +1229,9 @@ create_pg_locale(Oid collid, MemoryContext context)
1244
1229
1245
1230
result -> is_default = false;
1246
1231
1232
+ Assert ((result -> collate_is_c && result -> collate == NULL ) ||
1233
+ (!result -> collate_is_c && result -> collate != NULL ));
1234
+
1247
1235
datum = SysCacheGetAttr (COLLOID , tp , Anum_pg_collation_collversion ,
1248
1236
& isnull );
1249
1237
if (!isnull )
@@ -1467,19 +1455,7 @@ pg_strupper(char *dst, size_t dstsize, const char *src, ssize_t srclen,
1467
1455
int
1468
1456
pg_strcoll (const char * arg1 , const char * arg2 , pg_locale_t locale )
1469
1457
{
1470
- int result ;
1471
-
1472
- if (locale -> provider == COLLPROVIDER_LIBC )
1473
- result = strncoll_libc (arg1 , -1 , arg2 , -1 , locale );
1474
- #ifdef USE_ICU
1475
- else if (locale -> provider == COLLPROVIDER_ICU )
1476
- result = strncoll_icu (arg1 , -1 , arg2 , -1 , locale );
1477
- #endif
1478
- else
1479
- /* shouldn't happen */
1480
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1481
-
1482
- return result ;
1458
+ return locale -> collate -> strncoll (arg1 , -1 , arg2 , -1 , locale );
1483
1459
}
1484
1460
1485
1461
/*
@@ -1500,51 +1476,25 @@ int
1500
1476
pg_strncoll (const char * arg1 , ssize_t len1 , const char * arg2 , ssize_t len2 ,
1501
1477
pg_locale_t locale )
1502
1478
{
1503
- int result ;
1504
-
1505
- if (locale -> provider == COLLPROVIDER_LIBC )
1506
- result = strncoll_libc (arg1 , len1 , arg2 , len2 , locale );
1507
- #ifdef USE_ICU
1508
- else if (locale -> provider == COLLPROVIDER_ICU )
1509
- result = strncoll_icu (arg1 , len1 , arg2 , len2 , locale );
1510
- #endif
1511
- else
1512
- /* shouldn't happen */
1513
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1514
-
1515
- return result ;
1479
+ return locale -> collate -> strncoll (arg1 , len1 , arg2 , len2 , locale );
1516
1480
}
1517
1481
1518
1482
/*
1519
1483
* Return true if the collation provider supports pg_strxfrm() and
1520
1484
* pg_strnxfrm(); otherwise false.
1521
1485
*
1522
- * Unfortunately, it seems that strxfrm() for non-C collations is broken on
1523
- * many common platforms; testing of multiple versions of glibc reveals that,
1524
- * for many locales, strcoll() and strxfrm() do not return consistent
1525
- * results. While no other libc other than Cygwin has so far been shown to
1526
- * have a problem, we take the conservative course of action for right now and
1527
- * disable this categorically. (Users who are certain this isn't a problem on
1528
- * their system can define TRUST_STRXFRM.)
1529
1486
*
1530
1487
* No similar problem is known for the ICU provider.
1531
1488
*/
1532
1489
bool
1533
1490
pg_strxfrm_enabled (pg_locale_t locale )
1534
1491
{
1535
- if (locale -> provider == COLLPROVIDER_LIBC )
1536
- #ifdef TRUST_STRXFRM
1537
- return true;
1538
- #else
1539
- return false;
1540
- #endif
1541
- else if (locale -> provider == COLLPROVIDER_ICU )
1542
- return true ;
1543
- else
1544
- /* shouldn't happen */
1545
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1546
-
1547
- return false; /* keep compiler quiet */
1492
+ /*
1493
+ * locale->collate->strnxfrm is still a required method, even if it may
1494
+ * have the wrong behavior, because the planner uses it for estimates in
1495
+ * some cases.
1496
+ */
1497
+ return locale -> collate -> strxfrm_is_safe ;
1548
1498
}
1549
1499
1550
1500
/*
@@ -1555,19 +1505,7 @@ pg_strxfrm_enabled(pg_locale_t locale)
1555
1505
size_t
1556
1506
pg_strxfrm (char * dest , const char * src , size_t destsize , pg_locale_t locale )
1557
1507
{
1558
- size_t result = 0 ; /* keep compiler quiet */
1559
-
1560
- if (locale -> provider == COLLPROVIDER_LIBC )
1561
- result = strnxfrm_libc (dest , destsize , src , -1 , locale );
1562
- #ifdef USE_ICU
1563
- else if (locale -> provider == COLLPROVIDER_ICU )
1564
- result = strnxfrm_icu (dest , destsize , src , -1 , locale );
1565
- #endif
1566
- else
1567
- /* shouldn't happen */
1568
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1569
-
1570
- return result ;
1508
+ return locale -> collate -> strnxfrm (dest , destsize , src , -1 , locale );
1571
1509
}
1572
1510
1573
1511
/*
@@ -1593,19 +1531,7 @@ size_t
1593
1531
pg_strnxfrm (char * dest , size_t destsize , const char * src , ssize_t srclen ,
1594
1532
pg_locale_t locale )
1595
1533
{
1596
- size_t result = 0 ; /* keep compiler quiet */
1597
-
1598
- if (locale -> provider == COLLPROVIDER_LIBC )
1599
- result = strnxfrm_libc (dest , destsize , src , srclen , locale );
1600
- #ifdef USE_ICU
1601
- else if (locale -> provider == COLLPROVIDER_ICU )
1602
- result = strnxfrm_icu (dest , destsize , src , srclen , locale );
1603
- #endif
1604
- else
1605
- /* shouldn't happen */
1606
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1607
-
1608
- return result ;
1534
+ return locale -> collate -> strnxfrm (dest , destsize , src , srclen , locale );
1609
1535
}
1610
1536
1611
1537
/*
@@ -1615,15 +1541,7 @@ pg_strnxfrm(char *dest, size_t destsize, const char *src, ssize_t srclen,
1615
1541
bool
1616
1542
pg_strxfrm_prefix_enabled (pg_locale_t locale )
1617
1543
{
1618
- if (locale -> provider == COLLPROVIDER_LIBC )
1619
- return false;
1620
- else if (locale -> provider == COLLPROVIDER_ICU )
1621
- return true;
1622
- else
1623
- /* shouldn't happen */
1624
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1625
-
1626
- return false; /* keep compiler quiet */
1544
+ return (locale -> collate -> strnxfrm_prefix != NULL );
1627
1545
}
1628
1546
1629
1547
/*
@@ -1635,7 +1553,7 @@ size_t
1635
1553
pg_strxfrm_prefix (char * dest , const char * src , size_t destsize ,
1636
1554
pg_locale_t locale )
1637
1555
{
1638
- return pg_strnxfrm_prefix (dest , destsize , src , -1 , locale );
1556
+ return locale -> collate -> strnxfrm_prefix (dest , destsize , src , -1 , locale );
1639
1557
}
1640
1558
1641
1559
/*
@@ -1660,16 +1578,7 @@ size_t
1660
1578
pg_strnxfrm_prefix (char * dest , size_t destsize , const char * src ,
1661
1579
ssize_t srclen , pg_locale_t locale )
1662
1580
{
1663
- size_t result = 0 ; /* keep compiler quiet */
1664
-
1665
- #ifdef USE_ICU
1666
- if (locale -> provider == COLLPROVIDER_ICU )
1667
- result = strnxfrm_prefix_icu (dest , destsize , src , -1 , locale );
1668
- else
1669
- #endif
1670
- PGLOCALE_SUPPORT_ERROR (locale -> provider );
1671
-
1672
- return result ;
1581
+ return locale -> collate -> strnxfrm_prefix (dest , destsize , src , srclen , locale );
1673
1582
}
1674
1583
1675
1584
/*
0 commit comments