diff --git a/include/my_sys.h b/include/my_sys.h index 86ca6ec6a1f..5a769791955 100644 --- a/include/my_sys.h +++ b/include/my_sys.h @@ -216,7 +216,6 @@ extern CHARSET_INFO *get_charset_by_name(const char *cs_name, myf flags); extern CHARSET_INFO *get_charset_by_csname(const char *cs_name, uint cs_flags, myf my_flags); extern void free_charsets(void); -extern char *list_charsets(myf want_flags); /* my_free() this string... */ extern char *get_charsets_dir(char *buf); extern my_bool my_charset_same(CHARSET_INFO *cs1, CHARSET_INFO *cs2); diff --git a/mysql-test/t/ctype_latin1_de-master.opt b/mysql-test/t/ctype_latin1_de-master.opt index 62f864d501d..79fdb1c63dc 100644 --- a/mysql-test/t/ctype_latin1_de-master.opt +++ b/mysql-test/t/ctype_latin1_de-master.opt @@ -1 +1 @@ ---default-character-set=latin1_german2_ci +--default-character-set=latin1 --default-collation=latin1_german2_ci diff --git a/mysys/charset.c b/mysys/charset.c index 097c35caa56..2d9500e4b0d 100644 --- a/mysys/charset.c +++ b/mysys/charset.c @@ -688,70 +688,3 @@ static void charset_append(DYNAMIC_STRING *s, const char *name) dynstr_append(s, " "); } } - - -/* Returns a dynamically-allocated string listing the character sets - requested. The caller is responsible for freeing the memory. */ - -char *list_charsets(myf want_flags) -{ - DYNAMIC_STRING s; - char *p; - - (void)init_available_charsets(MYF(0)); - init_dynamic_string(&s, NullS, 256, 1024); - - if (want_flags & MY_CS_COMPILED) - { - CHARSET_INFO **cs; - for (cs= all_charsets; cs < all_charsets+255; cs++) - { - if (cs[0]) - { - dynstr_append(&s, cs[0]->name); - dynstr_append(&s, " "); - } - } - } - - if (want_flags & MY_CS_CONFIG) - { - CHARSET_INFO **cs; - char buf[FN_REFLEN]; - MY_STAT status; - - for (cs=all_charsets; cs < all_charsets+255; cs++) - { - if (!cs[0] || !cs[0]->name || charset_in_string(cs[0]->name, &s)) - continue; - get_charset_conf_name(cs[0]->name, buf); - if (!my_stat(buf, &status, MYF(0))) - continue; /* conf file doesn't exist */ - dynstr_append(&s, cs[0]->name); - dynstr_append(&s, " "); - } - } - - if (want_flags & (MY_CS_INDEX|MY_CS_LOADED)) - { - CHARSET_INFO **cs; - for (cs= all_charsets; cs < all_charsets + 255; cs++) - if (cs[0] && cs[0]->name && (cs[0]->state & want_flags) ) - charset_append(&s, cs[0]->name); - } - - if (s.length) - { - s.str[s.length - 1]= '\0'; /* chop trailing space */ - p= my_strdup(s.str, MYF(MY_WME)); - } - else - { - p= my_strdup("", MYF(MY_WME)); - } - dynstr_free(&s); - - return p; -} - - diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h index ea6e544a1fd..632007d1415 100644 --- a/sql/mysql_priv.h +++ b/sql/mysql_priv.h @@ -678,7 +678,7 @@ bool open_log(MYSQL_LOG *log, const char *hostname, extern time_t start_time; extern char *mysql_data_home,server_version[SERVER_VERSION_LENGTH], - mysql_real_data_home[], *charsets_list, *opt_mysql_tmpdir; + mysql_real_data_home[], *opt_mysql_tmpdir; #define mysql_tmpdir (my_tmpdir(&mysql_tmpdir_list)) extern MY_TMPDIR mysql_tmpdir_list; extern const char *command_name[]; diff --git a/sql/mysqld.cc b/sql/mysqld.cc index f73bd6721f0..b8b57f4e2f3 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -420,11 +420,12 @@ ulong expire_logs_days = 0; char mysql_real_data_home[FN_REFLEN], language[LIBLEN],reg_ext[FN_EXTLEN], - mysql_charsets_dir[FN_REFLEN], *charsets_list, + mysql_charsets_dir[FN_REFLEN], blob_newline,f_fyllchar,max_sort_char,*mysqld_user,*mysqld_chroot, *opt_init_file; char *language_ptr= language; char mysql_data_home_buff[2], *mysql_data_home=mysql_real_data_home; +char *default_collation_name= (char*) default_charset_info->name; #ifndef EMBEDDED_LIBRARY bool mysql_embedded=0; #else @@ -941,7 +942,6 @@ void clean_up(bool print_message) #endif if (defaults_argv) free_defaults(defaults_argv); - my_free(charsets_list, MYF(MY_ALLOW_ZERO_PTR)); free_tmpdir(&mysql_tmpdir_list); #ifdef HAVE_REPLICATION my_free(slave_load_tmpdir,MYF(MY_ALLOW_ZERO_PTR)); @@ -2088,14 +2088,28 @@ static int init_common_variables(const char *conf_file_name, int argc, #ifdef USE_REGEX regex_init(&my_charset_latin1); #endif - if (!(default_charset_info= get_charset_by_name(sys_charset.value, MYF(MY_WME)))) + if (!(default_charset_info= get_charset_by_csname(sys_charset.value, + MY_CS_PRIMARY, + MYF(MY_WME)))) return 1; + if (default_collation_name) + { + CHARSET_INFO *default_collation= get_charset_by_name(default_collation_name, + MYF(0)); + if (!default_collation || !my_charset_same(default_charset_info, + default_collation)) + { + sql_print_error(ER(ER_COLLATION_CHARSET_MISMATCH), + default_collation_name, + default_charset_info->csname); + return 1; + } + default_charset_info= default_collation; + } global_system_variables.collation_results= default_charset_info; global_system_variables.collation_client= default_charset_info; global_system_variables.collation_connection= default_charset_info; - charsets_list= list_charsets(MYF(MY_CS_COMPILED | MY_CS_CONFIG)); - if (use_temp_pool && bitmap_init(&temp_pool,1024,1)) return 1; return 0; @@ -3492,7 +3506,8 @@ enum options OPT_OLD_PASSWORDS, OPT_EXPIRE_LOGS_DAYS, OPT_DEFAULT_WEEK_FORMAT, - OPT_GROUP_CONCAT_MAX_LEN + OPT_GROUP_CONCAT_MAX_LEN, + OPT_DEFAULT_COLLATION }; @@ -3581,6 +3596,9 @@ Disable with --skip-bdb (will save memory)", {"default-character-set", 'C', "Set the default character set", (gptr*) &sys_charset.value, (gptr*) &sys_charset.value, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0 }, + {"default-collation", OPT_DEFAULT_COLLATION, "Set the default collation", + (gptr*) &default_collation_name, (gptr*) &default_collation_name, + 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0 }, {"default-table-type", OPT_TABLE_TYPE, "Set the default table type for tables", 0, 0, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0}, @@ -4586,6 +4604,7 @@ static void set_options(void) #endif sys_charset.value= (char*) MYSQL_CHARSET; + sys_charset_system.value= (char*) system_charset_info->csname; (void) strmake(language, LANGUAGE, sizeof(language)-1); (void) strmake(mysql_real_data_home, get_relative_path(DATADIR), sizeof(mysql_real_data_home)-1); @@ -4643,6 +4662,9 @@ get_one_option(int optid, const struct my_option *opt __attribute__((unused)), case 'b': strmake(mysql_home,argument,sizeof(mysql_home)-1); break; + case 'C': + default_collation_name= NULL; + break; case 'l': opt_log=1; break; diff --git a/sql/set_var.cc b/sql/set_var.cc index e8ae9b90a6c..c9b8584e672 100644 --- a/sql/set_var.cc +++ b/sql/set_var.cc @@ -105,6 +105,10 @@ sys_var_str sys_charset("character_set", sys_check_charset, sys_update_charset, sys_set_default_charset); +sys_var_str sys_charset_system("character_set_system", + sys_check_charset, + sys_update_charset, + sys_set_default_charset); sys_var_collation_client sys_collation_client("collation_client"); sys_var_collation_connection sys_collation_connection("collation_connection"); sys_var_collation_results sys_collation_results("collation_results"); @@ -463,8 +467,8 @@ struct show_var_st init_vars[]= { #endif {sys_binlog_cache_size.name,(char*) &sys_binlog_cache_size, SHOW_SYS}, {sys_bulk_insert_buff_size.name,(char*) &sys_bulk_insert_buff_size,SHOW_SYS}, - {sys_charset.name, (char*) &sys_charset, SHOW_SYS}, - {"character_sets", (char*) &charsets_list, SHOW_CHAR_PTR}, + {sys_charset.name, (char*) &sys_charset, SHOW_SYS}, + {sys_charset_system.name, (char*) &sys_charset_system, SHOW_SYS}, {sys_collation_client.name, (char*) &sys_collation_client, SHOW_SYS}, {sys_collation_connection.name,(char*) &sys_collation_connection, SHOW_SYS}, {sys_collation_results.name, (char*) &sys_collation_results, SHOW_SYS}, diff --git a/sql/set_var.h b/sql/set_var.h index fbd20228d24..03cc3b30a03 100644 --- a/sql/set_var.h +++ b/sql/set_var.h @@ -582,4 +582,5 @@ int sql_set_variables(THD *thd, List *var_list); void fix_delay_key_write(THD *thd, enum_var_type type); extern sys_var_str sys_charset; +extern sys_var_str sys_charset_system; CHARSET_INFO *get_old_charset_by_name(const char *old_name);