gbt_var_node_cp_len() contained logic to ensure that its choice of
a common prefix length didn't truncate away part of a multibyte
character. However, that was really dead code, because we have not
allowed truncation of text-string data types since
ef770cbb6, and
it seems unlikely that that behavior could ever get resurrected.
The code is still reachable via gbt_var_penalty, but for that
usage it hardly matters if we break in the middle of a multibyte
character: we're just calculating a small correction factor that
is arguably bunkum anyway in non-C locales.
Hence, delete said code. That actually removes all need for
gbtree_vinfo.eml, which allows const-ification of the gbtree_vinfo
structs in which we were changing it, which removes one headache
for future attempts to thread-ify the backend.
(Curiously, all this infrastructure was itself added by
ef770cbb6.
Not sure why Teodor didn't see the contradiction.)
Author: Tom Lane <tgl@sss.pgh.pa.us>
Reviewed-by: Ayush Tiwari <ayushtiwari.slg01@gmail.com>
Discussion: https://postgr.es/m/AH*AvQCYKhQGVvPWi1GiU4oY.8.
1781609375063.Hmail.
3020001251@tju.edu.cn
static const gbtree_vinfo tinfo =
{
gbt_t_bit,
- 0,
true, /* internal keys can be truncated */
gbt_bitgt,
gbt_bitge,
static const gbtree_vinfo tinfo =
{
gbt_t_bytea,
- 0,
true, /* internal keys can be truncated */
gbt_byteagt,
gbt_byteage,
static const gbtree_vinfo tinfo =
{
gbt_t_numeric,
- 0,
false, /* no truncation permitted */
gbt_numeric_gt,
gbt_numeric_ge,
* more complicated than C. The prefix-match hack used for simpler types
* can't fix it, either.
*/
-static gbtree_vinfo tinfo =
+static const gbtree_vinfo tinfo =
{
gbt_t_text,
- 0,
false, /* no truncation permitted */
gbt_textgt,
gbt_textge,
PointerGetDatum(b)));
}
-static gbtree_vinfo bptinfo =
+static const gbtree_vinfo bptinfo =
{
gbt_t_bpchar,
- 0,
false, /* as above, no truncation permitted */
gbt_bpchargt,
gbt_bpcharge,
{
GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0);
- if (tinfo.eml == 0)
- {
- tinfo.eml = pg_database_encoding_max_length();
- }
-
PG_RETURN_POINTER(gbt_var_compress(entry, &tinfo));
}
/* All cases served by this function are exact */
*recheck = false;
- if (tinfo.eml == 0)
- {
- tinfo.eml = pg_database_encoding_max_length();
- }
-
retval = gbt_var_consistent(&r, query, strategy, PG_GET_COLLATION(),
GIST_LEAF(entry), &tinfo, fcinfo->flinfo);
/* All cases served by this function are exact */
*recheck = false;
- if (bptinfo.eml == 0)
- {
- bptinfo.eml = pg_database_encoding_max_length();
- }
-
retval = gbt_var_consistent(&r, query, strategy, PG_GET_COLLATION(),
GIST_LEAF(entry), &bptinfo, fcinfo->flinfo);
PG_RETURN_BOOL(retval);
#include "btree_gist.h"
#include "btree_utils_var.h"
-#include "mb/pg_wchar.h"
#include "utils/rel.h"
#include "varatt.h"
/*
* returns the common prefix length of a node key
*
- * If the underlying type is character data, the prefix length may point in
- * the middle of a multibyte character.
+ * This is not used for any cases where the underlying type is character data
+ * (except in gbt_var_penalty, where it doesn't matter since we're just making
+ * an estimated correction not constructing a truncated string). If it were,
+ * we'd need to be careful not to truncate in the middle of a multibyte
+ * character.
*/
static int32
gbt_var_node_cp_len(const GBT_VARKEY *node, const gbtree_vinfo *tinfo)
{
GBT_VARKEY_R r = gbt_var_key_readable(node);
int32 i = 0;
- int32 l_left_to_match = 0;
- int32 l_total = 0;
int32 t1len = VARSIZE(r.lower) - VARHDRSZ;
int32 t2len = VARSIZE(r.upper) - VARHDRSZ;
int32 ml = Min(t1len, t2len);
char *p1 = VARDATA(r.lower);
char *p2 = VARDATA(r.upper);
- const char *end1 = p1 + t1len;
- const char *end2 = p2 + t2len;
if (ml == 0)
return 0;
while (i < ml)
{
- if (tinfo->eml > 1 && l_left_to_match == 0)
- {
- l_total = pg_mblen_range(p1, end1);
- if (l_total != pg_mblen_range(p2, end2))
- {
- return i;
- }
- l_left_to_match = l_total;
- }
if (*p1 != *p2)
- {
- if (tinfo->eml > 1)
- {
- int32 l_matched_subset = l_total - l_left_to_match;
-
- /* end common prefix at final byte of last matching char */
- return i - l_matched_subset;
- }
- else
- {
- return i;
- }
- }
-
+ return i;
p1++;
p2++;
- l_left_to_match--;
i++;
}
return ml; /* lower == upper */
/* Attribs */
enum gbtree_type t; /* data type */
- int32 eml; /* cached pg_database_encoding_max_length (0:
- * undefined) */
bool trnc; /* truncate (=compress) key */
/* Methods */