Commit 23549493 authored by unknown's avatar unknown

BUG#5390 - problems with merge tables

Additional fix for INSERT DELAYED with subselect.
Originally detected in 5.1, but 5.0 could also be affected.
The user thread creates a dummy table object,
which is not included in the lock. The 'real' table is
opened and locked by the 'delayed' system thread.
The dummy object is now marked as not locked and this is
tested in mysql_lock_have_duplicate().


sql/lock.cc:
  BUG#5390 - problems with merge tables
  Additional fix for INSERT DELAYED with subselect.
  The user thread creates a dummy table object,
  which is not included in the lock.
  Changed to safer asserts.
sql/sql_insert.cc:
  BUG#5390 - problems with merge tables
  Marked the dummy table object as not being
  included in the lock.
parent 6fa55915
...@@ -530,8 +530,11 @@ TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle, ...@@ -530,8 +530,11 @@ TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle,
THR_LOCK_DATA **end_data2; THR_LOCK_DATA **end_data2;
DBUG_ENTER("mysql_lock_have_duplicate"); DBUG_ENTER("mysql_lock_have_duplicate");
/* Table may not be defined for derived or view tables. */ /*
if (! (table= needle->table)) Table may not be defined for derived or view tables.
Table may not be part of a lock for delayed operations.
*/
if (! (table= needle->table) || ! table->lock_count)
goto end; goto end;
/* A temporary table does not have locks. */ /* A temporary table does not have locks. */
...@@ -550,7 +553,8 @@ TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle, ...@@ -550,7 +553,8 @@ TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle,
lock_tables= mylock->table; lock_tables= mylock->table;
/* Prepare table related variables that don't change in loop. */ /* Prepare table related variables that don't change in loop. */
DBUG_ASSERT(table == lock_tables[table->lock_position]); DBUG_ASSERT((table->lock_position < mylock->table_count) &&
(table == lock_tables[table->lock_position]));
table_lock_data= lock_locks + table->lock_data_start; table_lock_data= lock_locks + table->lock_data_start;
end_data= table_lock_data + table->lock_count; end_data= table_lock_data + table->lock_count;
...@@ -563,7 +567,8 @@ TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle, ...@@ -563,7 +567,8 @@ TABLE_LIST *mysql_lock_have_duplicate(THD *thd, TABLE_LIST *needle,
continue; continue;
/* All tables in list must be in lock. */ /* All tables in list must be in lock. */
DBUG_ASSERT(table2 == lock_tables[table2->lock_position]); DBUG_ASSERT((table2->lock_position < mylock->table_count) &&
(table2 == lock_tables[table2->lock_position]));
for (lock_data2= lock_locks + table2->lock_data_start, for (lock_data2= lock_locks + table2->lock_data_start,
end_data2= lock_data2 + table2->lock_count; end_data2= lock_data2 + table2->lock_count;
......
...@@ -1537,6 +1537,9 @@ TABLE *delayed_insert::get_local_table(THD* client_thd) ...@@ -1537,6 +1537,9 @@ TABLE *delayed_insert::get_local_table(THD* client_thd)
/* Adjust in_use for pointing to client thread */ /* Adjust in_use for pointing to client thread */
copy->in_use= client_thd; copy->in_use= client_thd;
/* Adjust lock_count. This table object is not part of a lock. */
copy->lock_count= 0;
return copy; return copy;
/* Got fatal error */ /* Got fatal error */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment