From 23321f629b465f17fd0d91d442aa736183b355b2 Mon Sep 17 00:00:00 2001 From: "Praveenkumar.Hulakund" Date: Wed, 14 Jan 2015 13:15:20 +0530 Subject: Bug#19786309 - CRASH IN UNLOCK TABLES AFTER LOCKING AND TRUNCATING TEMPORARY TABLE. Attempt to truncate temporary table using Blackhole storage and locked by LOCK TABLES caused assertion failure and crashes. Blackhole is a transaction-aware engine. While creating the temporary table in transaction-aware engine, temporary table of type "TRANSACTIONAL_TMP_TABLE" is created. For such temporary tables a THR_LOCK lock is acquired by the LOCK TABLE operation. References to them are also added into MYSQL_LOCK::table[] array. Also for Blackhole engine, flag HTON_CAN_RECREATE is set. While truncating temporary tables, no locks are taken and recreate_temporary_table() is called for engines having "HTON_CAN_RECREATE" in flag. Function closefrm() is called from the recreate_temporary_table(), to close the current temporary table. In closefrm(), the lock on table expected is "F_UNLCK". In debug builds, assert condition on this fails when lock of type "F_WRLCK" is acquired by LOCK TABLE operation on temporary tables using Blackhole engine. In non-debug builds closefrm() simply freed TABLE object leaving dangling pointer to this object in MYSQL_LOCK::table[] array which might lead to crashes later. Fix: --------- To fix this issue, we now unlock and remove table from MYSQL_LOCK::table[] array before calling close_temporary_table() in recreate_temporary_table(). This is achieved by calling mysql_lock_remove() function for this table. --- sql/sql_truncate.cc | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) (limited to 'sql/sql_truncate.cc') diff --git a/sql/sql_truncate.cc b/sql/sql_truncate.cc index 07bf145c847..4f250e6e7a0 100644 --- a/sql/sql_truncate.cc +++ b/sql/sql_truncate.cc @@ -1,4 +1,4 @@ -/* Copyright (c) 2010, 2014, Oracle and/or its affiliates. All rights reserved. +/* Copyright (c) 2010, 2015, 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 @@ -286,6 +286,12 @@ static bool recreate_temporary_table(THD *thd, TABLE *table) table->file->info(HA_STATUS_AUTO | HA_STATUS_NO_LOCK); + /* + If LOCK TABLES list is not empty and contains this table + then unlock the table and remove it from this list. + */ + mysql_lock_remove(thd, thd->lock, table); + /* Don't free share. */ close_temporary_table(thd, table, FALSE, FALSE); -- cgit v1.2.1