Merge marko@bk-internal.mysql.com:/home/bk/mysql-5.0

into hundin.mysql.fi:/home/marko/k/mysql-5.0


sql/ha_innodb.cc:
  Auto merged
This commit is contained in:
unknown 2005-02-14 17:23:12 +02:00
commit cc2843e2fa
7 changed files with 165 additions and 56 deletions

View file

@ -41,7 +41,7 @@ charset-collation code for them. */
ulint data_mysql_default_charset_coll = 99999999;
ulint data_mysql_latin1_swedish_charset_coll = 99999999;
dtype_t dtype_binary_val = {DATA_BINARY, 0, 0, 0};
dtype_t dtype_binary_val = {DATA_BINARY, 0, 0, 0, 0, 0};
dtype_t* dtype_binary = &dtype_binary_val;
/*************************************************************************
@ -216,6 +216,8 @@ dtype_validate(
ut_a((type->prtype & DATA_MYSQL_TYPE_MASK) < DATA_N_SYS_COLS);
}
ut_a(type->mbminlen <= type->mbmaxlen);
return(TRUE);
}

View file

@ -271,6 +271,24 @@ dtype_get_prec(
/*===========*/
dtype_t* type);
/*************************************************************************
Gets the minimum length of a character, in bytes. */
UNIV_INLINE
ulint
dtype_get_mbminlen(
/*===============*/
/* out: minimum length of a char, in bytes,
or 0 if this is not a character type */
const dtype_t* type); /* in: type */
/*************************************************************************
Gets the maximum length of a character, in bytes. */
UNIV_INLINE
ulint
dtype_get_mbmaxlen(
/*===============*/
/* out: maximum length of a char, in bytes,
or 0 if this is not a character type */
const dtype_t* type); /* in: type */
/*************************************************************************
Gets the padding character code for the type. */
UNIV_INLINE
ulint
@ -352,16 +370,25 @@ dtype_print(
/*========*/
dtype_t* type); /* in: type */
/* Structure for an SQL data type */
/* Structure for an SQL data type.
If you add fields to this structure, be sure to initialize them everywhere.
This structure is initialized in the following functions:
dtype_set()
dtype_read_for_order_and_null_size()
dtype_new_read_for_order_and_null_size()
sym_tab_add_null_lit() */
struct dtype_struct{
ulint mtype; /* main data type */
ulint prtype; /* precise type; MySQL data type */
/* the remaining two fields do not affect alphabetical ordering: */
/* the remaining fields do not affect alphabetical ordering: */
ulint len; /* length */
ulint prec; /* precision */
ulint mbminlen; /* minimum length of a character, in bytes */
ulint mbmaxlen; /* maximum length of a character, in bytes */
};
#ifndef UNIV_NONINL

View file

@ -9,15 +9,46 @@ Created 1/16/1996 Heikki Tuuri
#include "mach0data.h"
/**********************************************************************
Determines whether the given character set is of variable length.
Get the variable length bounds of the given character set.
NOTE: the prototype of this function is copied from ha_innodb.cc! If you change
this function, you MUST change also the prototype here! */
extern
ibool
innobase_is_mb_cset(
/*================*/
ulint cset); /* in: MySQL charset-collation code */
void
innobase_get_cset_width(
/*====================*/
ulint cset, /* in: MySQL charset-collation code */
ulint* mbminlen, /* out: minimum length of a char (in bytes) */
ulint* mbmaxlen); /* out: maximum length of a char (in bytes) */
/*************************************************************************
Gets the MySQL charset-collation code for MySQL string types. */
UNIV_INLINE
ulint
dtype_get_charset_coll(
/*===================*/
ulint prtype) /* in: precise data type */
{
return((prtype >> 16) & 0xFFUL);
}
/*************************************************************************
Sets the mbminlen and mbmaxlen members of a data type structure. */
UNIV_INLINE
void
dtype_set_mblen(
/*============*/
dtype_t* type) /* in/out: type struct */
{
ut_ad(type);
if (dtype_is_string_type(type->mtype)) {
innobase_get_cset_width(dtype_get_charset_coll(type->prtype),
&type->mbminlen, &type->mbmaxlen);
ut_ad(type->mbminlen <= type->mbmaxlen);
} else {
type->mbminlen = type->mbmaxlen = 0;
}
}
/*************************************************************************
Sets a data type structure. */
@ -39,6 +70,7 @@ dtype_set(
type->len = len;
type->prec = prec;
dtype_set_mblen(type);
ut_ad(dtype_validate(type));
}
@ -82,17 +114,6 @@ dtype_get_prtype(
return(type->prtype);
}
/*************************************************************************
Gets the MySQL charset-collation code for MySQL string types. */
UNIV_INLINE
ulint
dtype_get_charset_coll(
/*===================*/
ulint prtype) /* in: precise data type */
{
return((prtype >> 16) & 0xFFUL);
}
/*************************************************************************
Gets the type length. */
UNIV_INLINE
@ -119,6 +140,33 @@ dtype_get_prec(
return(type->prec);
}
/*************************************************************************
Gets the minimum length of a character, in bytes. */
UNIV_INLINE
ulint
dtype_get_mbminlen(
/*===============*/
/* out: minimum length of a char, in bytes,
or 0 if this is not a character type */
const dtype_t* type) /* in: type */
{
ut_ad(type);
return(type->mbminlen);
}
/*************************************************************************
Gets the maximum length of a character, in bytes. */
UNIV_INLINE
ulint
dtype_get_mbmaxlen(
/*===============*/
/* out: maximum length of a char, in bytes,
or 0 if this is not a character type */
const dtype_t* type) /* in: type */
{
ut_ad(type);
return(type->mbmaxlen);
}
/*************************************************************************
Gets the padding character code for the type. */
UNIV_INLINE
@ -211,6 +259,7 @@ dtype_read_for_order_and_null_size(
type->prtype = dtype_form_prtype(type->prtype,
data_mysql_default_charset_coll);
dtype_set_mblen(type);
}
/**************************************************************************
@ -262,6 +311,7 @@ dtype_new_read_for_order_and_null_size(
type->prtype = dtype_form_prtype(type->prtype, charset_coll);
}
dtype_set_mblen(type);
}
/***************************************************************************
@ -305,11 +355,40 @@ dtype_get_fixed_size(
case DATA_FLOAT:
case DATA_DOUBLE:
case DATA_MYSQL:
if ((type->prtype & DATA_BINARY_TYPE)
|| !innobase_is_mb_cset(
dtype_get_charset_coll(
type->prtype))) {
if (type->prtype & DATA_BINARY_TYPE) {
return(dtype_get_len(type));
} else {
/* We play it safe here and ask MySQL for
mbminlen and mbmaxlen. Although
type->mbminlen and type->mbmaxlen are
initialized if and only if type->prtype
is (in one of the 3 functions in this file),
it could be that none of these functions
has been called. */
ulint mbminlen, mbmaxlen;
innobase_get_cset_width(
dtype_get_charset_coll(type->prtype),
&mbminlen, &mbmaxlen);
if (type->mbminlen != mbminlen
|| type->mbmaxlen != mbmaxlen) {
ut_print_timestamp(stderr);
fprintf(stderr, " InnoDB: "
"mbminlen=%lu, "
"mbmaxlen=%lu, "
"type->mbminlen=%lu, "
"type->mbmaxlen=%lu\n",
(ulong) mbminlen,
(ulong) mbmaxlen,
(ulong) type->mbminlen,
(ulong) type->mbmaxlen);
}
if (mbminlen == mbmaxlen) {
return(dtype_get_len(type));
}
}
/* fall through for variable-length charsets */
case DATA_VARCHAR:

