diff options
author | Tatiana A. Nurnberg <azundris@mysql.com> | 2009-03-06 16:11:34 +0100 |
---|---|---|
committer | Tatiana A. Nurnberg <azundris@mysql.com> | 2009-03-06 16:11:34 +0100 |
commit | cee070e1bb20552136b2ed5f2351d3b685fbddeb (patch) | |
tree | 7fc5bfde8b352f380a7308cd118a1023c1ddd138 /sql | |
parent | 13328b0f45c449020b3b70ed9de1668e16d51bb4 (diff) | |
parent | 53802ae6ca0ea2d95c9d24b8c07a27213406131e (diff) | |
download | mariadb-git-cee070e1bb20552136b2ed5f2351d3b685fbddeb.tar.gz |
manual merge
Diffstat (limited to 'sql')
-rw-r--r-- | sql/item_func.cc | 10 | ||||
-rw-r--r-- | sql/log.cc | 7 | ||||
-rw-r--r-- | sql/mysqld.cc | 4 | ||||
-rw-r--r-- | sql/opt_range.cc | 57 | ||||
-rw-r--r-- | sql/protocol.cc | 3 | ||||
-rw-r--r-- | sql/rpl_record.cc | 34 | ||||
-rw-r--r-- | sql/set_var.cc | 13 | ||||
-rw-r--r-- | sql/share/errmsg.txt | 23 | ||||
-rw-r--r-- | sql/sp.cc | 4 | ||||
-rw-r--r-- | sql/sql_cache.cc | 47 | ||||
-rw-r--r-- | sql/sql_class.cc | 4 | ||||
-rw-r--r-- | sql/sql_class.h | 2 | ||||
-rw-r--r-- | sql/sql_lex.cc | 1 | ||||
-rw-r--r-- | sql/sql_lex.h | 9 | ||||
-rw-r--r-- | sql/sql_parse.cc | 21 | ||||
-rw-r--r-- | sql/sql_show.cc | 13 | ||||
-rw-r--r-- | sql/sql_table.cc | 9 | ||||
-rw-r--r-- | sql/sql_yacc.yy | 17 | ||||
-rw-r--r-- | sql/unireg.cc | 17 |
19 files changed, 234 insertions, 61 deletions
diff --git a/sql/item_func.cc b/sql/item_func.cc index ec95254baaa..4322fa058a7 100644 --- a/sql/item_func.cc +++ b/sql/item_func.cc @@ -4837,7 +4837,9 @@ bool Item_func_get_system_var::is_written_to_binlog() void Item_func_get_system_var::fix_length_and_dec() { + char *cptr; maybe_null=0; + max_length= 0; if (var->check_type(var_type)) { @@ -4867,8 +4869,14 @@ void Item_func_get_system_var::fix_length_and_dec() break; case SHOW_CHAR: case SHOW_CHAR_PTR: + pthread_mutex_lock(&LOCK_global_system_variables); + cptr= var->show_type() == SHOW_CHAR_PTR ? + *(char**) var->value_ptr(current_thd, var_type, &component) : + (char*) var->value_ptr(current_thd, var_type, &component); + if (cptr) + max_length= strlen(cptr) * system_charset_info->mbmaxlen; + pthread_mutex_unlock(&LOCK_global_system_variables); collation.set(system_charset_info, DERIVATION_SYSCONST); - max_length= MAX_BLOB_WIDTH; decimals=NOT_FIXED_DEC; break; case SHOW_BOOL: diff --git a/sql/log.cc b/sql/log.cc index 74dc75702ae..44296daa939 100644 --- a/sql/log.cc +++ b/sql/log.cc @@ -4650,10 +4650,14 @@ bool flush_error_log() uchar buf[IO_SIZE]; freopen(err_temp,"a+",stderr); + setbuf(stderr, NULL); (void) my_delete(err_renamed, MYF(0)); my_rename(log_error_file,err_renamed,MYF(0)); if (freopen(log_error_file,"a+",stdout)) + { freopen(log_error_file,"a+",stderr); + setbuf(stderr, NULL); + } if ((fd = my_open(err_temp, O_RDONLY, MYF(0))) >= 0) { @@ -4669,7 +4673,10 @@ bool flush_error_log() #else my_rename(log_error_file,err_renamed,MYF(0)); if (freopen(log_error_file,"a+",stdout)) + { freopen(log_error_file,"a+",stderr); + setbuf(stderr, NULL); + } else result= 1; #endif diff --git a/sql/mysqld.cc b/sql/mysqld.cc index bd1afc7f0ca..1391b87e8e3 100644 --- a/sql/mysqld.cc +++ b/sql/mysqld.cc @@ -3703,7 +3703,10 @@ static int init_server_components() #ifndef EMBEDDED_LIBRARY if (freopen(log_error_file, "a+", stdout)) #endif + { freopen(log_error_file, "a+", stderr); + setbuf(stderr, NULL); + } } } @@ -4331,6 +4334,7 @@ we force server id to 2, but this MySQL server will not act as a slave."); { freopen(log_error_file,"a+",stdout); freopen(log_error_file,"a+",stderr); + setbuf(stderr, NULL); FreeConsole(); // Remove window } #endif diff --git a/sql/opt_range.cc b/sql/opt_range.cc index 9f8f17eb4ba..31cb829fd93 100644 --- a/sql/opt_range.cc +++ b/sql/opt_range.cc @@ -9239,32 +9239,37 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) */ KEY *cur_index_info= table->key_info; KEY *cur_index_info_end= cur_index_info + table->s->keys; - KEY_PART_INFO *cur_part= NULL; - KEY_PART_INFO *end_part; /* Last part for loops. */ - /* Last index part. */ - KEY_PART_INFO *last_part= NULL; - KEY_PART_INFO *first_non_group_part= NULL; - KEY_PART_INFO *first_non_infix_part= NULL; - uint key_infix_parts= 0; - uint cur_group_key_parts= 0; - uint cur_group_prefix_len= 0; /* Cost-related variables for the best index so far. */ double best_read_cost= DBL_MAX; ha_rows best_records= 0; SEL_ARG *best_index_tree= NULL; ha_rows best_quick_prefix_records= 0; uint best_param_idx= 0; - double cur_read_cost= DBL_MAX; - ha_rows cur_records; + + const uint pk= param->table->s->primary_key; SEL_ARG *cur_index_tree= NULL; ha_rows cur_quick_prefix_records= 0; uint cur_param_idx=MAX_KEY; - key_map cur_used_key_parts; - uint pk= param->table->s->primary_key; for (uint cur_index= 0 ; cur_index_info != cur_index_info_end ; cur_index_info++, cur_index++) { + KEY_PART_INFO *cur_part; + KEY_PART_INFO *end_part; /* Last part for loops. */ + /* Last index part. */ + KEY_PART_INFO *last_part; + KEY_PART_INFO *first_non_group_part; + KEY_PART_INFO *first_non_infix_part; + uint key_infix_parts; + uint cur_group_key_parts= 0; + uint cur_group_prefix_len= 0; + double cur_read_cost; + ha_rows cur_records; + key_map used_key_parts_map; + uint cur_key_infix_len= 0; + uchar cur_key_infix[MAX_KEY_LENGTH]; + uint cur_used_key_parts; + /* Check (B1) - if current index is covering. */ if (!table->covering_keys.is_set(cur_index)) goto next_index; @@ -9334,7 +9339,7 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) else if (join->select_distinct) { select_items_it.rewind(); - cur_used_key_parts.clear_all(); + used_key_parts_map.clear_all(); uint max_key_part= 0; while ((item= select_items_it++)) { @@ -9345,13 +9350,13 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) Check if this attribute was already present in the select list. If it was present, then its corresponding key part was alredy used. */ - if (cur_used_key_parts.is_set(key_part_nr)) + if (used_key_parts_map.is_set(key_part_nr)) continue; if (key_part_nr < 1 || key_part_nr > join->fields_list.elements) goto next_index; cur_part= cur_index_info->key_part + key_part_nr - 1; cur_group_prefix_len+= cur_part->store_length; - cur_used_key_parts.set_bit(key_part_nr); + used_key_parts_map.set_bit(key_part_nr); ++cur_group_key_parts; max_key_part= max(max_key_part,key_part_nr); } @@ -9363,7 +9368,7 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) */ ulonglong all_parts, cur_parts; all_parts= (1<<max_key_part) - 1; - cur_parts= cur_used_key_parts.to_ulonglong() >> 1; + cur_parts= used_key_parts_map.to_ulonglong() >> 1; if (all_parts != cur_parts) goto next_index; } @@ -9413,7 +9418,8 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) &dummy); if (!get_constant_key_infix(cur_index_info, index_range_tree, first_non_group_part, min_max_arg_part, - last_part, thd, key_infix, &key_infix_len, + last_part, thd, cur_key_infix, + &cur_key_infix_len, &first_non_infix_part)) goto next_index; } @@ -9467,9 +9473,9 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) } /* If we got to this point, cur_index_info passes the test. */ - key_infix_parts= key_infix_len ? + key_infix_parts= cur_key_infix_len ? (first_non_infix_part - first_non_group_part) : 0; - used_key_parts= cur_group_key_parts + key_infix_parts; + cur_used_key_parts= cur_group_key_parts + key_infix_parts; /* Compute the cost of using this index. */ if (tree) @@ -9481,7 +9487,7 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) cur_quick_prefix_records= check_quick_select(param, cur_param_idx, cur_index_tree, TRUE); } - cost_group_min_max(table, cur_index_info, used_key_parts, + cost_group_min_max(table, cur_index_info, cur_used_key_parts, cur_group_key_parts, tree, cur_index_tree, cur_quick_prefix_records, have_min, have_max, &cur_read_cost, &cur_records); @@ -9492,7 +9498,6 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) */ if (cur_read_cost < best_read_cost - (DBL_EPSILON * cur_read_cost)) { - DBUG_ASSERT(tree != 0 || cur_param_idx == MAX_KEY); index_info= cur_index_info; index= cur_index; best_read_cost= cur_read_cost; @@ -9502,11 +9507,13 @@ get_best_group_min_max(PARAM *param, SEL_TREE *tree) best_param_idx= cur_param_idx; group_key_parts= cur_group_key_parts; group_prefix_len= cur_group_prefix_len; + key_infix_len= cur_key_infix_len; + if (key_infix_len) + memcpy (key_infix, cur_key_infix, sizeof (key_infix)); + used_key_parts= cur_used_key_parts; } - next_index: - cur_group_key_parts= 0; - cur_group_prefix_len= 0; + next_index:; } if (!index_info) /* No usable index found. */ DBUG_RETURN(NULL); diff --git a/sql/protocol.cc b/sql/protocol.cc index 6699196fbc7..16975c68a54 100644 --- a/sql/protocol.cc +++ b/sql/protocol.cc @@ -598,7 +598,8 @@ bool Protocol::send_fields(List<Item> *list, uint flags) field.length / item->collation.collation->mbminlen : field.length / item->collation.collation->mbmaxlen; max_length*= thd_charset->mbmaxlen; - field_length= (max_length > UINT_MAX32) ? UINT_MAX32 : max_length; + field_length= (max_length > UINT_MAX32) ? + UINT_MAX32 : (uint32) max_length; int4store(pos + 2, field_length); } pos[6]= field.type; diff --git a/sql/rpl_record.cc b/sql/rpl_record.cc index 7c74dcba5a0..14a80cbb4b6 100644 --- a/sql/rpl_record.cc +++ b/sql/rpl_record.cc @@ -297,21 +297,16 @@ unpack_row(Relay_log_info const *rli, /** Fills @c table->record[0] with default values. - First @c empty_record() is called and then, additionally, fields are - initialized explicitly with a call to @c set_default(). - - For optimization reasons, the explicit initialization can be skipped for - first @c skip fields. This is useful if later we are going to fill these - fields from other source (e.g. from a Rows replication event). - - If @c check is true, fields are explicitly initialized only if they have - default value or can be NULL. Otherwise error is reported. + First @c restore_record() is called to restore the default values for + record concerning the given table. Then, if @c check is true, + a check is performed to see if fields are have default value or can + be NULL. Otherwise error is reported. @param table Table whose record[0] buffer is prepared. - @param skip Number of columns for which default value initialization + @param skip Number of columns for which default/nullable check should be skipped. - @param check Indicates if errors should be checked when setting default - values. + @param check Indicates if errors should be raised when checking + default/nullable field properties. @returns 0 on success or a handler level error code */ @@ -321,25 +316,28 @@ int prepare_record(TABLE *const table, DBUG_ENTER("prepare_record"); int error= 0; - empty_record(table); + restore_record(table, s->default_values); - if (skip >= table->s->fields) // nothing to do + /* + This skip should be revisited in 6.0, because in 6.0 RBR one + can have holes in the row (as the grain of the writeset is + the column and not the entire row). + */ + if (skip >= table->s->fields || !check) DBUG_RETURN(0); - /* Explicit initialization of fields */ + /* Checking if exists default/nullable fields in the default values. */ for (Field **field_ptr= table->field+skip ; *field_ptr ; ++field_ptr) { uint32 const mask= NOT_NULL_FLAG | NO_DEFAULT_VALUE_FLAG; Field *const f= *field_ptr; - if (check && ((f->flags & mask) == mask)) + if (((f->flags & mask) == mask)) { my_error(ER_NO_DEFAULT_FOR_FIELD, MYF(0), f->field_name); error = HA_ERR_ROWS_EVENT_APPLY; } - else - f->set_default(); } DBUG_RETURN(error); diff --git a/sql/set_var.cc b/sql/set_var.cc index 6c2ac2e32a9..d6a9cbb19ee 100644 --- a/sql/set_var.cc +++ b/sql/set_var.cc @@ -110,6 +110,7 @@ static void sys_default_init_connect(THD*, enum_var_type type); static bool sys_update_init_slave(THD*, set_var*); static void sys_default_init_slave(THD*, enum_var_type type); static bool set_option_bit(THD *thd, set_var *var); +static bool set_option_log_bin_bit(THD *thd, set_var *var); static bool set_option_autocommit(THD *thd, set_var *var); static int check_log_update(THD *thd, set_var *var); static bool set_log_update(THD *thd, set_var *var); @@ -729,7 +730,7 @@ static sys_var_thd_bit sys_log_update(&vars, "sql_log_update", OPTION_BIN_LOG); static sys_var_thd_bit sys_log_binlog(&vars, "sql_log_bin", check_log_update, - set_option_bit, + set_option_log_bin_bit, OPTION_BIN_LOG); static sys_var_thd_bit sys_sql_warnings(&vars, "sql_warnings", 0, set_option_bit, @@ -3033,6 +3034,16 @@ static bool set_option_bit(THD *thd, set_var *var) return 0; } +/* + Functions to be only used to update thd->options OPTION_BIN_LOG bit +*/ +static bool set_option_log_bin_bit(THD *thd, set_var *var) +{ + set_option_bit(thd, var); + if (!thd->in_sub_stmt) + thd->sql_log_bin_toplevel= thd->options & OPTION_BIN_LOG; + return 0; +} static bool set_option_autocommit(THD *thd, set_var *var) { diff --git a/sql/share/errmsg.txt b/sql/share/errmsg.txt index 5dc75c340ea..aa1521acab6 100644 --- a/sql/share/errmsg.txt +++ b/sql/share/errmsg.txt @@ -6154,3 +6154,26 @@ WARN_PLUGIN_BUSY ER_VARIABLE_IS_READONLY eng "%s variable '%s' is read-only. Use SET %s to assign the value" + +ER_WARN_ENGINE_TRANSACTION_ROLLBACK + eng "Storage engine %s does not support rollback for this statement. Transaction rolled back and must be restarted" + +ER_SLAVE_HEARTBEAT_FAILURE + eng "Unexpected master's heartbeat data: %s" +ER_SLAVE_HEARTBEAT_VALUE_OUT_OF_RANGE + eng "The requested value for the heartbeat period %s %s" + +ER_NDB_REPLICATION_SCHEMA_ERROR + eng "Bad schema for mysql.ndb_replication table. Message: %-.64s" +ER_CONFLICT_FN_PARSE_ERROR + eng "Error in parsing conflict function. Message: %-.64s" +ER_EXCEPTIONS_WRITE_ERROR + eng "Write to exceptions table failed. Message: %-.128s"" + +ER_TOO_LONG_TABLE_COMMENT + eng "Comment for table '%-.64s' is too long (max = %lu)" + por "Comentário para a tabela '%-.64s' é longo demais (max = %lu)" + +ER_TOO_LONG_FIELD_COMMENT + eng "Comment for field '%-.64s' is too long (max = %lu)" + por "Comentário para o campo '%-.64s' é longo demais (max = %lu)" diff --git a/sql/sp.cc b/sql/sp.cc index cc545992857..b2c7c389136 100644 --- a/sql/sp.cc +++ b/sql/sp.cc @@ -936,10 +936,12 @@ sp_create_routine(THD *thd, int type, sp_head *sp) ret= SP_INTERNAL_ERROR; goto done; } - + /* restore sql_mode when binloging */ + thd->variables.sql_mode= saved_mode; /* Such a statement can always go directly to binlog, no trans cache */ thd->binlog_query(THD::MYSQL_QUERY_TYPE, log_query.c_ptr(), log_query.length(), FALSE, FALSE); + thd->variables.sql_mode= 0; } } diff --git a/sql/sql_cache.cc b/sql/sql_cache.cc index 4a5b75c4f78..25907d4ec20 100644 --- a/sql/sql_cache.cc +++ b/sql/sql_cache.cc @@ -418,6 +418,43 @@ TYPELIB query_cache_type_typelib= array_elements(query_cache_type_names)-1,"", query_cache_type_names, NULL }; + +/** + Helper function for determine if a SELECT statement has a SQL_NO_CACHE + directive. + + @param sql A pointer to the first white space character after SELECT + + @return + @retval TRUE The character string contains SQL_NO_CACHE + @retval FALSE No directive found. +*/ + +static bool has_no_cache_directive(char *sql) +{ + int i=0; + while (sql[i] == ' ') + ++i; + + if (my_toupper(system_charset_info, sql[i]) == 'S' && + my_toupper(system_charset_info, sql[i+1]) == 'Q' && + my_toupper(system_charset_info, sql[i+2]) == 'L' && + my_toupper(system_charset_info, sql[i+3]) == '_' && + my_toupper(system_charset_info, sql[i+4]) == 'N' && + my_toupper(system_charset_info, sql[i+5]) == 'O' && + my_toupper(system_charset_info, sql[i+6]) == '_' && + my_toupper(system_charset_info, sql[i+7]) == 'C' && + my_toupper(system_charset_info, sql[i+8]) == 'A' && + my_toupper(system_charset_info, sql[i+9]) == 'C' && + my_toupper(system_charset_info, sql[i+10]) == 'H' && + my_toupper(system_charset_info, sql[i+11]) == 'E' && + my_toupper(system_charset_info, sql[i+12]) == ' ') + return TRUE; + + return FALSE; +} + + /***************************************************************************** Query_cache_block_table method(s) *****************************************************************************/ @@ -1233,6 +1270,16 @@ Query_cache::send_result_to_client(THD *thd, char *sql, uint query_length) DBUG_PRINT("qcache", ("The statement is not a SELECT; Not cached")); goto err; } + + if (query_length > 20 && has_no_cache_directive(&sql[i+6])) + { + /* + We do not increase 'refused' statistics here since it will be done + later when the query is parsed. + */ + DBUG_PRINT("qcache", ("The statement has a SQL_NO_CACHE directive")); + goto err; + } } STRUCT_LOCK(&structure_guard_mutex); diff --git a/sql/sql_class.cc b/sql/sql_class.cc index 597478933d6..cd00d0e20f1 100644 --- a/sql/sql_class.cc +++ b/sql/sql_class.cc @@ -538,6 +538,7 @@ THD::THD() Open_tables_state(refresh_version), rli_fake(0), lock_id(&main_lock_id), user_time(0), in_sub_stmt(0), + sql_log_bin_toplevel(false), binlog_table_maps(0), binlog_flags(0UL), table_map_for_update(0), arg_of_last_insert_id_function(FALSE), @@ -787,6 +788,7 @@ void THD::init(void) update_charset(); reset_current_stmt_binlog_row_based(); bzero((char *) &status_var, sizeof(status_var)); + sql_log_bin_toplevel= options & OPTION_BIN_LOG; } @@ -3662,7 +3664,7 @@ int THD::binlog_query(THD::enum_binlog_query_type qtype, char const *query_arg, If we are in statement mode and trying to log an unsafe statement, we should print a warning. */ - if (lex->is_stmt_unsafe() && + if (sql_log_bin_toplevel && lex->is_stmt_unsafe() && variables.binlog_format == BINLOG_FORMAT_STMT) { push_warning(this, MYSQL_ERROR::WARN_LEVEL_WARN, diff --git a/sql/sql_class.h b/sql/sql_class.h index 3439e5b4f74..0a33d2767f5 100644 --- a/sql/sql_class.h +++ b/sql/sql_class.h @@ -1350,6 +1350,8 @@ public: /* <> 0 if we are inside of trigger or stored function. */ uint in_sub_stmt; + /* TRUE when the current top has SQL_LOG_BIN ON */ + bool sql_log_bin_toplevel; /* container for handler's private per-connection data */ Ha_data ha_data[MAX_HA]; diff --git a/sql/sql_lex.cc b/sql/sql_lex.cc index 9619d26893c..19a19f2b6fb 100644 --- a/sql/sql_lex.cc +++ b/sql/sql_lex.cc @@ -1559,6 +1559,7 @@ void st_select_lex::init_query() exclude_from_table_unique_test= no_wrap_view_item= FALSE; nest_level= 0; link_next= 0; + lock_option= TL_READ_DEFAULT; } void st_select_lex::init_select() diff --git a/sql/sql_lex.h b/sql/sql_lex.h index ed6b9e7d8df..a48b99d07c7 100644 --- a/sql/sql_lex.h +++ b/sql/sql_lex.h @@ -688,6 +688,15 @@ public: int cur_pos_in_select_list; List<udf_func> udf_list; /* udf function calls stack */ + + /** + Per sub-query locking strategy. + Note: This variable might interfer with the corresponding statement-level + variable Lex::lock_option because on how different parser rules depend + on eachother. + */ + thr_lock_type lock_option; + /* This is a copy of the original JOIN USING list that comes from the parser. The parser : diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc index f7d6d5bac4d..f7e895d150f 100644 --- a/sql/sql_parse.cc +++ b/sql/sql_parse.cc @@ -5580,6 +5580,14 @@ void mysql_reset_thd_for_next_command(THD *thd) } +/** + Resets the lex->current_select object. + @note It is assumed that lex->current_select != NULL + + This function is a wrapper around select_lex->init_select() with an added + check for the special situation when using INTO OUTFILE and LOAD DATA. +*/ + void mysql_init_select(LEX *lex) { @@ -5594,6 +5602,18 @@ mysql_init_select(LEX *lex) } +/** + Used to allocate a new SELECT_LEX object on the current thd mem_root and + link it into the relevant lists. + + This function is always followed by mysql_init_select. + + @see mysql_init_select + + @retval TRUE An error occurred + @retval FALSE The new SELECT_LEX was successfully allocated. +*/ + bool mysql_new_select(LEX *lex, bool move_down) { @@ -6411,7 +6431,6 @@ void st_select_lex::set_lock_for_tables(thr_lock_type lock_type) DBUG_ENTER("set_lock_for_tables"); DBUG_PRINT("enter", ("lock_type: %d for_update: %d", lock_type, for_update)); - for (TABLE_LIST *tables= (TABLE_LIST*) table_list.first; tables; tables= tables->next_local) diff --git a/sql/sql_show.cc b/sql/sql_show.cc index 942b131b301..3d702833620 100644 --- a/sql/sql_show.cc +++ b/sql/sql_show.cc @@ -3796,8 +3796,19 @@ static int get_schema_column_record(THD *thd, TABLE_LIST *tables, cs); table->field[4]->store((longlong) count, TRUE); field->sql_type(type); - table->field[14]->store(type.ptr(), type.length(), cs); + table->field[14]->store(type.ptr(), type.length(), cs); + /* + MySQL column type has the following format: + base_type [(dimension)] [unsigned] [zerofill]. + For DATA_TYPE column we extract only base type. + */ tmp_buff= strchr(type.ptr(), '('); + if (!tmp_buff) + /* + if there is no dimention part then check the presence of + [unsigned] [zerofill] attributes and cut them of if exist. + */ + tmp_buff= strchr(type.ptr(), ' '); table->field[7]->store(type.ptr(), (tmp_buff ? tmp_buff - type.ptr() : type.length()), cs); diff --git a/sql/sql_table.cc b/sql/sql_table.cc index 12e9357f533..60714348d03 100644 --- a/sql/sql_table.cc +++ b/sql/sql_table.cc @@ -4297,7 +4297,14 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables, view_checksum(thd, table) == HA_ADMIN_WRONG_CHECKSUM) push_warning(thd, MYSQL_ERROR::WARN_LEVEL_ERROR, ER_VIEW_CHECKSUM, ER(ER_VIEW_CHECKSUM)); - result_code= HA_ADMIN_CORRUPT; + if (thd->main_da.is_error() && + (thd->main_da.sql_errno() == ER_NO_SUCH_TABLE || + thd->main_da.sql_errno() == ER_FILE_NOT_FOUND)) + /* A missing table is just issued as a failed command */ + result_code= HA_ADMIN_FAILED; + else + /* Default failure code is corrupt table */ + result_code= HA_ADMIN_CORRUPT; goto send_result; } diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 371a146696d..e56ff7c6ad7 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -6489,7 +6489,8 @@ select_option: { if (check_simple_select()) MYSQL_YYABORT; - Lex->lock_option= TL_READ_HIGH_PRIORITY; + Lex->lock_option= TL_READ_HIGH_PRIORITY; + Lex->current_select->lock_option= TL_READ_HIGH_PRIORITY; } | DISTINCT { Select->options|= SELECT_DISTINCT; } | SQL_SMALL_RESULT { Select->options|= SELECT_SMALL_RESULT; } @@ -6535,6 +6536,7 @@ select_lock_type: { LEX *lex=Lex; lex->current_select->set_lock_for_tables(TL_WRITE); + lex->current_select->lock_option= TL_WRITE; lex->safe_to_cache_query=0; } | LOCK_SYM IN_SYM SHARE_SYM MODE_SYM @@ -6542,6 +6544,7 @@ select_lock_type: LEX *lex=Lex; lex->current_select-> set_lock_for_tables(TL_READ_WITH_SHARED_LOCKS); + lex->current_select->lock_option= TL_READ_WITH_SHARED_LOCKS; lex->safe_to_cache_query=0; } ; @@ -12909,6 +12912,18 @@ subselect_start: subselect_end: { LEX *lex=Lex; + /* + Set the required lock level for the tables associated with the + current sub-select. This will overwrite previous lock options set + using st_select_lex::add_table_to_list in any of the following + rules: single_multi, table_wild_one, load_data, table_alias_ref, + table_factor. + The default lock level is TL_READ_DEFAULT but it can be modified + with query options specific for a certain (sub-)SELECT. + */ + lex->current_select-> + set_lock_for_tables(lex->current_select->lock_option); + lex->pop_context(); SELECT_LEX *child= lex->current_select; lex->current_select = lex->current_select->return_after_parsing(); diff --git a/sql/unireg.cc b/sql/unireg.cc index da018ebec3d..51293184ad8 100644 --- a/sql/unireg.cc +++ b/sql/unireg.cc @@ -229,16 +229,16 @@ bool mysql_create_frm(THD *thd, const char *file_name, create_info->comment.length, 60); if (tmp_len < create_info->comment.length) { - (void) my_snprintf(buff, sizeof(buff), "Too long comment for table '%s'", - table); if ((thd->variables.sql_mode & (MODE_STRICT_TRANS_TABLES | MODE_STRICT_ALL_TABLES))) { - my_message(ER_UNKNOWN_ERROR, buff, MYF(0)); + my_error(ER_TOO_LONG_TABLE_COMMENT, MYF(0), table, tmp_len); goto err; } push_warning_printf(current_thd, MYSQL_ERROR::WARN_LEVEL_WARN, - ER_UNKNOWN_ERROR, ER(ER_UNKNOWN_ERROR), buff); + ER_TOO_LONG_TABLE_COMMENT, + ER(ER_TOO_LONG_TABLE_COMMENT), + table, tmp_len); create_info->comment.length= tmp_len; } @@ -613,17 +613,16 @@ static bool pack_header(uchar *forminfo, enum legacy_db_type table_type, 255); if (tmp_len < field->comment.length) { - char buff[128]; - (void) my_snprintf(buff,sizeof(buff), "Too long comment for field '%s'", - field->field_name); if ((current_thd->variables.sql_mode & (MODE_STRICT_TRANS_TABLES | MODE_STRICT_ALL_TABLES))) { - my_message(ER_UNKNOWN_ERROR, buff, MYF(0)); + my_error(ER_TOO_LONG_FIELD_COMMENT, MYF(0), field->field_name, tmp_len); DBUG_RETURN(1); } push_warning_printf(current_thd, MYSQL_ERROR::WARN_LEVEL_WARN, - ER_UNKNOWN_ERROR, ER(ER_UNKNOWN_ERROR), buff); + ER_TOO_LONG_FIELD_COMMENT, + ER(ER_TOO_LONG_FIELD_COMMENT), + field->field_name, tmp_len); field->comment.length= tmp_len; } |