List:Commits« Previous MessageNext Message »
From:cbell Date:December 11 2007 1:07am
Subject:bk commit into 6.0 tree (cbell:1.2748) BUG#33024
View as plain text  
Below is the list of changes that have just been committed into a local
6.0 repository of cbell. When cbell does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html

ChangeSet@stripped, 2007-12-10 19:45:45-05:00, cbell@mysql_cab_desk. +7 -0
  BUG#33024 : DDL Blocker uses exposed variables
  
  This patch includes a refactored DDL blocker that hides the 
  condition booleans and implements the methods as a singleton class.

  mysql-test/r/backup_ddl_blocker.result@stripped, 2007-12-10 19:43:11-05:00, Chuck@mysql_cab_desk. +42 -0
    BUG#33024 : DDL Blocker uses exposed variables
    
    New test results.

  mysql-test/t/backup_ddl_blocker.test@stripped, 2007-12-10 19:43:11-05:00, Chuck@mysql_cab_desk. +80 -0
    BUG#33024 : DDL Blocker uses exposed variables
    
    Added test for testing multiple blockers.

  sql/backup/kernel.cc@stripped, 2007-12-10 19:43:14-05:00, Chuck@mysql_cab_desk. +9 -9
    BUG#33024 : DDL Blocker uses exposed variables
    
    Changes made to call singleton.

  sql/ddl_blocker.cc@stripped, 2007-12-10 19:43:12-05:00, Chuck@mysql_cab_desk. +57 -11
    BUG#33024 : DDL Blocker uses exposed variables
    
    Refactored DDL blocker using a singleton class.

  sql/ddl_blocker.h@stripped, 2007-12-10 19:43:12-05:00, Chuck@mysql_cab_desk. +110 -41
    BUG#33024 : DDL Blocker uses exposed variables
    
    This patch changes the DDL blocker from APIs to a singleton class.

  sql/mysqld.cc@stripped, 2007-12-10 19:43:12-05:00, Chuck@mysql_cab_desk. +9 -17
    BUG#33024 : DDL Blocker uses exposed variables
    
    Instantiate the singleton class.

  sql/sql_parse.cc@stripped, 2007-12-10 19:43:13-05:00, Chuck@mysql_cab_desk. +30 -28
    BUG#33024 : DDL Blocker uses exposed variables
    
    Changes made to call singleton.

diff -Nrup a/mysql-test/r/backup_ddl_blocker.result b/mysql-test/r/backup_ddl_blocker.result
--- a/mysql-test/r/backup_ddl_blocker.result	2007-12-04 12:38:01 -05:00
+++ b/mysql-test/r/backup_ddl_blocker.result	2007-12-10 19:43:11 -05:00
@@ -1152,5 +1152,47 @@ WHERE TABLE_NAME = 't3' AND TABLE_SCHEMA
 count(*)
 2
 DROP TABLE test.t2;
+
+Starting Test 7 - Running multiple backups at the same time
+
+SET GLOBAL debug="d,backup_debug:d,backup:d,allow_multiple_backups";
+DROP DATABASE IF EXISTS test_bup;
+Warnings:
+Note	1008	Can't drop database 'test_bup'; database doesn't exist
+CREATE DATABASE test_bup;
+CREATE TABLE test_bup.t1 (a int);
+INSERT INTO test_bup.t1 VALUES (1), (2), (3), (4), (5);
+con1: Getting lock.
+SELECT get_lock("DDL_blocker_blocked", 100);
+get_lock("DDL_blocker_blocked", 100)
+1
+start a backup
+BACKUP DATABASE bup_ddl_blocker TO "bup_ddl_blocker.bak";
+start a backup
+BACKUP DATABASE test TO "bup_ddl_blocker_test.bak";
+start a backup
+BACKUP DATABASE test_bup TO "bup_ddl_blocker_test_bup.bak";
+con1: Checking locks
+SELECT state, info FROM INFORMATION_SCHEMA.PROCESSLIST
+WHERE info LIKE "BACKUP DATABASE bup_ddl_blocker%";
+state	info
+debug_sync_point: DDL_blocker_blocked	BACKUP DATABASE bup_ddl_blocker TO "bup_ddl_blocker.bak"
+SELECT state, info FROM INFORMATION_SCHEMA.PROCESSLIST
+WHERE info LIKE "BACKUP DATABASE test %";
+state	info
+DDL blocker: Checking block on blocker	BACKUP DATABASE test TO "bup_ddl_blocker_test.bak"
+SELECT state, info FROM INFORMATION_SCHEMA.PROCESSLIST
+WHERE info LIKE "BACKUP DATABASE test_bup%";
+state	info
+DDL blocker: Checking block on blocker	BACKUP DATABASE test_bup TO "bup_ddl_blocker_test_bup.bak"
+SELECT release_lock("DDL_blocker_blocked");
+release_lock("DDL_blocker_blocked")
+1
+backup_id
+#
+backup_id
+#
+backup_id
+#
 con1: Cleanup
 DROP DATABASE bup_ddl_blocker;
diff -Nrup a/mysql-test/t/backup_ddl_blocker.test b/mysql-test/t/backup_ddl_blocker.test
--- a/mysql-test/t/backup_ddl_blocker.test	2007-12-06 13:05:56 -05:00
+++ b/mysql-test/t/backup_ddl_blocker.test	2007-12-10 19:43:11 -05:00
@@ -1948,11 +1948,91 @@ WHERE TABLE_NAME = 't3' AND TABLE_SCHEMA
 DROP TABLE test.t2;
 
 
+
+
+##############################################################
+--echo 
+--echo Starting Test 7 - Running multiple backups at the same time
+--echo 
+##############################################################
+
+SET GLOBAL debug="d,backup_debug:d,backup:d,allow_multiple_backups";
+
+DROP DATABASE IF EXISTS test_bup;
+CREATE DATABASE test_bup;
+CREATE TABLE test_bup.t1 (a int);
+INSERT INTO test_bup.t1 VALUES (1), (2), (3), (4), (5);
+
+--echo con1: Getting lock.
+SELECT get_lock("DDL_blocker_blocked", 100);
+
+connection con2;
+
+# Start a backup operation and have it wait on the breakpoint
+--echo start a backup
+send BACKUP DATABASE bup_ddl_blocker TO "bup_ddl_blocker.bak";
+
+connection con3;
+
+# Start a backup operation and have it wait on the breakpoint
+--echo start a backup
+send BACKUP DATABASE test TO "bup_ddl_blocker_test.bak";
+
+connection con4;
+
+# Start a backup operation and have it wait on the breakpoint
+--echo start a backup
+send BACKUP DATABASE test_bup TO "bup_ddl_blocker_test_bup.bak";
+
+connection con1;
+
+# Wait for lock to be acquired and execution to reach breakpoint
+--echo con1: Checking locks
+let $wait_condition = SELECT state = "debug_sync_point: DDL_blocker_blocked"
+                      FROM INFORMATION_SCHEMA.PROCESSLIST
+                      WHERE info LIKE "BACKUP DATABASE bup_ddl_blocker%";
+--source include/wait_condition.inc
+
+SELECT state, info FROM INFORMATION_SCHEMA.PROCESSLIST
+WHERE info LIKE "BACKUP DATABASE bup_ddl_blocker%";
+
+let $wait_condition = SELECT state = "DDL blocker: Checking block on blocker"
+                      FROM INFORMATION_SCHEMA.PROCESSLIST
+                      WHERE info LIKE "BACKUP DATABASE test %";
+--source include/wait_condition.inc
+
+SELECT state, info FROM INFORMATION_SCHEMA.PROCESSLIST
+WHERE info LIKE "BACKUP DATABASE test %";
+
+let $wait_condition = SELECT state = "DDL blocker: Checking block on blocker"
+                      FROM INFORMATION_SCHEMA.PROCESSLIST
+                      WHERE info LIKE "BACKUP DATABASE test_bup%";
+--source include/wait_condition.inc
+
+SELECT state, info FROM INFORMATION_SCHEMA.PROCESSLIST
+WHERE info LIKE "BACKUP DATABASE test_bup%";
+
+SELECT release_lock("DDL_blocker_blocked");
+
+connection con2;
+--replace_column 1 #
+reap;
+
+connection con3;
+--replace_column 1 #
+reap;
+
+connection con4;
+--replace_column 1 #
+reap;
+
 --echo con1: Cleanup
 DROP DATABASE bup_ddl_blocker;
 
 remove_file $MYSQLTEST_VARDIR/master-data/bup_ddl_blocker_orig.bak;
 remove_file $MYSQLTEST_VARDIR/master-data/bup_ddl_blocker.bak;
+remove_file $MYSQLTEST_VARDIR/master-data/bup_ddl_blocker_test.bak;
+remove_file $MYSQLTEST_VARDIR/master-data/bup_ddl_blocker_test_bup.bak;
 
 
 
diff -Nrup a/sql/backup/kernel.cc b/sql/backup/kernel.cc
--- a/sql/backup/kernel.cc	2007-12-03 15:28:16 -05:00
+++ b/sql/backup/kernel.cc	2007-12-10 19:43:14 -05:00
@@ -29,6 +29,8 @@
 #include "ddl_blocker.h"
 #include "backup_progress.h"
 
+extern DDL_blocker_class *DDL_blocker;
+
 namespace backup {
 
 // Helper functions
@@ -67,10 +69,6 @@ void free_stream_memory();
 
 }
 
-extern pthread_mutex_t THR_LOCK_DDL_blocker;
-extern pthread_cond_t COND_backup_blocked;
-extern pthread_cond_t COND_DDL_blocker;
-
 /**
   Call backup kernel API to execute backup related SQL statement.
 
@@ -109,6 +107,7 @@ execute_backup_command(THD *thd, LEX *le
     DBUG_RETURN(ER_BACKUP_INVALID_LOC);
   }
 
+  DBUG_EXECUTE_IF("allow_multiple_backups", goto test_ddl_blocker;);
   /*
     Start_backup_or_restore() will check if another BACKUP/RESTORE command is 
     running now and inform us about that. If this is the case we report error.
@@ -121,6 +120,7 @@ execute_backup_command(THD *thd, LEX *le
       DBUG_RETURN(ER_BACKUP_RUNNING);
     }
 
+test_ddl_blocker:
   prepare_stream_memory();
   int res= 0;
 
@@ -177,7 +177,7 @@ execute_backup_command(THD *thd, LEX *le
       /*
         Freeze all DDL operations by turning on DDL blocker.
       */
