- 17 Dec, 2009 2 commits
-
-
Jon Olav Hauglid authored
------------------------------------------------------------ revno: 2617.14.26 committer: Vladislav Vaintroub <vvaintroub@mysql.com> branch nick: mysql-6.0-wtf timestamp: Wed 2008-11-05 11:19:19 +0100 message: CMakeLists.txt files cleanup. - remove SAFEMALLOC and SAFE_MUTEX definitions that were present in *each* CMakeLists.txt. Instead, put them into top level MakeLists.txt, but disable on Windows, because a) SAFEMALLOC does not add any functionality that is not already present in Debug C runtime ( and 2 safe malloc one on top of the other only unnecessarily slows down the server) b)SAFE_MUTEX does not work on Windows and have been explicitely disabled on Windows with #undef previously. Fortunately, ntdll does pretty good job identifying l problems with CRITICAL_SECTIONs. (DebugBreak()s on using uninited critical section, unlocking unowned critical section) -Remove occationally used -D_DEBUG (added by compiler anyway) -Remove MAP file generation, it became obsolete . There are many ways to get callstack of a crash now, with stacktrace in error log , minidump etc
-
Jon Olav Hauglid authored
If the handler (or delayed insert) thread failed to lock a table due to being killed, the "dead" flag was used to notify the connection thread of this failure. However, with the changes introduced by Bug#45949, the handler thread will no longer try to lock the table if it was killed. This meant that the "dead" flag would not be set, and the connection thread would not notice that the handler thread had failed. This could happen with concurrent INSERT DELAYED and FLUSH TABLES. FLUSH TABLES would kill any active INSERT DELAYED that had opened any table(s) to be flushed. This could cause the INSERT DELAYED connection thread to be stuck waiting for the handler thread to lock its table, while the handler thread would be looping, trying to get the connection thread to notice the error. The root of the problem was that the handler thread had both the "dead" flag and "thd->killed" to indicate that it had been killed. Most places both were set, but some only set "thd->killed". And Delayed_insert::get_local_table() only checked "dead" while waiting for the table to be locked. This patch removes the "dead" variable and replaces its usage with "thd->killed", thereby resolving the issue.
-
- 16 Dec, 2009 4 commits
-
-
Jon Olav Hauglid authored
The reason for the deadlock was an improper exit from MDL_context::wait_for_locks() which caused mysys_var->current_mutex to remain LOCK_mdl even though LOCK_mdl was no longer held by that connection. This could for example lead to a deadlock in the following way: 1) INSERT DELAYED tries to open a table but fails, and trying to recover it calls wait_for_locks(). 2) Due to a pending exclusive request, wait_for_locks() fails and exits without resetting mysys_var->current_mutex for the delayed insert handler thread. So it continues to point to LOCK_mdl. 3) The handler thread manages to open a table. 4) A different connection takes LOCK_open and tries to take LOCK_mdl. 5) FLUSH TABLES from a third connection notices that the handler thread has a table open, and tries to kill it. This involves locking mysys_var->current_mutex while having LOCK_open locked. Since current_mutex mistakenly points to LOCK_mdl, we have a deadlock. This patch makes sure MDL_EXIT_COND() is called before exiting wait_for_locks(). This clears mysys->current_mutex which resolves the issue. An assert is added to recover_from_failed_open_table_attempt() after wait_for_locks() is called, to check that current_mutex is indeed reset. With this assert in place, existing tests in (e.g.) mdl_sync.test will fail without this patch.
-
Konstantin Osipov authored
-
Konstantin Osipov authored
the fix for Bug#37148, since it is null-merged into 6.0.
-
Konstantin Osipov authored
-
- 15 Dec, 2009 4 commits
-
-
Konstantin Osipov authored
-
Konstantin Osipov authored
-
Konstantin Osipov authored
-
Jon Olav Hauglid authored
This deadlock would occur between two connections A and B if statements where executed in the following way: 1) Connection A executes a DML statement against table s1.t1 with autocommit off. This causes a shared metadata lock on s1.t1 to be acquired. (With autocommit on, the metadata lock will be dropped once the statment completes and the deadlock will not occour.) 2) Connection B tries to DROP DATABASE s1. This will block against the metadata lock connection A holds on s1.t1. While blocking, connection B will hold the LOCK_mysql_create_db mutex. 3) Connection A tries to ALTER DATABASE s1. This will block when trying to get LOCK_mysql_create_db mutex held by connection B. 4) Deadlock between DROP DATABASE and ALTER DATABASE (which has autocommit off). If Connection A used an explicitly started transaction rather than having autocommit off, this deadlock did not happen as ALTER DATABASE is disallowed inside transactions. This patch fixes the problem by changing ALTER DATABASE to cause an implicit commit before executing. This will cause the metadata lock on s1.t1 to be dropped, allowing DROP DATABASE to proceed. This will in turn cause the LOCK_mysql_create_db mutex to be unlocked, allowing ALTER DATABASE to proceed. Note that SQL commands other than ALTER DATABASE that also use LOCK_mysql_create_db, already cause an implicit commit. Incompatible change: ALTER DATABASE (and its synonym ALTER SCHEMA) now cause an implicit commit. This must be reflected in the documentation. Test case added to schema.test.
-
- 11 Dec, 2009 11 commits
-
-
Konstantin Osipov authored
------------------------------------------------------------ 2599.161.3 Ingo Struewing 2009-07-21 Bug#20667 - Truncate table fails for a write locked table TRUNCATE TABLE was not allowed under LOCK TABLES. The patch removes this restriction. mysql_truncate() does now handle that case.
-
Konstantin Osipov authored
----------------------------------------------------------- 2630.28.28 Magne Mahre 2008-12-05 Bug #38661 'all threads hang in "opening tables" or "waiting for table" and cpu is at 100%' Concurrent execution of FLUSH TABLES statement and at least two statements using the same table might have led to live-lock which caused all three connections to stall and hog 100% of CPU. tdc_wait_for_old_versions() wrongly assumed that there cannot be a share with an old version and no used TABLE instances and thus was failing to perform wait in situation when such old share was cached in MDL subsystem thanks to a still active metadata lock on the table. So it might have happened that two or more connections simultaneously executing statements which involve table being flushed managed to prevent each other from waiting in this function by keeping shared metadata lock on the table constantly active (i.e. one of the statements managed to take/hold this lock while other statements were calling tdc_wait_for_old_versions()). Thus they were forcing each other to loop infinitely in open_tables() - close_thread_tables_for_reopen() - tdc_wait_for_old_versions() cycle causing CPU hogging. This patch fixes this problem by removing this false assumption from tdc_wait_for_old_versions(). Note that the problem is specific only for server versions >= 6.0. No test case is submitted for this test, as the test infrastructure hasn't got the necessary primitives to test the behaviour. The manifestation is that throughput will decrease to a low level (possibly 0) after some time, and stay at that level. Several transactions will not complete. Manual testing can be done by running the code submitted by Shane Bester attached to the bug report. If the bug persists, the transaction thruput will almost immediately drop to near zero (shown as the transaction count output from the test program staying on a close to constant value, instead of increasing rapidly).
-
Konstantin Osipov authored
----------------------------------------------------------- 2497.392.1 Michael Widenius 2008-08-19 Fixes for Bug #38016 Maria: trying to access freed memory when committing a transaction. Don't write out states if they haven't changed.
-
Konstantin Osipov authored
---------------------------------------------------- 2736.2.10 Michael Widenius 2008-10-22 Fix for bug#39395 Maria: ma_extra.c:286: maria_extra: Assertion `share->reopen == 1' failed
-
Konstantin Osipov authored
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
- 10 Dec, 2009 19 commits
-
-
Alexander Nozdrin authored
-
Magne Mahre authored
An error occuring in the execution of a stored procedure, called from do_select is masked, since the error condition is not propagated back to the caller (join->conds->val_int() returns a result value, and not an error code) An explicit check was added to see if the thd error code has been set, and if so, the loop status is set to the error state. Backport from 6.0-codebase (revid: 2617.68.31)
-
Magne Mahre authored
(diagnostics_area) Execution of CREATE TABLE ... SELECT statement was not atomic in the sense that concurrent statements trying to affect its target table might have sneaked in between the moment when the table was created and moment when it was filled according to SELECT clause. This resulted in inconsistent binary log, unexpected target table contents. In cases when concurrent statement was a DDL statement CREATE TABLE ... SELECT might have failed with ER_CANT_LOCK error. In more detail: Due to premature metadata lock downgrade which occured after CREATE TABLE SELECT statement created table but before it managed to obtain table-level lock on it other statements were allowed to open, lock and change target table in the middle of CREATE TABLE SELECT execution. This also meant that it was possible that CREATE TABLE SELECT would wait in mysql_lock_tables() when it was called for newly created table and that this wait could have been aborted by concurrent DDL. The latter led to execution of unexpected branch of code and CREATE TABLE SELECT ending with ER_CANT_LOCK error. The premature downgrade occured because open_table(), which was called for newly created table, decided that it is OK to downgrade metadata lock from exclusive to shared since table exists, even although it was not acquired within this call. This fix ensures that open_table() does not downgrade metadata lock if it is not acquired during its current invocation. Testing: The bug is exposed in a race condition, and is thus difficult to expose in a standard mysql-test-run test case. Instead, a stress test using the Random Query Generator (https://launchpad.net/randgen) will trip the problem occasionally. % perl runall.pl \ --basedir=<build dir> \ --mysqld=--table-lock-wait-timeout=5 \ --mysqld=--skip-safemalloc \ --grammar=conf/maria_bulk_insert.yy \ --reporters=ErrorLog,Backtrace,WinPackage \ --mysqld=--log-output=file \ --queries=100000 \ --threads=10 \ --engine=myisam Note: You will need a debug build to expose the bug When the bug is tripped, the server will abort and dump core. Backport from 6.0-codebase (revid: 2617.53.4)
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
Alexander Nozdrin authored
-
Jon Olav Hauglid authored
Postfix for Bug#48210 FLUSH TABLES WITH READ LOCK deadlocks against concurrent CREATE PROCEDURE Rewrote the second test to use DROP PROCEDURE instead of CREATE USER as CREATE USER does not work with embedded server.
-
Jon Olav Hauglid authored
Bug #48210 FLUSH TABLES WITH READ LOCK deadlocks against concurrent CREATE PROCEDURE This deadlock occured between a) CREATE PROCEDURE (or other commands listed below) b) FLUSH TABLES WITH READ LOCK If the execution of them happened in the following order: - a) opens a table (e.g. mysql.proc) - b) locks the global read lock (or GRL) - a) sleeps inside wait_if_global_read_lock() - b) increases refresh_version and sleeps waiting for old tables to go away Note that a) must start waiting on the GRL before FLUSH increases refresh_version. Otherwise a) won't wait on the GRL and instead close its tables for reopen, allowing FLUSH to complete and thus avoid the deadlock. With this patch the deadlock is avoided by making CREATE PROCEDURE acquire a protection against global read locks before it starts executing. This means that FLUSH TABLES WITH READ LOCK will have to wait until CREATE PROCEDURE completes before acquiring the global read lock, thereby avoiding the deadlock. This is implemented by introducing a new SQL command flag called CF_PROTECT_AGAINST_GRL. Commands marked with this flag will acquire a GRL protection in the beginning of mysql_execute_command(). This patch adds the flag to CREATE, ALTER and DROP for PROCEDURE and FUNCTION, as well as CREATE USER, DROP USER, RENAME USER and REVOKE ALL. All these commands either call open_grant_tables() or open_system_table_for_updated() which make them susceptible for this deadlock. The patch also adds the CF_PROTECT_AGAINST_GRL flag to a number of commands that previously acquired GRL protection in their respective SQLCOM case in mysql_execute_command(). Test case that checks for GRL protection for CREATE PROCEDURE and CREATE USER added to mdl_sync.test.
-
Konstantin Osipov authored
2630.16.14 Sergei Golubchik 2008-08-25 fixed a crash in partition tests introduced by HA_EXTRA_PREPARE_FOR_DROP patch
-
Jon Olav Hauglid authored
Also re-enables the test for Bug #43867 Followup to Bug#46654 False deadlock on concurrent DML/DDL with partitions, inconsistent behavior Partition_sync.test uses features only available in debug builds. Disabling the test for non-debug builds.
-
Konstantin Osipov authored
"ha_maria.cc:2415: assertion in ha_maria::store_lock()".
-
Jon Olav Hauglid authored
Bug #46654 False deadlock on concurrent DML/DDL with partitions, inconsistent behavior The problem was that if one connection is running a multi-statement transaction which involves a single partitioned table, and another connection attempts to alter the table, the first connection gets ER_LOCK_DEADLOCK and cannot proceed anymore, even when the ALTER TABLE statement in another connection has timed out or failed. The reason for this was that the prepare phase for ALTER TABLE for partitioned tables removed all instances of the table from the table definition cache before it started waiting on the lock. The transaction running in the first connection would notice this and report ER_LOCK_DEADLOCK. This patch changes the prep_alter_part_table() ALTER TABLE code so that tdc_remove_table() is no longer called. Instead, only the TABLE instance changed by prep_alter_part_table() is marked as needing reopen. The patch also removes an unnecessary call to tdc_remove_table() from mysql_unpack_partition() as the changed TABLE object is destroyed by the caller at a later point. Test case added in partition_sync.test.
-
Jon Olav Hauglid authored
Bug#40181 Made use of tdc_remove_table instead of just setting share->version to 0 to make sure all unused table instances go away as part of CREATE/ALTER TABLE.
-
Jon Olav Hauglid authored
Bug #47313 assert in check_key_in_view during CALL procedure View definitions are inlined in a stored procedure when the procedure is fist called. This means that if a temporary table is later added with the same name as the view, the stored procedure will still use the view. This happens even if temporary tables normally shadow base tables/views. The reason for the assert was that even if the stored procedure referenced the view, open_table() still tried to open the temporary table. This "half view/half temporary table" state caused the assert. The bug was not present in 5.1 as open_table() is not called for the view there. This code was changed with the introduction of MDL in order to properly lock the view and any objects it refers to. This patch fixes the problem by instructing open_table() to open base tables/views (using OT_BASE_ONLY) when reopening tables/views used by stored procedures. This also means that a prepared statement is no longer invalidated if a temporary table is created with the same name as a view used in the prepared statement. Test case added to sp.test. The test case also demonstrates the effect of sp cache invalidation between CALLs.
-
Jon Olav Hauglid authored
Bug #47635 assert in start_waiting_global_read_lock during CREATE VIEW The problem was that CREATE VIEW would trigger an assert if a temporary table with the same name already existed. This bug was fixed by the patch for Bug#47335. CREATE/ALTER VIEW will now ignore temporary tables. See Bug#47335 for more information. Test case added to view.test.
-
Jon Olav Hauglid authored
Bug #47335 assert in get_table_share The assert would happen if ALTER VIEW was used to alter a view (existing or non-existing) and a temporary table with the same name already existed. The assert is triggered if the current statement does not have a MDL lock on the view to be altered. This would happen because open_table() would open the temporary table instead and MDL locks are not taken for temporary tables (since they are local to one connection). The patch changes open_type for CREATE/ALTER VIEW to OT_BASE_ONLY. This prevents open_table() from trying to open a temporary table with the same name should one exist. Now the view will be altered if it exists or ER_NO_SUCH_TABLE will be reported if it does not. Test case added to view.test
-
Jon Olav Hauglid authored
Followup to Bug#42546 Backup: RESTORE fails, thinking it finds an existing table This patch updates lowercase_table2.test with the changed error message CREATE TABLE produces if it fails because it finds an matching TABLE_SHARE in the TDC even if the .FRM/.MYD has been removed from disk. With the changes introduced in Bug#42546, CREATE TABLE uses open_tables() which will find the TDC entry and fail in open_table_from_share() with ER_FILE_NOT_FOUND. Before, CREATE TABLE would not use open_tables() and fail with ER_TABLE_EXISTS_ERROR upon finding the TDC entry in mysql_create_table_no_lock().
-
Jon Olav Hauglid authored
Bug#42546 Backup: RESTORE fails, thinking it finds an existing table The problem occured when a MDL locking conflict happened for a non-existent table between a CREATE and a INSERT statement. The code for CREATE interpreted this lock conflict to mean that the table existed, which meant that the statement failed when it should not have. The problem could occur for CREATE TABLE, CREATE TABLE LIKE and ALTER TABLE RENAME. This patch fixes the problem for CREATE TABLE and CREATE TABLE LIKE. It is based on code backported from the mysql-6.1-fk tree written by Dmitry Lenev. CREATE now uses normal open_and_lock_tables() code to acquire exclusive locks. This means that for the test case in the bug description, CREATE will wait until INSERT completes so that it can get the exclusive lock. This resolves the reported bug. The patch also prohibits CREATE TABLE and CREATE TABLE LIKE under LOCK TABLES. Note that this is an incompatible change and must be reflected in the documentation. Affected test cases have been updated. mdl_sync.test contains tests for CREATE TABLE and CREATE TABLE LIKE. Fixing the issue for ALTER TABLE RENAME is beyond the scope of this patch. ALTER TABLE cannot be prohibited from working under LOCK TABLES as this could seriously impact customers and a proper fix would require a significant rewrite.
-
Magne Mahre authored
An assert in reload_acl_and_cache didn't account for the case when the function is called with a NULL thd. A null thd is used whenever the function is called from the SIGHUP signal handler. Backported from 6.0-codebase (revid: 2617.69.35)
-