summaryrefslogtreecommitdiff
path: root/sql
diff options
context:
space:
mode:
authorMattias Jonsson <mattiasj@mysql.com>2008-08-11 20:06:08 +0200
committerMattias Jonsson <mattiasj@mysql.com>2008-08-11 20:06:08 +0200
commit1c06de1fd6696c69185ab25f00bdf5f20e298f78 (patch)
treeca19bdadefe661b11ba81a5f4b4905e2f09744b5 /sql
parent2ace7dc939ea28b5ee7bc526f5fa49142cb2de54 (diff)
parentf50c4207f22e2c7483965ef83104839e9d7b4887 (diff)
downloadmariadb-git-1c06de1fd6696c69185ab25f00bdf5f20e298f78.tar.gz
manual merge of Bug#20129 into 5.1-bugteam
Diffstat (limited to 'sql')
-rw-r--r--sql/ha_partition.cc232
-rw-r--r--sql/ha_partition.h4
-rw-r--r--sql/handler.cc60
-rw-r--r--sql/handler.h12
-rw-r--r--sql/mysql_priv.h2
-rw-r--r--sql/protocol.cc3
-rw-r--r--sql/sql_partition.cc96
-rw-r--r--sql/sql_table.cc55
-rw-r--r--sql/sql_yacc.yy8
9 files changed, 220 insertions, 252 deletions
diff --git a/sql/ha_partition.cc b/sql/ha_partition.cc
index 6a9c283622d..c7711ca37b8 100644
--- a/sql/ha_partition.cc
+++ b/sql/ha_partition.cc
@@ -841,6 +841,9 @@ int ha_partition::rename_partitions(const char *path)
#define CHECK_PARTS 3
#define REPAIR_PARTS 4
+static const char *opt_op_name[]= {NULL,
+ "optimize", "analyze", "check", "repair" };
+
/*
Optimize table
@@ -858,8 +861,10 @@ int ha_partition::optimize(THD *thd, HA_CHECK_OPT *check_opt)
{
DBUG_ENTER("ha_partition::optimize");
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- OPTIMIZE_PARTS, TRUE));
+ DBUG_RETURN(handle_opt_partitions(thd, check_opt,
+ OPTIMIZE_PARTS,
+ thd->lex->alter_info.flags &
+ ALTER_OPTIMIZE_PARTITION ? FALSE : TRUE));
}
@@ -880,8 +885,10 @@ int ha_partition::analyze(THD *thd, HA_CHECK_OPT *check_opt)
{
DBUG_ENTER("ha_partition::analyze");
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- ANALYZE_PARTS, TRUE));
+ DBUG_RETURN(handle_opt_partitions(thd, check_opt,
+ ANALYZE_PARTS,
+ thd->lex->alter_info.flags &
+ ALTER_ANALYZE_PARTITION ? FALSE : TRUE));
}
@@ -902,8 +909,10 @@ int ha_partition::check(THD *thd, HA_CHECK_OPT *check_opt)
{
DBUG_ENTER("ha_partition::check");
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- CHECK_PARTS, TRUE));
+ DBUG_RETURN(handle_opt_partitions(thd, check_opt,
+ CHECK_PARTS,
+ thd->lex->alter_info.flags &
+ ALTER_CHECK_PARTITION ? FALSE : TRUE));
}
@@ -924,96 +933,13 @@ int ha_partition::repair(THD *thd, HA_CHECK_OPT *check_opt)
{
DBUG_ENTER("ha_partition::repair");
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- REPAIR_PARTS, TRUE));
-}
-
-/*
- Optimize partitions
-
- SYNOPSIS
- optimize_partitions()
- thd Thread object
- RETURN VALUE
- >0 Failure
- 0 Success
- DESCRIPTION
- Call optimize on each partition marked with partition state PART_CHANGED
-*/
-
-int ha_partition::optimize_partitions(THD *thd)
-{
- DBUG_ENTER("ha_partition::optimize_partitions");
-
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- OPTIMIZE_PARTS, FALSE));
+ DBUG_RETURN(handle_opt_partitions(thd, check_opt,
+ REPAIR_PARTS,
+ thd->lex->alter_info.flags &
+ ALTER_REPAIR_PARTITION ? FALSE : TRUE));
}
/*
- Analyze partitions
-
- SYNOPSIS
- analyze_partitions()
- thd Thread object
- RETURN VALUE
- >0 Failure
- 0 Success
- DESCRIPTION
- Call analyze on each partition marked with partition state PART_CHANGED
-*/
-
-int ha_partition::analyze_partitions(THD *thd)
-{
- DBUG_ENTER("ha_partition::analyze_partitions");
-
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- ANALYZE_PARTS, FALSE));
-}
-
-/*
- Check partitions
-
- SYNOPSIS
- check_partitions()
- thd Thread object
- RETURN VALUE
- >0 Failure
- 0 Success
- DESCRIPTION
- Call check on each partition marked with partition state PART_CHANGED
-*/
-
-int ha_partition::check_partitions(THD *thd)
-{
- DBUG_ENTER("ha_partition::check_partitions");
-
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- CHECK_PARTS, FALSE));
-}
-
-/*
- Repair partitions
-
- SYNOPSIS
- repair_partitions()
- thd Thread object
- RETURN VALUE
- >0 Failure
- 0 Success
- DESCRIPTION
- Call repair on each partition marked with partition state PART_CHANGED
-*/
-
-int ha_partition::repair_partitions(THD *thd)
-{
- DBUG_ENTER("ha_partition::repair_partitions");
-
- DBUG_RETURN(handle_opt_partitions(thd, &thd->lex->check_opt,
- REPAIR_PARTS, FALSE));
-}
-
-
-/*
Handle optimize/analyze/check/repair of one partition
SYNOPSIS
@@ -1028,7 +954,6 @@ int ha_partition::repair_partitions(THD *thd)
0 Success
*/
-#ifdef WL4176_IS_DONE
static int handle_opt_part(THD *thd, HA_CHECK_OPT *check_opt,
handler *file, uint flag)
{
@@ -1036,12 +961,6 @@ static int handle_opt_part(THD *thd, HA_CHECK_OPT *check_opt,
DBUG_ENTER("handle_opt_part");
DBUG_PRINT("enter", ("flag = %u", flag));
- /*
- TODO:
- Rewrite the code for ANALYZE/CHECK/OPTIMIZE/REPAIR PARTITION WL4176
- */
- DBUG_RETURN(HA_ADMIN_NOT_IMPLEMENTED);
-
if (flag == OPTIMIZE_PARTS)
error= file->ha_optimize(thd, check_opt);
else if (flag == ANALYZE_PARTS)
@@ -1059,7 +978,59 @@ static int handle_opt_part(THD *thd, HA_CHECK_OPT *check_opt,
error= 0;
DBUG_RETURN(error);
}
-#endif
+
+
+/*
+ print a message row formatted for ANALYZE/CHECK/OPTIMIZE/REPAIR TABLE
+ (modelled after mi_check_print_msg)
+ TODO: move this into the handler, or rewrite mysql_admin_table.
+*/
+static bool print_admin_msg(THD* thd, const char* msg_type,
+ const char* db_name, const char* table_name,
+ const char* op_name, const char *fmt, ...)
+{
+ va_list args;
+ Protocol *protocol= thd->protocol;
+ uint length, msg_length;
+ char msgbuf[MI_MAX_MSG_BUF];
+ char name[NAME_LEN*2+2];
+
+ va_start(args, fmt);
+ msg_length= my_vsnprintf(msgbuf, sizeof(msgbuf), fmt, args);
+ va_end(args);
+ msgbuf[sizeof(msgbuf) - 1] = 0; // healthy paranoia
+
+
+ if (!thd->vio_ok())
+ {
+ sql_print_error(msgbuf);
+ return TRUE;
+ }
+
+ length=(uint) (strxmov(name, db_name, ".", table_name,NullS) - name);
+ /*
+ TODO: switch from protocol to push_warning here. The main reason we didn't
+ it yet is parallel repair. Due to following trace:
+ mi_check_print_msg/push_warning/sql_alloc/my_pthread_getspecific_ptr.
+
+ Also we likely need to lock mutex here (in both cases with protocol and
+ push_warning).
+ */
+ DBUG_PRINT("info",("print_admin_msg: %s, %s, %s, %s", name, op_name,
+ msg_type, msgbuf));
+ protocol->prepare_for_resend();
+ protocol->store(name, length, system_charset_info);
+ protocol->store(op_name, system_charset_info);
+ protocol->store(msg_type, system_charset_info);
+ protocol->store(msgbuf, msg_length, system_charset_info);
+ if (protocol->write())
+ {
+ sql_print_error("Failed on my_net_write, writing to stderr instead: %s\n",
+ msgbuf);
+ return TRUE;
+ }
+ return FALSE;
+}
/*
@@ -1080,53 +1051,86 @@ static int handle_opt_part(THD *thd, HA_CHECK_OPT *check_opt,
int ha_partition::handle_opt_partitions(THD *thd, HA_CHECK_OPT *check_opt,
uint flag, bool all_parts)
{
-#ifdef WL4176_IS_DONE
List_iterator<partition_element> part_it(m_part_info->partitions);
uint no_parts= m_part_info->no_parts;
uint no_subparts= m_part_info->no_subparts;
uint i= 0;
int error;
-#endif
DBUG_ENTER("ha_partition::handle_opt_partitions");
DBUG_PRINT("enter", ("all_parts %u, flag= %u", all_parts, flag));
- /*
- TODO:
- Rewrite the code for ANALYZE/CHECK/OPTIMIZE/REPAIR PARTITION WL4176
- */
- DBUG_RETURN(HA_ADMIN_NOT_IMPLEMENTED);
-#ifdef WL4176_IS_DONE
do
{
partition_element *part_elem= part_it++;
- if (all_parts || part_elem->part_state == PART_CHANGED)
+ /*
+ when ALTER TABLE <CMD> PARTITION ...
+ it should only do named partitions, otherwise all partitions
+ */
+ if (all_parts ||
+ part_elem->part_state == PART_CHANGED)
{
if (m_is_sub_partitioned)
{
+ List_iterator<partition_element> subpart_it(part_elem->subpartitions);
+ partition_element *sub_elem;
uint j= 0, part;
do
{
+ sub_elem= subpart_it++;
part= i * no_subparts + j;
- DBUG_PRINT("info", ("Optimize subpartition %u",
- part));
+ DBUG_PRINT("info", ("Optimize subpartition %u (%s)",
+ part, sub_elem->partition_name));
+#ifdef NOT_USED
+ if (print_admin_msg(thd, "note", table_share->db.str, table->alias,
+ opt_op_name[flag],
+ "Start to operate on subpartition %s",
+ sub_elem->partition_name))
+ DBUG_RETURN(HA_ADMIN_INTERNAL_ERROR);
+#endif
if ((error= handle_opt_part(thd, check_opt, m_file[part], flag)))
{
+ /* print a line which partition the error belongs to */
+ if (error != HA_ADMIN_NOT_IMPLEMENTED &&
+ error != HA_ADMIN_ALREADY_DONE &&
+ error != HA_ADMIN_TRY_ALTER)
+ {
+ print_admin_msg(thd, "error", table_share->db.str, table->alias,
+ opt_op_name[flag],
+ "Subpartition %s returned error",
+ sub_elem->partition_name);
+ }
DBUG_RETURN(error);
}
} while (++j < no_subparts);
}
else
{
- DBUG_PRINT("info", ("Optimize partition %u", i));
+ DBUG_PRINT("info", ("Optimize partition %u (%s)", i,
+ part_elem->partition_name));
+#ifdef NOT_USED
+ if (print_admin_msg(thd, "note", table_share->db.str, table->alias,
+ opt_op_name[flag],
+ "Start to operate on partition %s",
+ part_elem->partition_name))
+ DBUG_RETURN(HA_ADMIN_INTERNAL_ERROR);
+#endif
if ((error= handle_opt_part(thd, check_opt, m_file[i], flag)))
{
+ /* print a line which partition the error belongs to */
+ if (error != HA_ADMIN_NOT_IMPLEMENTED &&
+ error != HA_ADMIN_ALREADY_DONE &&
+ error != HA_ADMIN_TRY_ALTER)
+ {
+ print_admin_msg(thd, "error", table_share->db.str, table->alias,
+ opt_op_name[flag], "Partition %s returned error",
+ part_elem->partition_name);
+ }
DBUG_RETURN(error);
}
}
}
} while (++i < no_parts);
DBUG_RETURN(FALSE);
-#endif
}
diff --git a/sql/ha_partition.h b/sql/ha_partition.h
index 790f6c5dd08..97f5624608f 100644
--- a/sql/ha_partition.h
+++ b/sql/ha_partition.h
@@ -932,10 +932,6 @@ public:
virtual int analyze(THD* thd, HA_CHECK_OPT *check_opt);
virtual int check(THD* thd, HA_CHECK_OPT *check_opt);
virtual int repair(THD* thd, HA_CHECK_OPT *check_opt);
- virtual int optimize_partitions(THD *thd);
- virtual int analyze_partitions(THD *thd);
- virtual int check_partitions(THD *thd);
- virtual int repair_partitions(THD *thd);
virtual bool check_and_repair(THD *thd);
virtual bool auto_repair() const;
virtual bool is_crashed() const;
diff --git a/sql/handler.cc b/sql/handler.cc
index fe4944ed836..e550295ebba 100644
--- a/sql/handler.cc
+++ b/sql/handler.cc
@@ -3285,66 +3285,6 @@ handler::ha_rename_partitions(const char *path)
/**
- Optimize partitions: public interface.
-
- @sa handler::optimize_partitions()
-*/
-
-int
-handler::ha_optimize_partitions(THD *thd)
-{
- mark_trx_read_write();
-
- return optimize_partitions(thd);
-}
-
-
-/**
- Analyze partitions: public interface.
-
- @sa handler::analyze_partitions()
-*/
-
-int
-handler::ha_analyze_partitions(THD *thd)
-{
- mark_trx_read_write();
-
- return analyze_partitions(thd);
-}
-
-
-/**
- Check partitions: public interface.
-
- @sa handler::check_partitions()
-*/
-
-int
-handler::ha_check_partitions(THD *thd)
-{
- mark_trx_read_write();
-
- return check_partitions(thd);
-}
-
-
-/**
- Repair partitions: public interface.
-
- @sa handler::repair_partitions()
-*/
-
-int
-handler::ha_repair_partitions(THD *thd)
-{
- mark_trx_read_write();
-
- return repair_partitions(thd);
-}
-
-
-/**
Tell the storage engine that it is allowed to "disable transaction" in the
handler. It is a hint that ACID is not required - it is used in NDB for
ALTER TABLE, for example, when data are copied to temporary table.
diff --git a/sql/handler.h b/sql/handler.h
index d674c07a57d..df6157f80b4 100644
--- a/sql/handler.h
+++ b/sql/handler.h
@@ -1247,10 +1247,6 @@ public:
size_t pack_frm_len);
int ha_drop_partitions(const char *path);
int ha_rename_partitions(const char *path);
- int ha_optimize_partitions(THD *thd);
- int ha_analyze_partitions(THD *thd);
- int ha_check_partitions(THD *thd);
- int ha_repair_partitions(THD *thd);
void adjust_next_insert_id_after_explicit_value(ulonglong nr);
int update_auto_increment();
@@ -1911,14 +1907,6 @@ private:
{ return HA_ERR_WRONG_COMMAND; }
virtual int rename_partitions(const char *path)
{ return HA_ERR_WRONG_COMMAND; }
- virtual int optimize_partitions(THD *thd)
- { return HA_ERR_WRONG_COMMAND; }
- virtual int analyze_partitions(THD *thd)
- { return HA_ERR_WRONG_COMMAND; }
- virtual int check_partitions(THD *thd)
- { return HA_ERR_WRONG_COMMAND; }
- virtual int repair_partitions(THD *thd)
- { return HA_ERR_WRONG_COMMAND; }
};
diff --git a/sql/mysql_priv.h b/sql/mysql_priv.h
index f6ba5fc9739..e9deb479c5e 100644
--- a/sql/mysql_priv.h
+++ b/sql/mysql_priv.h
@@ -1571,6 +1571,8 @@ uint fast_alter_partition_table(THD *thd, TABLE *table,
char *db,
const char *table_name,
uint fast_alter_partition);
+uint set_part_state(Alter_info *alter_info, partition_info *tab_part_info,
+ enum partition_state part_state);
uint prep_alter_part_table(THD *thd, TABLE *table, Alter_info *alter_info,
HA_CREATE_INFO *create_info,
handlerton *old_db_type,
diff --git a/sql/protocol.cc b/sql/protocol.cc
index 5fe56724d08..4177cd0054d 100644
--- a/sql/protocol.cc
+++ b/sql/protocol.cc
@@ -788,6 +788,9 @@ bool Protocol_text::store(const char *from, size_t length,
{
CHARSET_INFO *tocs= this->thd->variables.character_set_results;
#ifndef DBUG_OFF
+ DBUG_PRINT("info", ("Protocol_text::store field %u (%u): %s", field_pos,
+ field_count, from));
+ DBUG_ASSERT(field_pos < field_count);
DBUG_ASSERT(field_types == 0 ||
field_types[field_pos] == MYSQL_TYPE_DECIMAL ||
field_types[field_pos] == MYSQL_TYPE_BIT ||
diff --git a/sql/sql_partition.cc b/sql/sql_partition.cc
index 121ee3c22b4..6419d336b9f 100644
--- a/sql/sql_partition.cc
+++ b/sql/sql_partition.cc
@@ -4080,6 +4080,38 @@ error:
/*
+ Sets which partitions to be used in the command
+*/
+uint set_part_state(Alter_info *alter_info, partition_info *tab_part_info,
+ enum partition_state part_state)
+{
+ uint part_count= 0;
+ uint no_parts_found= 0;
+ List_iterator<partition_element> part_it(tab_part_info->partitions);
+
+ do
+ {
+ partition_element *part_elem= part_it++;
+ if ((alter_info->flags & ALTER_ALL_PARTITION) ||
+ (is_name_in_list(part_elem->partition_name,
+ alter_info->partition_names)))
+ {
+ /*
+ Mark the partition.
+ I.e mark the partition as a partition to be "changed" by
+ analyzing/optimizing/rebuilding/checking/repairing
+ */
+ no_parts_found++;
+ part_elem->part_state= part_state;
+ DBUG_PRINT("info", ("Setting part_state to %u for partition %s",
+ part_state, part_elem->partition_name));
+ }
+ } while (++part_count < tab_part_info->no_parts);
+ return no_parts_found;
+}
+
+
+/*
Prepare for ALTER TABLE of partition structure
SYNOPSIS
@@ -4534,26 +4566,9 @@ that are reorganised.
(alter_info->flags & ALTER_REPAIR_PARTITION) ||
(alter_info->flags & ALTER_REBUILD_PARTITION))
{
+ uint no_parts_found;
uint no_parts_opt= alter_info->partition_names.elements;
- uint part_count= 0;
- uint no_parts_found= 0;
- List_iterator<partition_element> part_it(tab_part_info->partitions);
-
- do
- {
- partition_element *part_elem= part_it++;
- if ((alter_info->flags & ALTER_ALL_PARTITION) ||
- (is_name_in_list(part_elem->partition_name,
- alter_info->partition_names)))
- {
- /*
- Mark the partition as a partition to be "changed" by
- analyzing/optimizing/rebuilding/checking/repairing
- */
- no_parts_found++;
- part_elem->part_state= PART_CHANGED;
- }
- } while (++part_count < tab_part_info->no_parts);
+ no_parts_found= set_part_state(alter_info, tab_part_info, PART_CHANGED);
if (no_parts_found != no_parts_opt &&
(!(alter_info->flags & ALTER_ALL_PARTITION)))
{
@@ -6026,48 +6041,7 @@ uint fast_alter_partition_table(THD *thd, TABLE *table,
lpt->pack_frm_len= 0;
thd->work_part_info= part_info;
- if (alter_info->flags & ALTER_OPTIMIZE_PARTITION ||
- alter_info->flags & ALTER_ANALYZE_PARTITION ||
- alter_info->flags & ALTER_CHECK_PARTITION ||
- alter_info->flags & ALTER_REPAIR_PARTITION)
- {
- /*
- In this case the user has specified that he wants a set of partitions
- to be optimised and the partition engine can handle optimising
- partitions natively without requiring a full rebuild of the
- partitions.
-
- In this case it is enough to call optimise_partitions, there is no
- need to change frm files or anything else.
- */
- int error;
- written_bin_log= FALSE;
- if (((alter_info->flags & ALTER_OPTIMIZE_PARTITION) &&
- (error= table->file->ha_optimize_partitions(thd))) ||
- ((alter_info->flags & ALTER_ANALYZE_PARTITION) &&
- (error= table->file->ha_analyze_partitions(thd))) ||
- ((alter_info->flags & ALTER_CHECK_PARTITION) &&
- (error= table->file->ha_check_partitions(thd))) ||
- ((alter_info->flags & ALTER_REPAIR_PARTITION) &&
- (error= table->file->ha_repair_partitions(thd))))
- {
- if (error == HA_ADMIN_NOT_IMPLEMENTED) {
- if (alter_info->flags & ALTER_OPTIMIZE_PARTITION)
- my_error(ER_CHECK_NOT_IMPLEMENTED, MYF(0), "optimize partition");
- else if (alter_info->flags & ALTER_ANALYZE_PARTITION)
- my_error(ER_CHECK_NOT_IMPLEMENTED, MYF(0), "analyze partition");
- else if (alter_info->flags & ALTER_CHECK_PARTITION)
- my_error(ER_CHECK_NOT_IMPLEMENTED, MYF(0), "check partition");
- else if (alter_info->flags & ALTER_REPAIR_PARTITION)
- my_error(ER_CHECK_NOT_IMPLEMENTED, MYF(0), "repair partition");
- else
- table->file->print_error(error, MYF(0));
- } else
- table->file->print_error(error, MYF(0));
- goto err;
- }
- }
- else if (fast_alter_partition & HA_PARTITION_ONE_PHASE)
+ if (fast_alter_partition & HA_PARTITION_ONE_PHASE)
{
/*
In the case where the engine supports one phase online partition
diff --git a/sql/sql_table.cc b/sql/sql_table.cc
index 2b3b5ef67d9..226facffe7c 100644
--- a/sql/sql_table.cc
+++ b/sql/sql_table.cc
@@ -4194,6 +4194,46 @@ static bool mysql_admin_table(THD* thd, TABLE_LIST* tables,
table->next_global= save_next_global;
table->next_local= save_next_local;
thd->open_options&= ~extra_open_options;
+#ifdef WITH_PARTITION_STORAGE_ENGINE
+ if (table->table && table->table->part_info)
+ {
+ /*
+ Set up which partitions that should be processed
+ if ALTER TABLE t ANALYZE/CHECK/OPTIMIZE/REPAIR PARTITION ..
+ */
+ Alter_info *alter_info= &lex->alter_info;
+
+ if (alter_info->flags & ALTER_ANALYZE_PARTITION ||
+ alter_info->flags & ALTER_CHECK_PARTITION ||
+ alter_info->flags & ALTER_OPTIMIZE_PARTITION ||
+ alter_info->flags & ALTER_REPAIR_PARTITION)
+ {
+ uint no_parts_found;
+ uint no_parts_opt= alter_info->partition_names.elements;
+ no_parts_found= set_part_state(alter_info, table->table->part_info,
+ PART_CHANGED);
+ if (no_parts_found != no_parts_opt &&
+ (!(alter_info->flags & ALTER_ALL_PARTITION)))
+ {
+ char buff[FN_REFLEN + MYSQL_ERRMSG_SIZE];
+ uint length;
+ DBUG_PRINT("admin", ("sending non existent partition error"));
+ protocol->prepare_for_resend();
+ protocol->store(table_name, system_charset_info);
+ protocol->store(operator_name, system_charset_info);
+ protocol->store(STRING_WITH_LEN("error"), system_charset_info);
+ length= my_snprintf(buff, sizeof(buff),
+ ER(ER_DROP_PARTITION_NON_EXISTENT),
+ table_name);
+ protocol->store(buff, length, system_charset_info);
+ if(protocol->write())
+ goto err;
+ my_eof(thd);
+ goto err;
+ }
+ }
+ }
+#endif
}
DBUG_PRINT("admin", ("table: 0x%lx", (long) table->table));
@@ -4428,9 +4468,17 @@ send_result_message:
This is currently used only by InnoDB. ha_innobase::optimize() answers
"try with alter", so here we close the table, do an ALTER TABLE,
reopen the table and do ha_innobase::analyze() on it.
+ We have to end the row, so analyze could return more rows.
*/
+ protocol->store(STRING_WITH_LEN("note"), system_charset_info);
+ protocol->store(STRING_WITH_LEN(
+ "Table does not support optimize, doing recreate + analyze instead"),
+ system_charset_info);
+ if (protocol->write())
+ goto err;
ha_autocommit_or_rollback(thd, 0);
close_thread_tables(thd);
+ DBUG_PRINT("info", ("HA_ADMIN_TRY_ALTER, trying analyze..."));
TABLE_LIST *save_next_local= table->next_local,
*save_next_global= table->next_global;
table->next_local= table->next_global= 0;
@@ -4453,6 +4501,10 @@ send_result_message:
((result_code= table->table->file->ha_analyze(thd, check_opt)) > 0))
result_code= 0; // analyze went ok
}
+ /* Start a new row for the final status row */
+ protocol->prepare_for_resend();
+ protocol->store(table_name, system_charset_info);
+ protocol->store(operator_name, system_charset_info);
if (result_code) // either mysql_recreate_table or analyze failed
{
DBUG_ASSERT(thd->is_error());
@@ -4468,7 +4520,8 @@ send_result_message:
/* Hijack the row already in-progress. */
protocol->store(STRING_WITH_LEN("error"), system_charset_info);
protocol->store(err_msg, system_charset_info);
- (void)protocol->write();
+ if (protocol->write())
+ goto err;
/* Start off another row for HA_ADMIN_FAILED */
protocol->prepare_for_resend();
protocol->store(table_name, system_charset_info);
diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy
index ccd64c24960..c3f691ef808 100644
--- a/sql/sql_yacc.yy
+++ b/sql/sql_yacc.yy
@@ -5543,6 +5543,7 @@ alter_commands:
all_or_alt_part_name_list
{
LEX *lex= Lex;
+ lex->sql_command = SQLCOM_OPTIMIZE;
lex->alter_info.flags|= ALTER_OPTIMIZE_PARTITION;
lex->no_write_to_binlog= $3;
lex->check_opt.init();
@@ -5552,6 +5553,7 @@ alter_commands:
all_or_alt_part_name_list
{
LEX *lex= Lex;
+ lex->sql_command = SQLCOM_ANALYZE;
lex->alter_info.flags|= ALTER_ANALYZE_PARTITION;
lex->no_write_to_binlog= $3;
lex->check_opt.init();
@@ -5559,6 +5561,7 @@ alter_commands:
| CHECK_SYM PARTITION_SYM all_or_alt_part_name_list
{
LEX *lex= Lex;
+ lex->sql_command = SQLCOM_CHECK;
lex->alter_info.flags|= ALTER_CHECK_PARTITION;
lex->check_opt.init();
}
@@ -5567,6 +5570,7 @@ alter_commands:
all_or_alt_part_name_list
{
LEX *lex= Lex;
+ lex->sql_command = SQLCOM_REPAIR;
lex->alter_info.flags|= ALTER_REPAIR_PARTITION;
lex->no_write_to_binlog= $3;
lex->check_opt.init();
@@ -6009,6 +6013,7 @@ repair:
lex->sql_command = SQLCOM_REPAIR;
lex->no_write_to_binlog= $2;
lex->check_opt.init();
+ lex->alter_info.reset();
}
table_list opt_mi_repair_type
{}
@@ -6037,6 +6042,7 @@ analyze:
lex->sql_command = SQLCOM_ANALYZE;
lex->no_write_to_binlog= $2;
lex->check_opt.init();
+ lex->alter_info.reset();
}
table_list
{}
@@ -6062,6 +6068,7 @@ check:
}
lex->sql_command = SQLCOM_CHECK;
lex->check_opt.init();
+ lex->alter_info.reset();
}
table_list opt_mi_check_type
{}
@@ -6093,6 +6100,7 @@ optimize:
lex->sql_command = SQLCOM_OPTIMIZE;
lex->no_write_to_binlog= $2;
lex->check_opt.init();
+ lex->alter_info.reset();
}
table_list
{}