List:Commits« Previous MessageNext Message »
From:antony Date:February 21 2008 2:23am
Subject:bk commit into 5.1 tree (acurtis:1.2525) BUG#34409
View as plain text  
Below is the list of changes that have just been committed into a local
5.1 repository of acurtis.  When acurtis 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, 2008-02-20 18:23:08-08:00, acurtis@stripped +6 -0
  Bug#34409
    "LOCK_plugin contention via... plugin_foreach()"
    First commit draft for comments/review.

  sql/log_event.cc@stripped, 2008-02-20 18:22:52-08:00, acurtis@stripped +4 -4
    make use of new method THD::free_mem_root()

  sql/sql_class.cc@stripped, 2008-02-20 18:22:52-08:00, acurtis@stripped +3 -1
    initialize and cleanup new property THD::cached_plugin_list

  sql/sql_class.h@stripped, 2008-02-20 18:22:52-08:00, acurtis@stripped +16 -0
    new property THD::cached_plugin_list
    new methods THD::free_mem_root() and THD::alloc_plugin_cache()

  sql/sql_parse.cc@stripped, 2008-02-20 18:22:52-08:00, acurtis@stripped +2 -2
    make use of new method THD::free_mem_root()

  sql/sql_plugin.cc@stripped, 2008-02-20 18:22:52-08:00, acurtis@stripped +54 -0
    new function plugin_unlock_cached() releases plugins stored on THD::cached_plugin_list
    implement a 'fast-path' in function plugin_foreach_with_mask() to reduce contention
    on the LOCK_plugin mutex.
    for some other operations, it may be faster to iterate cached plugins list instead of
    acquiring mutex and performing hash lookup.... perhaps try_lock may be used to detect
    contention and fallback on iterating through cached list.

  sql/sql_plugin.h@stripped, 2008-02-20 18:22:53-08:00, acurtis@stripped +1 -0
    prototype for new function plugin_unlock_cached()

diff -Nrup a/sql/log_event.cc b/sql/log_event.cc
--- a/sql/log_event.cc	2008-02-05 05:51:57 -08:00
+++ b/sql/log_event.cc	2008-02-20 18:22:52 -08:00
@@ -2554,7 +2554,7 @@ end:
   thd->first_successful_insert_id_in_prev_stmt_for_binlog= 0;
   thd->first_successful_insert_id_in_prev_stmt= 0;
   thd->stmt_depends_on_first_successful_insert_id_in_prev_stmt= 0;
-  free_root(thd->mem_root,MYF(MY_KEEP_PREALLOC));
+  thd->free_mem_root(MYF(MY_KEEP_PREALLOC));
   return thd->is_slave_error;
 }
 
@@ -3963,10 +3963,10 @@ error:
     rli->report(ERROR_LEVEL, sql_errno,"\
 Error '%s' running LOAD DATA INFILE on table '%s'. Default database: '%s'",
                     err, (char*)table_name, print_slave_db_safe(remember_db));
-    free_root(thd->mem_root,MYF(MY_KEEP_PREALLOC));
+    thd->free_mem_root(MYF(MY_KEEP_PREALLOC));
     return 1;
   }
-  free_root(thd->mem_root,MYF(MY_KEEP_PREALLOC));
+  thd->free_mem_root(MYF(MY_KEEP_PREALLOC));
 
   if (thd->is_fatal_error)
   {
@@ -4888,7 +4888,7 @@ int User_var_log_event::do_apply_event(R
     a column value, it could always have IMPLICIT derivation.
    */
   e.update_hash(val, val_len, type, charset, DERIVATION_IMPLICIT, 0);
-  free_root(thd->mem_root,0);
+  thd->free_mem_root(0);
 
   return 0;
 }
diff -Nrup a/sql/sql_class.cc b/sql/sql_class.cc
--- a/sql/sql_class.cc	2008-02-12 09:21:07 -08:00
+++ b/sql/sql_class.cc	2008-02-20 18:22:52 -08:00
@@ -500,7 +500,8 @@ THD::THD()
    bootstrap(0),
    derived_tables_processing(FALSE),
    spcont(NULL),
-   m_lip(NULL)
+   m_lip(NULL),
+   cached_plugin_list(NULL)
 {
   ulong tmp;
 
@@ -876,6 +877,7 @@ THD::~THD()
   }
 #endif
 
+  plugin_unlock_cached(this);
   free_root(&main_mem_root, MYF(0));
   DBUG_VOID_RETURN;
 }
diff -Nrup a/sql/sql_class.h b/sql/sql_class.h
--- a/sql/sql_class.h	2008-01-31 07:31:51 -08:00
+++ b/sql/sql_class.h	2008-02-20 18:22:52 -08:00
@@ -1693,6 +1693,8 @@ public:
   partition_info *work_part_info;
 #endif
 
+  plugin_ref *cached_plugin_list;
+
   THD();
   ~THD();
 
@@ -2107,6 +2109,20 @@ private:
     tree itself is reused between executions and thus is stored elsewhere.
   */
   MEM_ROOT main_mem_root;
+public:
+  void free_mem_root(myf MyFLAGS)
+  {
+    if (mem_root == &main_mem_root)
+      plugin_unlock_cached(this);
+    free_root(mem_root, MyFLAGS);
+  }
+  plugin_ref *alloc_plugin_cache(uint size)
+  {
+    DBUG_ASSERT(!cached_plugin_list);
+    return (cached_plugin_list= (plugin_ref*)
+                                alloc_root(&main_mem_root,
+                                           (size + 1) * sizeof(plugin_ref)));
+  }
 };
 
 
diff -Nrup a/sql/sql_parse.cc b/sql/sql_parse.cc
--- a/sql/sql_parse.cc	2008-02-14 07:52:59 -08:00
+++ b/sql/sql_parse.cc	2008-02-20 18:22:52 -08:00
@@ -446,7 +446,7 @@ pthread_handler_t handle_bootstrap(void 
     if (bootstrap_error)
       break;
 
-    free_root(thd->mem_root,MYF(MY_KEEP_PREALLOC));
+    thd->free_mem_root(MYF(MY_KEEP_PREALLOC));
 #ifdef USING_TRANSACTIONS
     free_root(&thd->transaction.mem_root,MYF(MY_KEEP_PREALLOC));
 #endif
@@ -1506,7 +1506,7 @@ bool dispatch_command(enum enum_server_c
   thread_running--;
   VOID(pthread_mutex_unlock(&LOCK_thread_count));
   thd->packet.shrink(thd->variables.net_buffer_length);	// Reclaim some memory
-  free_root(thd->mem_root,MYF(MY_KEEP_PREALLOC));
+  thd->free_mem_root(MYF(MY_KEEP_PREALLOC));
   DBUG_RETURN(error);
 }
 
diff -Nrup a/sql/sql_plugin.cc b/sql/sql_plugin.cc
--- a/sql/sql_plugin.cc	2008-02-19 13:36:44 -08:00
+++ b/sql/sql_plugin.cc	2008-02-20 18:22:52 -08:00
@@ -989,6 +989,22 @@ void plugin_unlock_list(THD *thd, plugin
 }
 
 
+void plugin_unlock_cached(THD *thd)
+{
+  plugin_ref *list= thd->cached_plugin_list;
+  DBUG_ENTER("plugin_unlock_cached");
+  thd->cached_plugin_list= NULL;
+  if (!list || !*list)
+    DBUG_VOID_RETURN;
+  pthread_mutex_lock(&LOCK_plugin);
+  while (*list)
+    intern_plugin_unlock(NULL, *list++);
+  reap_plugins();
+  pthread_mutex_unlock(&LOCK_plugin);
+  DBUG_VOID_RETURN;
+}
+
+
 static int plugin_initialize(struct st_plugin_int *plugin)
 {
   DBUG_ENTER("plugin_initialize");
@@ -1758,6 +1774,44 @@ bool plugin_foreach_with_mask(THD *thd, 
     DBUG_RETURN(FALSE);
 
   state_mask= ~state_mask; // do it only once
+
+  if (likely(thd && state_mask == ~(uint) PLUGIN_IS_READY))
+  {
+    plugin_ref *list;
+
+    if (unlikely(!thd->cached_plugin_list))
+    {    
+      pthread_mutex_lock(&LOCK_plugin);
+      total= plugin_array.elements;
+      if ((list= thd->alloc_plugin_cache(total)))
+      {
+        for (idx= 0; idx < total; idx++)
+        {
+          if ((*list= my_intern_plugin_lock(NULL, plugin_int_to_ref(
+               *dynamic_element(&plugin_array, idx, struct st_plugin_int **)))))
+            list++;
+        }
+        *list= 0;
+      }
+      pthread_mutex_unlock(&LOCK_plugin);
+    }
+
+    if (likely(thd->cached_plugin_list != 0))
+    {
+      for (list= thd->cached_plugin_list; *list; list++)
+      {
+        if (plugin_state(*list) & state_mask)
+          continue;
+
+        if (type != MYSQL_ANY_PLUGIN && type != plugin_decl(*list)->type)
+          continue;
+        
+        if (func(thd, *list, arg))
+          DBUG_RETURN(TRUE);
+      }
+      DBUG_RETURN(FALSE);
+    }
+  }
 
   pthread_mutex_lock(&LOCK_plugin);
   total= type == MYSQL_ANY_PLUGIN ? plugin_array.elements
diff -Nrup a/sql/sql_plugin.h b/sql/sql_plugin.h
--- a/sql/sql_plugin.h	2007-06-12 08:41:54 -07:00
+++ b/sql/sql_plugin.h	2008-02-20 18:22:53 -08:00
@@ -123,6 +123,7 @@ extern plugin_ref plugin_lock_by_name(TH
                                       int type CALLER_INFO_PROTO);
 extern void plugin_unlock(THD *thd, plugin_ref plugin);
 extern void plugin_unlock_list(THD *thd, plugin_ref *list, uint count);
+extern void plugin_unlock_cached(THD *thd);
 extern bool mysql_install_plugin(THD *thd, const LEX_STRING *name,
                                  const LEX_STRING *dl);
 extern bool mysql_uninstall_plugin(THD *thd, const LEX_STRING *name);
Thread
bk commit into 5.1 tree (acurtis:1.2525) BUG#34409antony21 Feb
  • Re: bk commit into 5.1 tree (acurtis:1.2525) BUG#34409Sergei Golubchik22 Feb