summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/sql_common.h1
-rw-r--r--libmysqld/lib_sql.cc7
-rw-r--r--libmysqld/libmysqld.c48
-rw-r--r--mysql-test/r/gis.result9
-rw-r--r--mysql-test/t/gis.test5
-rw-r--r--sql-common/client.c86
-rw-r--r--sql/item_geofunc.h2
-rw-r--r--sql/sql_parse.cc59
8 files changed, 108 insertions, 109 deletions
diff --git a/include/sql_common.h b/include/sql_common.h
index c07a4a831bb..9fc8d4f457b 100644
--- a/include/sql_common.h
+++ b/include/sql_common.h
@@ -22,6 +22,7 @@ extern const char *not_error_sqlstate;
extern "C" {
#endif
+extern CHARSET_INFO *default_client_charset_info;
MYSQL_FIELD *unpack_fields(MYSQL_DATA *data,MEM_ROOT *alloc,uint fields,
my_bool default_value, uint server_capabilities);
void free_rows(MYSQL_DATA *cur);
diff --git a/libmysqld/lib_sql.cc b/libmysqld/lib_sql.cc
index a2fdae994b1..a2c570c2fbc 100644
--- a/libmysqld/lib_sql.cc
+++ b/libmysqld/lib_sql.cc
@@ -37,6 +37,8 @@ extern "C"
int check_user(THD *thd, enum enum_server_command command,
const char *passwd, uint passwd_len, const char *db,
bool check_count);
+void thd_init_client_charset(THD *thd, uint cs_number);
+
C_MODE_START
#include <mysql.h>
@@ -600,11 +602,14 @@ err:
return NULL;
}
+
#ifdef NO_EMBEDDED_ACCESS_CHECKS
int check_embedded_connection(MYSQL *mysql)
{
int result;
THD *thd= (THD*)mysql->thd;
+ thd_init_client_charset(thd, mysql->charset->number);
+ thd->update_charset();
Security_context *sctx= thd->security_ctx;
sctx->host_or_ip= sctx->host= (char*) my_localhost;
strmake(sctx->priv_host, (char*) my_localhost, MAX_HOSTNAME-1);
@@ -623,6 +628,8 @@ int check_embedded_connection(MYSQL *mysql)
char scramble_buff[SCRAMBLE_LENGTH];
int passwd_len;
+ thd_init_client_charset(thd, mysql->charset->number);
+ thd->update_charset();
if (mysql->options.client_ip)
{
sctx->host= my_strdup(mysql->options.client_ip, MYF(0));
diff --git a/libmysqld/libmysqld.c b/libmysqld/libmysqld.c
index cad1bd4c47b..5df61783451 100644
--- a/libmysqld/libmysqld.c
+++ b/libmysqld/libmysqld.c
@@ -90,49 +90,7 @@ static void end_server(MYSQL *mysql)
}
-static int mysql_init_charset(MYSQL *mysql)
-{
- char charset_name_buff[16], *charset_name;
-
- if ((charset_name=mysql->options.charset_name))
- {
- const char *save=charsets_dir;
- if (mysql->options.charset_dir)
- charsets_dir=mysql->options.charset_dir;
- mysql->charset=get_charset_by_name(mysql->options.charset_name,
- MYF(MY_WME));
- charsets_dir=save;
- }
- else if (mysql->server_language)
- {
- charset_name=charset_name_buff;
- sprintf(charset_name,"%d",mysql->server_language); /* In case of errors */
- mysql->charset=get_charset((uint8) mysql->server_language, MYF(MY_WME));
- }
- else
- mysql->charset=default_charset_info;
-
- if (!mysql->charset)
- {
- mysql->net.last_errno=CR_CANT_READ_CHARSET;
- strmov(mysql->net.sqlstate, "HY0000");
- if (mysql->options.charset_dir)
- sprintf(mysql->net.last_error,ER(mysql->net.last_errno),
- charset_name ? charset_name : "unknown",
- mysql->options.charset_dir);
- else
- {
- char cs_dir_name[FN_REFLEN];
- get_charsets_dir(cs_dir_name);
- sprintf(mysql->net.last_error,ER(mysql->net.last_errno),
- charset_name ? charset_name : "unknown",
- cs_dir_name);
- }
- return mysql->net.last_errno;
- }
- return 0;
-}
-
+int mysql_init_character_set(MYSQL *mysql);
MYSQL * STDCALL
mysql_real_connect(MYSQL *mysql,const char *host, const char *user,
@@ -222,10 +180,10 @@ mysql_real_connect(MYSQL *mysql,const char *host, const char *user,
init_embedded_mysql(mysql, client_flag, db_name);
- if (check_embedded_connection(mysql))
+ if (mysql_init_character_set(mysql))
goto error;
- if (mysql_init_charset(mysql))
+ if (check_embedded_connection(mysql))
goto error;
mysql->server_status= SERVER_STATUS_AUTOCOMMIT;
diff --git a/mysql-test/r/gis.result b/mysql-test/r/gis.result
index 13e2d56d83e..8d1f0bb3937 100644
--- a/mysql-test/r/gis.result
+++ b/mysql-test/r/gis.result
@@ -693,4 +693,13 @@ create table t1(pt GEOMETRY);
alter table t1 add primary key pti(pt);
ERROR 42000: BLOB/TEXT column 'pt' used in key specification without a key length
alter table t1 add primary key pti(pt(20));
+create table t1 (g GEOMETRY);
+select * from t1;
+Catalog Database Table Table_alias Column Column_alias Type Length Max length Is_null Flags Decimals Charsetnr
+def test t1 t1 g g 255 4294967295 0 Y 144 0 63
+g
+select asbinary(g) from t1;
+Catalog Database Table Table_alias Column Column_alias Type Length Max length Is_null Flags Decimals Charsetnr
+def asbinary(g) 252 8192 0 Y 128 0 63
+asbinary(g)
drop table t1;
diff --git a/mysql-test/t/gis.test b/mysql-test/t/gis.test
index bb3f621d194..566dbf882ad 100644
--- a/mysql-test/t/gis.test
+++ b/mysql-test/t/gis.test
@@ -408,4 +408,9 @@ create table t1(pt GEOMETRY);
--error 1170
alter table t1 add primary key pti(pt);
alter table t1 add primary key pti(pt(20));
+--enable_metadata
+create table t1 (g GEOMETRY);
+select * from t1;
+select asbinary(g) from t1;
+--disable_metadata
drop table t1;
diff --git a/sql-common/client.c b/sql-common/client.c
index 26ebc9cc6b0..56a5862c90e 100644
--- a/sql-common/client.c
+++ b/sql-common/client.c
@@ -130,6 +130,8 @@ static void mysql_close_free(MYSQL *mysql);
static int wait_for_data(my_socket fd, uint timeout);
#endif
+CHARSET_INFO *default_client_charset_info = &my_charset_latin1;
+
/****************************************************************************
A modified version of connect(). my_connect() allows you to specify
@@ -1431,7 +1433,7 @@ mysql_init(MYSQL *mysql)
bzero((char*) (mysql), sizeof(*(mysql)));
mysql->options.connect_timeout= CONNECT_TIMEOUT;
mysql->last_used_con= mysql->next_slave= mysql->master = mysql;
- mysql->charset=default_charset_info;
+ mysql->charset=default_client_charset_info;
strmov(mysql->net.sqlstate, not_error_sqlstate);
/*
By default, we are a replication pivot. The caller must reset it
@@ -1660,7 +1662,51 @@ static MYSQL_METHODS client_methods=
#endif
};
-MYSQL *
+C_MODE_START
+int mysql_init_character_set(MYSQL *mysql)
+{
+ NET *net= &mysql->net;
+ /* Set character set */
+ if (!mysql->options.charset_name &&
+ !(mysql->options.charset_name=
+ my_strdup(MYSQL_DEFAULT_CHARSET_NAME,MYF(MY_WME))))
+ return 1;
+
+ {
+ const char *save= charsets_dir;
+ if (mysql->options.charset_dir)
+ charsets_dir=mysql->options.charset_dir;
+ mysql->charset=get_charset_by_csname(mysql->options.charset_name,
+ MY_CS_PRIMARY, MYF(MY_WME));
+ charsets_dir= save;
+ }
+
+ if (!mysql->charset)
+ {
+ net->last_errno=CR_CANT_READ_CHARSET;
+ strmov(net->sqlstate, unknown_sqlstate);
+ if (mysql->options.charset_dir)
+ my_snprintf(net->last_error, sizeof(net->last_error)-1,
+ ER(net->last_errno),
+ mysql->options.charset_name,
+ mysql->options.charset_dir);
+ else
+ {
+ char cs_dir_name[FN_REFLEN];
+ get_charsets_dir(cs_dir_name);
+ my_snprintf(net->last_error, sizeof(net->last_error)-1,
+ ER(net->last_errno),
+ mysql->options.charset_name,
+ cs_dir_name);
+ }
+ return 1;
+ }
+ return 0;
+}
+C_MODE_END
+
+
+MYSQL * STDCALL
CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
const char *passwd, const char *db,
uint port, const char *unix_socket,ulong client_flag)
@@ -1997,42 +2043,8 @@ CLI_MYSQL_REAL_CONNECT(MYSQL *mysql,const char *host, const char *user,
goto error;
}
- /* Set character set */
- if (!mysql->options.charset_name &&
- !(mysql->options.charset_name=
- my_strdup(MYSQL_DEFAULT_CHARSET_NAME,MYF(MY_WME))))
- goto error;
-
- {
- const char *save= charsets_dir;
- if (mysql->options.charset_dir)
- charsets_dir=mysql->options.charset_dir;
- mysql->charset=get_charset_by_csname(mysql->options.charset_name,
- MY_CS_PRIMARY, MYF(MY_WME));
- charsets_dir= save;
- }
-
- if (!mysql->charset)
- {
- net->last_errno=CR_CANT_READ_CHARSET;
- strmov(net->sqlstate, unknown_sqlstate);
- if (mysql->options.charset_dir)
- my_snprintf(net->last_error, sizeof(net->last_error)-1,
- ER(net->last_errno),
- mysql->options.charset_name,
- mysql->options.charset_dir);
- else
- {
- char cs_dir_name[FN_REFLEN];
- get_charsets_dir(cs_dir_name);
- my_snprintf(net->last_error, sizeof(net->last_error)-1,
- ER(net->last_errno),
- mysql->options.charset_name,
- cs_dir_name);
- }
+ if (mysql_init_character_set(mysql))
goto error;
- }
-
/* Save connection information */
if (!my_multi_malloc(MYF(0),
diff --git a/sql/item_geofunc.h b/sql/item_geofunc.h
index c45fb88a48a..1f64fdba609 100644
--- a/sql/item_geofunc.h
+++ b/sql/item_geofunc.h
@@ -32,6 +32,7 @@ public:
Item_geometry_func(Item *a,Item *b,Item *c) :Item_str_func(a,b,c) {}
Item_geometry_func(List<Item> &list) :Item_str_func(list) {}
void fix_length_and_dec();
+ enum_field_types field_type() const { return MYSQL_TYPE_GEOMETRY; }
};
class Item_func_geometry_from_text: public Item_geometry_func
@@ -67,6 +68,7 @@ public:
Item_func_as_wkb(Item *a): Item_geometry_func(a) {}
const char *func_name() const { return "aswkb"; }
String *val_str(String *);
+ enum_field_types field_type() const { return MYSQL_TYPE_BLOB; }
};
class Item_func_geometry_type: public Item_str_func
diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc
index ebbe6e6f558..d0bc2f434d5 100644
--- a/sql/sql_parse.cc
+++ b/sql/sql_parse.cc
@@ -775,6 +775,37 @@ static void reset_mqh(LEX_USER *lu, bool get_them= 0)
#endif /* NO_EMBEDDED_ACCESS_CHECKS */
}
+void thd_init_client_charset(THD *thd, uint cs_number)
+{
+ /*
+ Use server character set and collation if
+ - opt_character_set_client_handshake is not set
+ - client has not specified a character set
+ - client character set is the same as the servers
+ - client character set doesn't exists in server
+ */
+ if (!opt_character_set_client_handshake ||
+ !(thd->variables.character_set_client= get_charset(cs_number, MYF(0))) ||
+ !my_strcasecmp(&my_charset_latin1,
+ global_system_variables.character_set_client->name,
+ thd->variables.character_set_client->name))
+ {
+ thd->variables.character_set_client=
+ global_system_variables.character_set_client;
+ thd->variables.collation_connection=
+ global_system_variables.collation_connection;
+ thd->variables.character_set_results=
+ global_system_variables.character_set_results;
+ }
+ else
+ {
+ thd->variables.character_set_results=
+ thd->variables.collation_connection=
+ thd->variables.character_set_client;
+ }
+}
+
+
/*
Perform handshake, authorize client and update thd ACL variables.
SYNOPSIS
@@ -910,33 +941,7 @@ static int check_connection(THD *thd)
thd->client_capabilities|= ((ulong) uint2korr(net->read_pos+2)) << 16;
thd->max_client_packet_length= uint4korr(net->read_pos+4);
DBUG_PRINT("info", ("client_character_set: %d", (uint) net->read_pos[8]));
- /*
- Use server character set and collation if
- - opt_character_set_client_handshake is not set
- - client has not specified a character set
- - client character set is the same as the servers
- - client character set doesn't exists in server
- */
- if (!opt_character_set_client_handshake ||
- !(thd->variables.character_set_client=
- get_charset((uint) net->read_pos[8], MYF(0))) ||
- !my_strcasecmp(&my_charset_latin1,
- global_system_variables.character_set_client->name,
- thd->variables.character_set_client->name))
- {
- thd->variables.character_set_client=
- global_system_variables.character_set_client;
- thd->variables.collation_connection=
- global_system_variables.collation_connection;
- thd->variables.character_set_results=
- global_system_variables.character_set_results;
- }
- else
- {
- thd->variables.character_set_results=
- thd->variables.collation_connection=
- thd->variables.character_set_client;
- }
+ thd_init_client_charset(thd, (uint) net->read_pos[8]);
thd->update_charset();
end= (char*) net->read_pos+32;
}