diff options
author | Igor Solodovnikov <igor.solodovnikov@oracle.com> | 2013-02-07 19:46:08 +0200 |
---|---|---|
committer | Igor Solodovnikov <igor.solodovnikov@oracle.com> | 2013-02-07 19:46:08 +0200 |
commit | cb08544b575cf61c0597c255f1234765368e1ff3 (patch) | |
tree | 96d17e2d721bfa0bfb7dec5efefc7c2ec90c0d0d /sql/sql_parse.cc | |
parent | 370ac0669e41a41a6f73850aee0cb3b5675c49b8 (diff) | |
download | mariadb-git-cb08544b575cf61c0597c255f1234765368e1ff3.tar.gz |
bug#14163155 COM_CHANGE_USER DOESN'T WORK WITH CHARACTER-SET-SERVER=UCS2 IN
5.1 SERVER
Problem was caused by the COM_CHANGE_USER parsing code. That code ignored
character set number passed in COM_CHANGE_USER packet. Instead
character_set_client values was used. User name was not converted at all.
Fixed by using passed character set number to convert both db and user names.
If COM_CHANGE_USER does not contain character set number then
character_set_client is used to convert both names.
Diffstat (limited to 'sql/sql_parse.cc')
-rw-r--r-- | sql/sql_parse.cc | 35 |
1 files changed, 21 insertions, 14 deletions
diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index 6c376d2c0da..457be355f81 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -1,5 +1,5 @@ /* - Copyright (c) 2000, 2011, Oracle and/or its affiliates. All rights reserved. + Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved. This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -1109,6 +1109,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd, char *user= (char*) packet, *packet_end= packet + packet_length; /* Safe because there is always a trailing \0 at the end of the packet */ char *passwd= strend(user)+1; + uint user_length= passwd - user - 1; thd->change_user(); thd->clear_error(); // if errors from rollback @@ -1122,6 +1123,7 @@ bool dispatch_command(enum enum_server_command command, THD *thd, for *passwd > 127 and become 2**32-127 after casting to uint. */ char db_buff[NAME_LEN+1]; // buffer to store db in utf8 + char user_buff[USERNAME_LENGTH + 1]; // buffer to store user in utf8 char *db= passwd; char *save_db; /* @@ -1172,15 +1174,31 @@ bool dispatch_command(enum enum_server_command command, THD *thd, my_error(ER_WRONG_VALUE_FOR_VAR, MYF(0), "character_set_client", cs->csname); break; - } + } + + if (cs_number) + { + /* + We have checked charset earlier, + so thd_init_client_charset cannot fail. + */ + if (thd_init_client_charset(thd, cs_number)) + DBUG_ASSERT(0); + thd->update_charset(); + } } - /* Convert database name to utf8 */ + /* Convert database and user names to utf8 */ db_buff[copy_and_convert(db_buff, sizeof(db_buff)-1, system_charset_info, db, db_length, thd->charset(), &dummy_errors)]= 0; db= db_buff; + user_buff[copy_and_convert(user_buff,sizeof(user_buff)-1, + system_charset_info, user, user_length, + thd->charset(), &dummy_errors)]= 0; + user= user_buff; + /* Save user and privileges */ save_db_length= thd->db_length; save_db= thd->db; @@ -1215,17 +1233,6 @@ bool dispatch_command(enum enum_server_command command, THD *thd, #endif /* NO_EMBEDDED_ACCESS_CHECKS */ x_free(save_db); x_free(save_security_ctx.user); - - if (cs_number) - { - /* - We have checked charset earlier, - so thd_init_client_charset cannot fail. - */ - if (thd_init_client_charset(thd, cs_number)) - DBUG_ASSERT(0); - thd->update_charset(); - } } break; } |