List:Commits« Previous MessageNext Message »
From:ahmad.abdullateef Date:December 18 2012 4:54pm
Subject:bzr push into mysql-5.5 branch (ahmad.abdullateef:4118 to 4119) Bug#14727815
View as plain text  
 4119 Ahmad Abdullateef	2012-12-18 [merge]
      BUG#14727815 - CRASH IN PTHREAD_RWLOCK_WRLOCK/SRW_UNLOCK
                                   IN QUERY CACHE CODE
      
      DESCRIPTION:
      MySQL Server crashes sporadically when Query Caching is on and
      the server has high contention among clients. 
      
      
      ANALYSIS :
      
      Scenario 1:
      In Query_cache::move_by_type() when handling RESULT or its related blocks,
      Write Lock is acquired on its parent Query block. However the next and prev
      pointers are cached in local variables before lock acquisition. In an extremely
      high contention scenario there exists a possibility that
      Query_cache::append_result_data() is operating on the same query block
      and as a consequence might append a new Result block to the end of Result
      blocks Linked List of the Query. This would manipulate the next, prev pointers
      of the Block being processed in move_by_type(), however the local pointers
      still point to previous nodes there by causing Data Corruption leading to crash.
      
      Scenario 2:
      In Windows SDK "BOOL" is typedefed as "int" and BOOLEAN is typedefed as
      "usigned char". The function pointer definition "srw_bool_func" mistakenly uses 
      BOOL instead of BOOLEAN thereby virtually making the function 
      my_TryAcquireSRWLockExclusive() always succeed because only the LSB of EAX
      has the actual result of the call, however due to type mismatch all bytes of EAX
      are used for evaluation. Again during high contention scenarios in 
      Query_cache::free_old_query() calls try_lock_writing() on a Query, this call 
      always succeeds and the query is freed, even though it is used by some other
      thread, in this case Query_cache::send_result_to_client() was using it and the
      code causes a crash because it accessed free or reallocated memory.
      
      FIX :
      
      Scenario 1:
      The next, prev pointers are now accessed only after Lock acquisition in 
      Query_cache::move_by_type().
      
      Scenario 2:
      In the definition of "srw_bool_func" BOOL has been replaced with "BOOLEAN"

    modified:
      mysys/thr_rwlock.c
      sql/sql_cache.cc
 4118 Vasil Dimov	2012-12-18 [merge]
      Merge mysql-5.1 -> mysql-5.5

    modified:
      storage/innobase/include/univ.i
=== modified file 'mysys/thr_rwlock.c'
--- a/mysys/thr_rwlock.c	2011-06-30 15:46:53 +0000
+++ b/mysys/thr_rwlock.c	2012-12-18 16:46:12 +0000
@@ -24,7 +24,7 @@
 static BOOL have_srwlock= FALSE;
 /* Prototypes and function pointers for windows  functions */
 typedef VOID (WINAPI* srw_func) (PSRWLOCK SRWLock);
-typedef BOOL (WINAPI* srw_bool_func) (PSRWLOCK SRWLock);
+typedef BOOLEAN (WINAPI* srw_bool_func) (PSRWLOCK SRWLock);
 
 static srw_func my_InitializeSRWLock;
 static srw_func my_AcquireSRWLockExclusive;

=== modified file 'sql/sql_cache.cc'
--- a/sql/sql_cache.cc	2012-12-11 18:04:30 +0000
+++ b/sql/sql_cache.cc	2012-12-18 16:46:12 +0000
@@ -3967,15 +3967,14 @@ my_bool Query_cache::move_by_type(uchar 
   case Query_cache_block::RES_CONT:
   case Query_cache_block::RESULT:
   {
-    DBUG_PRINT("qcache", ("block 0x%lx RES* (%d)", (ulong) block,
-			(int) block->type));
-    if (*border == 0)
-      break;
-    Query_cache_block *query_block = block->result()->parent(),
-		      *next = block->next,
-		      *prev = block->prev;
-    Query_cache_block::block_type type = block->type;
-    BLOCK_LOCK_WR(query_block);
+    DBUG_PRINT("qcache", ("block 0x%lx RES* (%d)", (ulong) block,
+               (int) block->type));
+    if (*border == 0)
+      break;
+    Query_cache_block *query_block= block->result()->parent();
+    BLOCK_LOCK_WR(query_block);
+    Query_cache_block *next= block->next, *prev= block->prev;
+    Query_cache_block::block_type type= block->type;
     ulong len = block->length, used = block->used;
     Query_cache_block *pprev = block->pprev,
 		      *pnext = block->pnext,

No bundle (reason: useless for push emails).
Thread
bzr push into mysql-5.5 branch (ahmad.abdullateef:4118 to 4119) Bug#14727815ahmad.abdullateef19 Dec