View file

@ -458,6 +458,10 @@ struct mysql_row_templ_struct {
numbers DATA_CHAR... */
ulint charset; /* MySQL charset-collation code
of the column, or zero */
ulint mbminlen; /* minimum length of a char, in bytes,
or zero if not a char type */
ulint mbmaxlen; /* maximum length of a char, in bytes,
or zero if not a char type */
ulint is_unsigned; /* if a column type is an integer
type and this field is != 0, then
it is an unsigned integer type */

View file

@ -93,17 +93,11 @@ row_mysql_store_col_in_innobase_format(
|| type == DATA_BINARY) {
/* Remove trailing spaces. */
/* Handle UCS2 strings differently. As no new
collations will be introduced in 4.1, we hardcode the
charset-collation codes here. In 5.0, the logic will
be based on mbminlen. */
ulint cset = dtype_get_charset_coll(
dtype_get_prtype(dfield_get_type(dfield)));
/* Handle UCS2 strings differently. */
ulint mbminlen = dtype_get_mbminlen(
dfield_get_type(dfield));
ptr = row_mysql_read_var_ref(&col_len, mysql_data);
if (cset == 35/*ucs2_general_ci*/
|| cset == 90/*ucs2_bin*/
|| (cset >= 128/*ucs2_unicode_ci*/
&& cset <= 144/*ucs2_persian_ci*/)) {
if (mbminlen == 2) {
/* space=0x0020 */
/* Trim "half-chars", just in case. */
col_len &= ~1;
@ -113,6 +107,7 @@ row_mysql_store_col_in_innobase_format(
col_len -= 2;
}
} else {
ut_a(mbminlen == 1);
/* space=0x20 */
while (col_len > 0 && ptr[col_len - 1] == 0x20) {
col_len--;

View file

@ -2410,14 +2410,9 @@ row_sel_store_mysql_rec(
/* Pad with trailing spaces */
data = mysql_rec + templ->mysql_col_offset;
/* Handle UCS2 strings differently. As no new
collations will be introduced in 4.1, we
hardcode the charset-collation codes here.
5.0 will use a different approach. */
if (templ->charset == 35
|| templ->charset == 90
|| (templ->charset >= 128
&& templ->charset <= 144)) {
ut_ad(templ->mbminlen <= templ->mbmaxlen);
/* Handle UCS2 strings differently. */
if (templ->mbminlen == 2) {
/* space=0x0020 */
ulint col_len = templ->mysql_col_len;
@ -2436,6 +2431,7 @@ row_sel_store_mysql_rec(
data[len++] = 0x20;
}
} else {
ut_ad(templ->mbminlen == 1);
/* space=0x20 */
memset(data + len, 0x20,
templ->mysql_col_len - len);
@ -2477,14 +2473,8 @@ row_sel_store_mysql_rec(
pad_char = '\0';
}
/* Handle UCS2 strings differently. As no new
collations will be introduced in 4.1,
we hardcode the charset-collation codes here.
5.0 will use a different approach. */
if (templ->charset == 35
|| templ->charset == 90
|| (templ->charset >= 128
&& templ->charset <= 144)) {
/* Handle UCS2 strings differently. */
if (templ->mbminlen == 2) {
/* There are two bytes per char, so the length
has to be an even number. */
ut_a(!(templ->mysql_col_len & 1));
@ -2497,6 +2487,7 @@ row_sel_store_mysql_rec(
len -= 2;
}
} else {
ut_ad(templ->mbminlen == 1);
memset(mysql_rec + templ->mysql_col_offset,
pad_char, templ->mysql_col_len);
}