-      if (!block_DDL(thd))
+      if (!DDL_blocker->block_DDL(thd))
       {
         stop= my_time(0); 
         info.save_end_time(stop);
@@ -235,7 +235,7 @@ execute_backup_command(THD *thd, LEX *le
     /*
       Unfreeze all DDL operations by turning off DDL blocker.
     */
-    unblock_DDL();
+    DDL_blocker->unblock_DDL();
     BACKUP_BREAKPOINT("DDL_unblocked");
     
     if (stream)
@@ -267,7 +267,7 @@ execute_backup_command(THD *thd, LEX *le
               be counted. Waiting until after this step caused backup to
               skip new or dropped tables.
       */
-      if (!block_DDL(thd))
+      if (!DDL_blocker->block_DDL(thd))
         goto backup_error;
 
       Backup_info info(thd);
@@ -359,7 +359,7 @@ execute_backup_command(THD *thd, LEX *le
     /*
       Unfreeze all DDL operations by turning off DDL blocker.
     */
-    unblock_DDL();
+    DDL_blocker->unblock_DDL();
     BACKUP_BREAKPOINT("DDL_unblocked");
 
     if (stream)
@@ -442,7 +442,7 @@ int mysql_backup(THD *thd,
 
  error:
 
-  unblock_DDL();
+  DDL_blocker->unblock_DDL();
   DBUG_RETURN(ERROR);
 }
 
diff -Nrup a/sql/ddl_blocker.cc b/sql/ddl_blocker.cc
--- a/sql/ddl_blocker.cc	2007-11-23 08:27:41 -05:00
+++ b/sql/ddl_blocker.cc	2007-12-10 19:43:12 -05:00
@@ -29,15 +29,49 @@
 
 #include "ddl_blocker.h"
 
-my_bool DDL_blocked= FALSE;   ///< Assume DDL is not blocked.
-int DDL_blocks= 0;            ///< Number of DDL operations in progress.
+DDL_blocker_class *DDL_blocker_class::m_instance= NULL;
+
+DDL_blocker_class *DDL_blocker_class::get_DDL_blocker_class_instance()
+{
+  if (m_instance == NULL)
+    m_instance = new DDL_blocker_class();
+  return m_instance;
+}
+
+void DDL_blocker_class::destroy_DDL_blocker_class_instance()
+{
+  delete m_instance;
+  m_instance= NULL;
+}
+
+DDL_blocker_class::DDL_blocker_class()
+{
+  pthread_mutex_init(&THR_LOCK_DDL_blocker, MY_MUTEX_INIT_FAST);
+  pthread_mutex_init(&THR_LOCK_DDL_is_blocked, MY_MUTEX_INIT_FAST);
+  pthread_mutex_init(&THR_LOCK_DDL_blocker_blocked, MY_MUTEX_INIT_FAST);
+  pthread_cond_init(&COND_DDL_blocker, NULL);
+  pthread_cond_init(&COND_process_blocked, NULL);
+  pthread_cond_init(&COND_DDL_blocker_blocked, NULL);
+  DDL_blocked= FALSE;
+  DDL_blocks= 0;
+}
+
+DDL_blocker_class::~DDL_blocker_class()
+{
+  pthread_mutex_destroy(&THR_LOCK_DDL_blocker);
+  pthread_mutex_destroy(&THR_LOCK_DDL_is_blocked);
+  pthread_mutex_destroy(&THR_LOCK_DDL_blocker_blocked);
+  pthread_cond_destroy(&COND_DDL_blocker);
+  pthread_cond_destroy(&COND_process_blocked);
+  pthread_cond_destroy(&COND_DDL_blocker_blocked);
+}
 
 /**
    start_DDL()
 
    Increments the DDL_blocks counter to indicate a DDL is in progress.
   */
-void start_DDL()
+void DDL_blocker_class::start_DDL()
 {
   DBUG_ENTER("start_DDL()");
   pthread_mutex_lock(&THR_LOCK_DDL_blocker);
@@ -52,7 +86,7 @@ void start_DDL()
    Decrements the DDL_blocks counter to indicate a DDL is done.
    Signals blocked process if counter == 0.
   */
-void end_DDL()
+void DDL_blocker_class::end_DDL()
 {
   DBUG_ENTER("end_DDL()");
   pthread_mutex_lock(&THR_LOCK_DDL_blocker);
@@ -65,7 +99,7 @@ void end_DDL()
 }
 
 /**
-    check_ddl_blocker
+    check_DDL_blocker
 
     Check to see if we are blocked from continuing. If so,
     wait until the blocked process signals the condition.
@@ -73,7 +107,7 @@ void end_DDL()
     @param thd The THD object from the caller.
     @returns TRUE
   */
-my_bool check_DDL_blocker(THD *thd)
+my_bool DDL_blocker_class::check_DDL_blocker(THD *thd)
 {
   DBUG_ENTER("check_DDL_blocker()");
   BACKUP_BREAKPOINT("DDL_not_blocked");
@@ -105,16 +139,27 @@ my_bool check_DDL_blocker(THD *thd)
    @params thd THD object.
    @returns TRUE
   */
-my_bool block_DDL(THD *thd)
+my_bool DDL_blocker_class::block_DDL(THD *thd)
 {
   DBUG_ENTER("block_DDL()");
 
   BACKUP_BREAKPOINT("DDL_in_progress");
+
   /*
     Only 1 DDL blocking operation can run at a time.
+    Check the blocker blocked condition. 
+    Rest until blocker is released.
   */
-  if (DDL_blocked)
-    DBUG_RETURN(FALSE);
+  pthread_mutex_lock(&THR_LOCK_DDL_blocker_blocked);
+  thd->enter_cond(&COND_DDL_blocker_blocked, &THR_LOCK_DDL_blocker_blocked,
+                  "DDL blocker: Checking block on blocker");
+  while (DDL_blocked)
+    pthread_cond_wait(&COND_DDL_blocker_blocked, &THR_LOCK_DDL_blocker_blocked);
+  DDL_blocked= TRUE;
+  thd->exit_cond("DDL blocker: Ok to block operation - no blocker in progress");
+
+  BACKUP_BREAKPOINT("DDL_blocker_blocked");
+
   /*
     Check the ddl blocker condition. Rest until ddl blocker is released.
   */
@@ -123,8 +168,8 @@ my_bool block_DDL(THD *thd)
                   "DDL blocker: Checking block on DDL changes");
   while (DDL_blocks != 0)
     pthread_cond_wait(&COND_process_blocked, &THR_LOCK_DDL_blocker);
-  DDL_blocked= TRUE;
   thd->exit_cond("DDL blocker: Ok to run operation - no DDL in progress");
+
   BACKUP_BREAKPOINT("DDL_blocked");
   DBUG_RETURN(TRUE);
 }
@@ -135,11 +180,12 @@ my_bool block_DDL(THD *thd)
    This method is used to unblock all DDL commands. It sets the boolean
    DDL_blocked to FALSE to tell the DDL operations that they can proceed.
   */
-void unblock_DDL()
+void DDL_blocker_class::unblock_DDL()
 {
   pthread_mutex_lock(&THR_LOCK_DDL_blocker);
   DDL_blocked= FALSE;
   pthread_cond_broadcast(&COND_DDL_blocker);
+  pthread_cond_signal(&COND_DDL_blocker_blocked);
   pthread_mutex_unlock(&THR_LOCK_DDL_blocker);
 }
 
diff -Nrup a/sql/ddl_blocker.h b/sql/ddl_blocker.h
--- a/sql/ddl_blocker.h	2007-11-24 16:45:07 -05:00
+++ b/sql/ddl_blocker.h	2007-12-10 19:43:12 -05:00
@@ -6,44 +6,113 @@
 #include "mysql_priv.h"
 #include "backup/debug.h"
 
-/*
-  Mutexes and condition variables -- see mysqld.cc.
-*/
-extern pthread_mutex_t THR_LOCK_DDL_blocker; 
-extern pthread_mutex_t THR_LOCK_DDL_is_blocked; 
-extern pthread_cond_t COND_DDL_blocker;
-extern pthread_cond_t COND_process_blocked;
-
-/*
-  Increments the backup's counter to indicate a DDL is in progress.
-*/
-void start_DDL();
-
-/*
-  Decrements the backup's counter to indicate a DDL is done.
-  Signals backup process if counter == 0.
-*/
-void end_DDL();
-
-/*
-  Check to see if we are blocked from continuing. If so,
-  wait until the backup process signals the condition.
-*/
-my_bool check_DDL_blocker(THD *thd);
-
-/*
-  This method is used to block all DDL commands. It checks the counter
-  DDL_blocks and if > 0 it blocks the backup until all DDL operations are
-  complete and the condition variable has been signaled. 
-
-  The method also sets the boolean DDL_blocked to TRUE to tell the DDL
-  operations that they must block until the backup operation is complete.
-*/
-my_bool block_DDL(THD *thd);
-
-/*
-  This method is used to unblock all DDL commands. It sets the boolean
-  DDL_blocked to FALSE to tell the DDL operations that they can proceed.
-*/
-void unblock_DDL();
-
+/**
+   @class DDL_blocker_class
+ 
+   @brief Implements a simple DDL blocker mechanism.
+ 
+   The DDL_blocker_class is a singleton class designed to allow DDL
+   operations to be blocked while an operation that uses this class
+   executes. The class is designed to allow any number of DDL operations
+   to execute but only one blocking operation can block DDL operations
+   at a time. 
+
+   If an operation has blocked DDL operations and another operation attempts
+   to block DDL operations, the second blocking operation will wait
+   until the first blocking operation is complete.
+ 
+   Checking for Block
+   For any DDL operation that needs to be blocked while another 
+   operation is executing, you can check the status of the DDL blocker
+   by calling @c check_DDL_blocker(). This method will return when there
+   is no block or wait while the blocking operation is running. Once the
+   method returns, the DDL operation that called the method is registered
+   so that any other blocking operation will wait while the DDL operation
+   is running. When the DDL operation is complete, you must unregister the
+   DDL operation by calling end_DDL().
+
+   Blocking DDL Operations
+   To block a DDL operation, call block_DDL(). This registers the blocking
+   operation and prevents any DDL operations that use check_DDL_blocker()
+   to block while the blocking operation is running. When the blocking
+   operation is complete, you must call unblock_DDL() to unregister
+   the blocking operation.
+
+   Singleton Methods
+   The creation of the singleton is accomplished using 
+   get_DDL_blocker_class_instance(). This method is called from mysqld.cc
+   and creates and initializes all of the private mutex, condition, and
+   controlling variables. The method destroy_DDL_blocker_class_instance()
+   destroys the mutex and condition variables. 
+
+   Calling the Singleton
+   To call the singleton class, you must declare an external variable
+   to the global variable DDL_blocker as shown below.
+
+   @c extern DDL_blocker_class *DDL_blocker;
+
+   Calling methods on the singleton is accomplished using the DDL_blocker
+   variable such as: @c DDL_blocker->block_DDL().
+  */
+class DDL_blocker_class
+{
+  public:
+
+    /*
+      Singleton class
+    */
+    static DDL_blocker_class *get_DDL_blocker_class_instance();
+    static void destroy_DDL_blocker_class_instance();
+
+    /*
+      Check to see if we are blocked from continuing. If so,
+      wait until the backup process signals the condition.
+    */
+    my_bool check_DDL_blocker(THD *thd);
+
+    /*
+      Decrements the backup's counter to indicate a DDL is done.
+      Signals backup process if counter == 0.
+    */
+    void end_DDL();
+
+    /*
+      This method is used to block all DDL commands. It checks the counter
+      DDL_blocks and if > 0 it blocks the backup until all DDL operations are
+      complete and the condition variable has been signaled. 
+
+      The method also sets the boolean DDL_blocked to TRUE to tell the DDL
+      operations that they must block until the backup operation is complete.
+    */
+    my_bool block_DDL(THD *thd);
+
+    /*
+      This method is used to unblock all DDL commands. It sets the boolean
+      DDL_blocked to FALSE to tell the DDL operations that they can proceed.
+    */
+    void unblock_DDL();
+
+  private:
+
+    DDL_blocker_class();
+    ~DDL_blocker_class();
+
+    /*
+      Increments the backup's counter to indicate a DDL is in progress.
+    */
+    void start_DDL();
+
+    /*
+      These variables are used to implement the metadata freeze "DDL blocker"
+      for online backup.
+    */
+    pthread_mutex_t THR_LOCK_DDL_blocker;    ///< Mutex for blocking DDL   
+    pthread_mutex_t THR_LOCK_DDL_is_blocked; ///< Mutex for checking block DDL 
+    pthread_mutex_t THR_LOCK_DDL_blocker_blocked; ///< One blocker at a time 
+    pthread_cond_t COND_DDL_blocker;         ///< cond for blocking DDL
+    pthread_cond_t COND_process_blocked;     ///< cond for checking block DDL
+    pthread_cond_t COND_DDL_blocker_blocked; ///< cond for blocker blocked
+    my_bool DDL_blocked;                     ///< Is blocking operation running
+    int DDL_blocks;              ///< Number of DDL operations in progress.
+    static DDL_blocker_class *m_instance;    ///< instance var for singleton 
+};
diff -Nrup a/sql/mysqld.cc b/sql/mysqld.cc
--- a/sql/mysqld.cc	2007-12-06 12:31:04 -05:00
+++ b/sql/mysqld.cc	2007-12-10 19:43:12 -05:00
@@ -26,6 +26,7 @@
 #include "mysqld_suffix.h"
 #include "mysys_err.h"
 #include "events.h"
+#include "DDL_blocker.h"
 
 #include "../storage/myisam/ha_myisam.h"
 
@@ -364,6 +365,7 @@ static pthread_cond_t COND_thread_cache,
 
 /* Global variables */
 
+DDL_blocker_class *DDL_blocker= NULL;
 bool opt_update_log, opt_bin_log;
 my_bool opt_log, opt_slow_log;
 ulong log_output_options;
@@ -579,15 +581,6 @@ pthread_mutex_t LOCK_mysql_create_db, LO
 		LOCK_crypt, LOCK_bytes_sent, LOCK_bytes_received,
 	        LOCK_global_system_variables,
 		LOCK_user_conn, LOCK_slave_list, LOCK_active_mi;
-
-/*
-  These variables are used to implement the metadata freeze "DDL blocker"
-  for online backup.
-*/
-pthread_mutex_t THR_LOCK_DDL_blocker; 
-pthread_mutex_t THR_LOCK_DDL_is_blocked; 
-pthread_cond_t COND_DDL_blocker;
-pthread_cond_t COND_process_blocked;
 pthread_mutex_t LOCK_backup;
 
 /*
@@ -1348,11 +1341,7 @@ static void clean_up_mutexes()
   (void) pthread_mutex_destroy(&LOCK_bytes_sent);
   (void) pthread_mutex_destroy(&LOCK_bytes_received);
   (void) pthread_mutex_destroy(&LOCK_user_conn);
-  (void) pthread_mutex_destroy(&THR_LOCK_DDL_blocker);
-  (void) pthread_mutex_destroy(&THR_LOCK_DDL_is_blocked);
   (void) pthread_mutex_destroy(&LOCK_backup);
-  (void) pthread_cond_destroy(&COND_DDL_blocker);
-  (void) pthread_cond_destroy(&COND_process_blocked);
   Events::destroy_mutexes();
 #ifdef HAVE_OPENSSL
   (void) pthread_mutex_destroy(&LOCK_des_key_file);
@@ -1380,6 +1369,7 @@ static void clean_up_mutexes()
   (void) pthread_cond_destroy(&COND_thread_cache);
   (void) pthread_cond_destroy(&COND_flush_thread_cache);
   (void) pthread_cond_destroy(&COND_manager);
+  DDL_blocker_class::destroy_DDL_blocker_class_instance();
 }
 
 #endif /*EMBEDDED_LIBRARY*/
@@ -3109,11 +3099,7 @@ static int init_thread_environment()
   (void) pthread_mutex_init(&LOCK_global_read_lock, MY_MUTEX_INIT_FAST);
   (void) pthread_mutex_init(&LOCK_prepared_stmt_count, MY_MUTEX_INIT_FAST);
   (void) pthread_mutex_init(&LOCK_uuid_generator, MY_MUTEX_INIT_FAST);
-  (void) pthread_mutex_init(&THR_LOCK_DDL_blocker, MY_MUTEX_INIT_FAST);
-  (void) pthread_mutex_init(&THR_LOCK_DDL_is_blocked, MY_MUTEX_INIT_FAST);
   (void) pthread_mutex_init(&LOCK_backup, MY_MUTEX_INIT_FAST);
-  (void) pthread_cond_init(&COND_DDL_blocker, NULL);
-  (void) pthread_cond_init(&COND_process_blocked, NULL);
 #ifdef HAVE_OPENSSL
   (void) pthread_mutex_init(&LOCK_des_key_file,MY_MUTEX_INIT_FAST);
 #ifndef HAVE_YASSL
@@ -3143,6 +3129,12 @@ static int init_thread_environment()
 #endif
   (void) pthread_mutex_init(&LOCK_server_started, MY_MUTEX_INIT_FAST);
   (void) pthread_cond_init(&COND_server_started,NULL);
+
+  /*
+    Initialize the DDL blocker
+  */
+  DDL_blocker= DDL_blocker_class::get_DDL_blocker_class_instance();
+
   sp_cache_init();
   Events::init_mutexes();
   /* Parameter for threads created for connections */
diff -Nrup a/sql/sql_parse.cc b/sql/sql_parse.cc
--- a/sql/sql_parse.cc	2007-12-06 12:31:04 -05:00
+++ b/sql/sql_parse.cc	2007-12-10 19:43:13 -05:00
@@ -89,6 +89,8 @@ const char *xa_state_names[]={
   "NON-EXISTING", "ACTIVE", "IDLE", "PREPARED"
 };
 
+extern DDL_blocker_class *DDL_blocker;
+
 static void unlock_locked_tables(THD *thd)
 {
   if (thd->locked_tables)
@@ -2142,7 +2144,7 @@ mysql_execute_command(THD *thd)
       TABLE in the same way. That way we avoid that a new table is
       created during a gobal read lock.
     */
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     if (!thd->locked_tables &&
         !(need_start_waiting= !wait_if_global_read_lock(thd, 0, 1)))
     {
@@ -2240,7 +2242,7 @@ mysql_execute_command(THD *thd)
           res= handle_select(thd, lex, result, 0);
           delete result;
         }
-        end_DDL();
+        DDL_blocker->end_DDL();
       }
       else if (!(create_info.options & HA_LEX_CREATE_TMP_TABLE))
         create_table= lex->unlink_first_table(&link_to_local);
@@ -2267,7 +2269,7 @@ mysql_execute_command(THD *thd)
 
     /* put tables back for PS rexecuting */
 end_with_restore_list:
-    end_DDL();
+    DDL_blocker->end_DDL();
     lex->link_first_table_back(create_table, link_to_local);
     break;
   }
@@ -2351,7 +2353,7 @@ end_with_restore_list:
   case SQLCOM_ALTER_TABLE:
     DBUG_ASSERT(first_table == all_tables && first_table != 0);
     {
-      check_DDL_blocker(thd);
+      DDL_blocker->check_DDL_blocker(thd);
       ulong priv=0;
       ulong priv_needed= ALTER_ACL;
       /*
@@ -2365,7 +2367,7 @@ end_with_restore_list:
 
       if (thd->is_fatal_error) /* out of memory creating a copy of alter_info */
       {
-        end_DDL();
+        DDL_blocker->end_DDL();
         goto error;
       }
       /*
@@ -2386,7 +2388,7 @@ end_with_restore_list:
 				   (TABLE_LIST *)
 				   create_info.merge_list.first))
       {
-        end_DDL();
+        DDL_blocker->end_DDL();
 	goto error;				/* purecov: inspected */
       }
       if (check_grant(thd, priv_needed, all_tables, 0, UINT_MAX, 0))
@@ -2401,7 +2403,7 @@ end_with_restore_list:
           if (check_grant(thd, INSERT_ACL | CREATE_ACL, &tmp_table, 0,
               UINT_MAX, 0))
           {
-            end_DDL();
+            DDL_blocker->end_DDL();
             goto error;
           }
       }
@@ -2422,7 +2424,7 @@ end_with_restore_list:
           !(need_start_waiting= !wait_if_global_read_lock(thd, 0, 1)))
       {
         res= 1;
-        end_DDL();
+        DDL_blocker->end_DDL();
         break;
       }
 
@@ -2434,7 +2436,7 @@ end_with_restore_list:
                              select_lex->order_list.elements,
                              (ORDER *) select_lex->order_list.first,
                              lex->ignore);
-      end_DDL();
+      DDL_blocker->end_DDL();
       break;
     }
   case SQLCOM_RENAME_TABLE:
@@ -2463,13 +2465,13 @@ end_with_restore_list:
         goto error;
     }
 
-      check_DDL_blocker(thd);
+      DDL_blocker->check_DDL_blocker(thd);
     if (end_active_trans(thd) || mysql_rename_tables(thd, first_table, 0))
       {
-        end_DDL();
+        DDL_blocker->end_DDL();
         goto error;
       }
-      end_DDL();
+      DDL_blocker->end_DDL();
     break;
   }
 #ifndef EMBEDDED_LIBRARY
@@ -2519,9 +2521,9 @@ end_with_restore_list:
     if (check_table_access(thd, SELECT_ACL | INSERT_ACL, all_tables, 0))
       goto error; /* purecov: inspected */
     thd->enable_slow_log= opt_log_slow_admin_statements;
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= mysql_repair_table(thd, first_table, &lex->check_opt);
-    end_DDL();
+    DDL_blocker->end_DDL();
     /* ! we write after unlocking the table */
     if (!res && !lex->no_write_to_binlog)
     {
@@ -2571,11 +2573,11 @@ end_with_restore_list:
     if (check_table_access(thd, SELECT_ACL | INSERT_ACL, all_tables, 0))
       goto error; /* purecov: inspected */
     thd->enable_slow_log= opt_log_slow_admin_statements;
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= (specialflag & (SPECIAL_SAFE_MODE | SPECIAL_NO_NEW_FUNC)) ?
       mysql_recreate_table(thd, first_table) :
       mysql_optimize_table(thd, first_table, &lex->check_opt);
-    end_DDL();
+    DDL_blocker->end_DDL();
     /* ! we write after unlocking the table */
     if (!res && !lex->no_write_to_binlog)
     {
@@ -2818,9 +2820,9 @@ end_with_restore_list:
       goto error;
     }
 
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= mysql_truncate(thd, first_table, 0);
-    end_DDL();
+    DDL_blocker->end_DDL();
 
     break;
   case SQLCOM_DELETE:
@@ -2927,11 +2929,11 @@ end_with_restore_list:
       /* So that DROP TEMPORARY TABLE gets to binlog at commit/rollback */
       thd->options|= OPTION_KEEP_LOG;
     }
-      check_DDL_blocker(thd);
+      DDL_blocker->check_DDL_blocker(thd);
     /* DDL and binlog write order protected by LOCK_open */
     res= mysql_rm_table(thd, first_table, lex->drop_if_exists,
 			lex->drop_temporary);
-      end_DDL();
+      DDL_blocker->end_DDL();
   }
   break;
   case SQLCOM_SHOW_PROCESSLIST:
@@ -3162,10 +3164,10 @@ end_with_restore_list:
     if (check_access(thd,CREATE_ACL,lex->name.str, 0, 1, 0,
                      is_schema_db(lex->name.str)))
       break;
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= mysql_create_db(thd,(lower_case_table_names == 2 ? alias :
                               lex->name.str), &create_info, 0);
-    end_DDL();
+    DDL_blocker->end_DDL();
     break;
   }
   case SQLCOM_DROP_DB:
@@ -3205,9 +3207,9 @@ end_with_restore_list:
                  ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
       goto error;
     }
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= mysql_rm_db(thd, lex->name.str, lex->drop_if_exists, 0);
-    end_DDL();
+    DDL_blocker->end_DDL();
     break;
   }
   case SQLCOM_ALTER_DB_UPGRADE:
@@ -3248,9 +3250,9 @@ end_with_restore_list:
       goto error;
     }
 
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= mysql_upgrade_db(thd, db);
-    end_DDL();
+    DDL_blocker->end_DDL();
     if (!res)
       send_ok(thd);
     break;
@@ -3288,9 +3290,9 @@ end_with_restore_list:
                  ER(ER_LOCK_OR_ACTIVE_TRANSACTION), MYF(0));
       goto error;
     }
-    check_DDL_blocker(thd);
+    DDL_blocker->check_DDL_blocker(thd);
     res= mysql_alter_db(thd, db->str, &create_info);
-    end_DDL();
+    DDL_blocker->end_DDL();
     break;
   }
   case SQLCOM_SHOW_CREATE_DB:

Thread
bk commit into 6.0 tree (cbell:1.2748) BUG#33024cbell11 Dec
  • Re: bk commit into 6.0 tree (cbell:1.2748) BUG#33024Rafal Somla11 Dec
    • RE: bk commit into 6.0 tree (cbell:1.2748) BUG#33024Chuck Bell11 Dec
      • Re: bk commit into 6.0 tree (cbell:1.2748) BUG#33024Rafal Somla11 Dec