mirror of
https://github.com/MariaDB/server.git
synced 2026-05-09 08:34:28 +02:00
Several problems were fixed (mostly BLOB+charset related)
Fixed that MyISAM were not working properly with non-8bit charsets in some cases CONVERT() function now works properly myisam/mi_unique.c: Fix for non-8bit charsets sql/field.cc: Initialize blobs with charset sql/field.h: Initialize blobs with charset sql/field_conv.cc: Initialize blobs with charset sql/item_strfunc.cc: CONVERT() function now has working fix_lenght_and_dec(), and it's own fix_fields() sql/item_strfunc.h: CONVERT() function now has working fix_lenght_and_dec(), and it's own fix_fields() sql/sql_select.cc: Fixes for BLOBs Fixed that wrong charset was used in some cases
This commit is contained in:
parent
969919146e
commit
1ff701ee0c
7 changed files with 77 additions and 34 deletions
|
|
@ -99,11 +99,20 @@ ha_checksum mi_unique_hash(MI_UNIQUEDEF *def, const byte *record)
|
|||
end= pos+length;
|
||||
if (type == HA_KEYTYPE_TEXT || type == HA_KEYTYPE_VARTEXT)
|
||||
{
|
||||
uchar *sort_order=keyseg->charset->sort_order;
|
||||
while (pos != end)
|
||||
crc=((crc << 8) +
|
||||
(((uchar) sort_order[*(uchar*) pos++]))) +
|
||||
(crc >> (8*sizeof(ha_checksum)-8));
|
||||
if (keyseg->charset->hash_sort)
|
||||
{
|
||||
ulong nr=1, nr2=4;
|
||||
keyseg->charset->hash_sort(keyseg->charset,(const uchar*)pos,length,&nr, &nr2);
|
||||
crc=nr;
|
||||
}
|
||||
else
|
||||
{
|
||||
uchar *sort_order=keyseg->charset->sort_order;
|
||||
while (pos != end)
|
||||
crc=((crc << 8) +
|
||||
(((uchar) sort_order[*(uchar*) pos++]))) +
|
||||
(crc >> (8*sizeof(ha_checksum)-8));
|
||||
}
|
||||
}
|
||||
else
|
||||
while (pos != end)
|
||||
|
|
@ -173,11 +182,19 @@ int mi_unique_comp(MI_UNIQUEDEF *def, const byte *a, const byte *b,
|
|||
end= pos_a+length;
|
||||
if (type == HA_KEYTYPE_TEXT || type == HA_KEYTYPE_VARTEXT)
|
||||
{
|
||||
uchar *sort_order=keyseg->charset->sort_order;
|
||||
while (pos_a != end)
|
||||
if (sort_order[*(uchar*) pos_a++] !=
|
||||
sort_order[*(uchar*) pos_b++])
|
||||
if (use_strcoll(keyseg->charset))
|
||||
{
|
||||
if (my_strnncoll(keyseg->charset,pos_a,length,pos_b,length))
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
uchar *sort_order=keyseg->charset->sort_order;
|
||||
while (pos_a != end)
|
||||
if (sort_order[*(uchar*) pos_a++] !=
|
||||
sort_order[*(uchar*) pos_b++])
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
while (pos_a != end)
|
||||
|
|
|
|||
11
sql/field.cc
11
sql/field.cc
|
|
@ -3782,10 +3782,10 @@ uint Field_varstring::max_packed_col_length(uint max_length)
|
|||
Field_blob::Field_blob(char *ptr_arg, uchar *null_ptr_arg, uchar null_bit_arg,
|
||||
enum utype unireg_check_arg, const char *field_name_arg,
|
||||
struct st_table *table_arg,uint blob_pack_length,
|
||||
bool binary_arg)
|
||||
bool binary_arg, CHARSET_INFO *cs)
|
||||
:Field_str(ptr_arg, (1L << min(blob_pack_length,3)*8)-1L,
|
||||
null_ptr_arg, null_bit_arg, unireg_check_arg, field_name_arg,
|
||||
table_arg, default_charset_info),
|
||||
table_arg, cs),
|
||||
packlength(blob_pack_length),binary_flag(binary_arg), geom_flag(true)
|
||||
{
|
||||
flags|= BLOB_FLAG;
|
||||
|
|
@ -3967,9 +3967,9 @@ String *Field_blob::val_str(String *val_buffer __attribute__((unused)),
|
|||
char *blob;
|
||||
memcpy_fixed(&blob,ptr+packlength,sizeof(char*));
|
||||
if (!blob)
|
||||
val_ptr->set("",0,default_charset_info); // A bit safer than ->length(0)
|
||||
val_ptr->set("",0,field_charset); // A bit safer than ->length(0)
|
||||
else
|
||||
val_ptr->set((const char*) blob,get_length(ptr),default_charset_info);
|
||||
val_ptr->set((const char*) blob,get_length(ptr),field_charset);
|
||||
return val_ptr;
|
||||
}
|
||||
|
||||
|
|
@ -4782,7 +4782,8 @@ Field *make_field(char *ptr, uint32 field_length,
|
|||
if (f_is_blob(pack_flag))
|
||||
return new Field_blob(ptr,null_pos,null_bit,
|
||||
unireg_check, field_name, table,
|
||||
pack_length,f_is_binary(pack_flag) != 0);
|
||||
pack_length,f_is_binary(pack_flag) != 0,
|
||||
default_charset_info);
|
||||
if (f_is_geom(pack_flag))
|
||||
return new Field_geom(ptr,null_pos,null_bit,
|
||||
unireg_check, field_name, table,
|
||||
|
|
|
|||
11
sql/field.h
11
sql/field.h
|
|
@ -842,11 +842,11 @@ public:
|
|||
Field_blob(char *ptr_arg, uchar *null_ptr_arg, uchar null_bit_arg,
|
||||
enum utype unireg_check_arg, const char *field_name_arg,
|
||||
struct st_table *table_arg,uint blob_pack_length,
|
||||
bool binary_arg);
|
||||
bool binary_arg, CHARSET_INFO *cs);
|
||||
Field_blob(uint32 len_arg,bool maybe_null_arg, const char *field_name_arg,
|
||||
struct st_table *table_arg, bool binary_arg)
|
||||
struct st_table *table_arg, bool binary_arg, CHARSET_INFO *cs)
|
||||
:Field_str((char*) 0,len_arg, maybe_null_arg ? (uchar*) "": 0,0,
|
||||
NONE, field_name_arg, table_arg, default_charset_info),
|
||||
NONE, field_name_arg, table_arg, cs),
|
||||
packlength(3),binary_flag(binary_arg), geom_flag(true)
|
||||
{
|
||||
flags|= BLOB_FLAG;
|
||||
|
|
@ -930,11 +930,12 @@ public:
|
|||
struct st_table *table_arg,uint blob_pack_length,
|
||||
bool binary_arg)
|
||||
:Field_blob(ptr_arg, null_ptr_arg, null_bit_arg, unireg_check_arg,
|
||||
field_name_arg, table_arg, blob_pack_length,binary_arg) {}
|
||||
field_name_arg, table_arg, blob_pack_length,binary_arg,
|
||||
default_charset_info) {}
|
||||
Field_geom(uint32 len_arg,bool maybe_null_arg, const char *field_name_arg,
|
||||
struct st_table *table_arg, bool binary_arg)
|
||||
:Field_blob(len_arg, maybe_null_arg, field_name_arg,
|
||||
table_arg, binary_arg) {}
|
||||
table_arg, binary_arg, default_charset_info) {}
|
||||
enum ha_base_keytype key_type() const { return HA_KEYTYPE_VARBINARY; }
|
||||
|
||||
void get_key_image(char *buff,uint length, imagetype type);
|
||||
|
|
|
|||
|
|
@ -508,7 +508,8 @@ void field_conv(Field *to,Field *from)
|
|||
if (!blob->value.is_alloced() &&
|
||||
from->real_type() != FIELD_TYPE_STRING)
|
||||
blob->value.copy();
|
||||
blob->store(blob->value.ptr(),blob->value.length(),default_charset_info);
|
||||
blob->store(blob->value.ptr(),blob->value.length(),
|
||||
to->binary()?default_charset_info:((Field_str*)to)->charset());
|
||||
return;
|
||||
}
|
||||
if ((from->result_type() == STRING_RESULT &&
|
||||
|
|
|
|||
|
|
@ -1799,7 +1799,7 @@ String *Item_func_conv_charset::val_str(String *str)
|
|||
s=(const uchar*)arg->ptr();
|
||||
se=s+arg->length();
|
||||
|
||||
dmaxlen=arg->length()*(conv_charset->mbmaxlen?conv_charset->mbmaxlen:1)+1;
|
||||
dmaxlen=arg->length()*(to->mbmaxlen?to->mbmaxlen:1)+1;
|
||||
str->alloc(dmaxlen);
|
||||
d0=d=(unsigned char*)str->ptr();
|
||||
de=d+dmaxlen;
|
||||
|
|
@ -1841,7 +1841,7 @@ outp:
|
|||
|
||||
void Item_func_conv_charset::fix_length_and_dec()
|
||||
{
|
||||
/* BAR TODO: What to do here??? */
|
||||
max_length = args[0]->max_length*(conv_charset->mbmaxlen?conv_charset->mbmaxlen:1);
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -1911,6 +1911,32 @@ outp:
|
|||
return str;
|
||||
}
|
||||
|
||||
|
||||
bool Item_func_conv_charset::fix_fields(THD *thd,struct st_table_list *tables)
|
||||
{
|
||||
char buff[STACK_BUFF_ALLOC]; // Max argument in function
|
||||
binary=0;
|
||||
used_tables_cache=0;
|
||||
const_item_cache=1;
|
||||
|
||||
if (thd && check_stack_overrun(thd,buff))
|
||||
return 0; // Fatal error if flag is set!
|
||||
if (args[0]->fix_fields(thd,tables))
|
||||
return 1;
|
||||
maybe_null=args[0]->maybe_null;
|
||||
binary=args[0]->binary;
|
||||
str_value.set_charset(conv_charset);
|
||||
fix_length_and_dec();
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void Item_func_conv_charset3::fix_length_and_dec()
|
||||
{
|
||||
max_length = args[0]->max_length;
|
||||
}
|
||||
|
||||
|
||||
String *Item_func_charset::val_str(String *str)
|
||||
{
|
||||
String *res = args[0]->val_str(str);
|
||||
|
|
@ -1922,14 +1948,6 @@ String *Item_func_charset::val_str(String *str)
|
|||
}
|
||||
|
||||
|
||||
void Item_func_conv_charset3::fix_length_and_dec()
|
||||
{
|
||||
/* BAR TODO: What to do here??? */
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
String *Item_func_hex::val_str(String *str)
|
||||
{
|
||||
if (args[0]->result_type() != STRING_RESULT)
|
||||
|
|
|
|||
|
|
@ -40,7 +40,8 @@ public:
|
|||
if (!t_arg)
|
||||
return result_field;
|
||||
return (max_length > 255) ?
|
||||
(Field *)new Field_blob(max_length,maybe_null, name,t_arg, binary) :
|
||||
(Field *)new Field_blob(max_length,maybe_null, name,t_arg, binary,
|
||||
default_charset_info) :
|
||||
(Field *) new Field_string(max_length,maybe_null, name,t_arg, binary,
|
||||
default_charset_info);
|
||||
}
|
||||
|
|
@ -488,6 +489,7 @@ public:
|
|||
{
|
||||
conv_charset=cs;
|
||||
}
|
||||
bool fix_fields(THD *thd,struct st_table_list *tables);
|
||||
String *val_str(String *);
|
||||
void fix_length_and_dec();
|
||||
const char *func_name() const { return "conv_charset"; }
|
||||
|
|
|
|||
|
|
@ -3523,7 +3523,7 @@ Field *create_tmp_field(THD *thd, TABLE *table,Item *item, Item::Type type,
|
|||
case STRING_RESULT:
|
||||
if (item_sum->max_length > 255)
|
||||
return new Field_blob(item_sum->max_length,maybe_null,
|
||||
item->name,table,item->binary);
|
||||
item->name,table,item->binary,default_charset_info);
|
||||
return new Field_string(item_sum->max_length,maybe_null,
|
||||
item->name,table,item->binary,default_charset_info);
|
||||
}
|
||||
|
|
@ -3576,7 +3576,8 @@ Field *create_tmp_field(THD *thd, TABLE *table,Item *item, Item::Type type,
|
|||
case STRING_RESULT:
|
||||
if (item->max_length > 255)
|
||||
new_field= new Field_blob(item->max_length,maybe_null,
|
||||
item->name,table,item->binary);
|
||||
item->name,table,item->binary,
|
||||
item->str_value.charset());
|
||||
else
|
||||
new_field= new Field_string(item->max_length,maybe_null,
|
||||
item->name,table,item->binary,
|
||||
|
|
@ -4104,7 +4105,9 @@ static bool create_myisam_tmp_table(TABLE *table,TMP_TABLE_PARAM *param,
|
|||
{
|
||||
Field *field=keyinfo->key_part[i].field;
|
||||
seg->flag= 0;
|
||||
seg->language= MY_CHARSET_CURRENT;
|
||||
seg->language= field->binary() ? MY_CHARSET_CURRENT :
|
||||
((Field_str*)field)->charset()->number;
|
||||
|
||||
seg->length= keyinfo->key_part[i].length;
|
||||
seg->start= keyinfo->key_part[i].offset;
|
||||
if (field->flags & BLOB_FLAG)
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue