List:Commits« Previous MessageNext Message »
From:cpowers Date:April 10 2008 7:32am
Subject:bk commit into 6.0 tree (cpowers:1.2637) BUG#35692
View as plain text  
Below is the list of changes that have just been committed into a local
6.0 repository of cpowers.  When cpowers 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-04-10 00:32:33-05:00, cpowers@stripped +2 -0
  Bug#35692, "Running falcon_record_cache_memory_leak2-big crashes Falcon"
  
  Removed deadlock. Table::rollbackRecord() locked syncPrior(Shared) before
  calling Table::insert(), but Table::insert() locks Table::syncObject. The
  Table lock must always be taken before the prior record version lock. 
  
  Now Table::rollbackRecord() holds syncPrior(Shared) just long enough to
  get the prior record and addRef, and unlocks syncPrior before calling ::insert().
  
  RecordVersion::scavenge(): Loop through prior versions with shared lock. Change
  prior version linkage under exclusive lock.

  storage/falcon/RecordVersion.cpp@stripped, 2008-04-10 00:32:31-05:00, cpowers@stripped
+5 -1
    Use syncPrior(Shared) to find prior version. Use exclusive to setPriorVersion().

  storage/falcon/Table.cpp@stripped, 2008-04-10 00:32:31-05:00, cpowers@stripped +19 -9
    Table::rollbackRecord: Hold syncPrior(Shared) long enough to get the prior
    version and addref. Unlock before calling insert.

diff -Nrup a/storage/falcon/RecordVersion.cpp b/storage/falcon/RecordVersion.cpp
--- a/storage/falcon/RecordVersion.cpp	2008-04-09 09:51:53 -05:00
+++ b/storage/falcon/RecordVersion.cpp	2008-04-10 00:32:31 -05:00
@@ -239,7 +239,7 @@ void RecordVersion::scavenge(TransId tar
 		return;
 
 	Sync syncPrior(getSyncPrior(), "RecordVersion::scavenge(2)");
-	syncPrior.lock(Exclusive);
+	syncPrior.lock(Shared);
 	
 	Record *rec = priorVersion;
 	Record *ptr = NULL;
@@ -268,6 +268,10 @@ void RecordVersion::scavenge(TransId tar
 	
 	Record *prior = priorVersion;
 	prior->addRef();
+
+	syncPrior.unlock();
+	syncPrior.lock(Exclusive);
+	
 	setPriorVersion(rec);
 	//ptr->setPriorVersion(NULL);
 	ptr->state = recEndChain;
diff -Nrup a/storage/falcon/Table.cpp b/storage/falcon/Table.cpp
--- a/storage/falcon/Table.cpp	2008-04-09 15:48:57 -05:00
+++ b/storage/falcon/Table.cpp	2008-04-10 00:32:31 -05:00
@@ -963,12 +963,6 @@ Record* Table::backlogFetch(int32 record
 
 Record* Table::rollbackRecord(RecordVersion * recordToRollback, Transaction *transaction)
 {
-	Sync syncPrior(getSyncPrior(recordToRollback), "Table::rollbackRecord");
-	
-	//cwp tbd: Problem if systemConnection->rollback() and table deleted
-	if (!transaction->systemTransaction)
-		syncPrior.lock(Shared);
-
 #ifdef CHECK_RECORD_ACTIVITY
 	recordToRollback->active = false;
 #endif
@@ -976,12 +970,25 @@ Record* Table::rollbackRecord(RecordVers
 	int priorState = recordToRollback->state;
 	recordToRollback->state = recRollback;
 
-	// Find the record that will become the current version.
+	// Hold syncPrior long enough to get prior version and addRef. Unlock before insert().
+	
+	Sync syncPrior(getSyncPrior(recordToRollback), "Table::rollbackRecord");
+
+	if (!transaction->systemTransaction)
+		syncPrior.lock(Shared);
 
+	// Find the record that will become the current version.
+	
 	Record *priorRecord = recordToRollback->getPriorVersion();
 
 	if (priorRecord)
+		{
+		priorRecord->addRef();
 		priorRecord->setSuperceded(false);
+		}
+	
+	if (!transaction->systemTransaction)
+		syncPrior.unlock();
 
 	// Replace the current version of this record.
 
@@ -1002,6 +1009,9 @@ Record* Table::rollbackRecord(RecordVers
 
 	if (backloggedRecords)
 		deleteRecordBacklog(recordToRollback->recordNumber);
+	
+	if (priorRecord)
+		priorRecord->release();
 			
 	return priorRecord;
 }
@@ -3262,8 +3272,8 @@ void Table::validateAndInsert(Transactio
 		if (prior)
 			{
 			syncTable.lock(Exclusive);
-			syncPrior.lock(Shared);
 			Record *current = fetch(record->recordNumber);
+			syncPrior.lock(Shared);
 
 			if (current)
 				{
@@ -3282,8 +3292,8 @@ void Table::validateAndInsert(Transactio
 
 					if (transaction->waitForTransaction(transId))
 						{
-						syncPrior.lock(Shared);
 						current = fetch(record->recordNumber);
+						syncPrior.lock(Shared);
 						
 						if (current == prior)
 							current->release();
Thread
bk commit into 6.0 tree (cpowers:1.2637) BUG#35692cpowers10 Apr