force flush when there are pending ops on the memtable executor even when none have finished yet. this fixes test case intermittent failures. patch by jbellis; reviewed by Eric Evans for CASSANDRA-141

git-svn-id: https://svn.apache.org/repos/asf/incubator/cassandra/trunk@772361 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Jonathan Ellis 2009-05-06 17:04:32 +00:00
parent 3ed4e051b8
commit 65f66e982d
3 changed files with 18 additions and 3 deletions

View File

@ -437,7 +437,8 @@ public class ColumnFamilyStore implements ColumnFamilyStoreMBean
void forceBlockingFlush() throws IOException, ExecutionException, InterruptedException void forceBlockingFlush() throws IOException, ExecutionException, InterruptedException
{ {
forceFlush(); Memtable oldMemtable = memtable_.get();
oldMemtable.forceflush();
// block for flush to finish by adding a no-op action to the flush executorservice // block for flush to finish by adding a no-op action to the flush executorservice
// and waiting for that to finish. (this works since flush ES is single-threaded.) // and waiting for that to finish. (this works since flush ES is single-threaded.)
Future f = MemtableManager.instance().flusher_.submit(new Runnable() Future f = MemtableManager.instance().flusher_.submit(new Runnable()
@ -447,6 +448,7 @@ public class ColumnFamilyStore implements ColumnFamilyStoreMBean
} }
}); });
f.get(); f.get();
assert oldMemtable.isFlushed() || oldMemtable.isClean();
} }
void forceFlushBinary() void forceFlushBinary()

View File

@ -56,7 +56,8 @@ public class Memtable implements Comparable<Memtable>
} }
private MemtableThreadPoolExecutor executor_; private MemtableThreadPoolExecutor executor_;
private boolean isFrozen_; private volatile boolean isFrozen_;
private volatile boolean isFlushed_; // for tests, in particular forceBlockingFlush asserts this
private int threshold_ = DatabaseDescriptor.getMemtableSize()*1024*1024; private int threshold_ = DatabaseDescriptor.getMemtableSize()*1024*1024;
private int thresholdCount_ = (int)(DatabaseDescriptor.getMemtableObjectCount()*1024*1024); private int thresholdCount_ = (int)(DatabaseDescriptor.getMemtableObjectCount()*1024*1024);
@ -81,6 +82,11 @@ public class Memtable implements Comparable<Memtable>
runningExecutorServices_.add(executor_); runningExecutorServices_.add(executor_);
} }
public boolean isFlushed()
{
return isFlushed_;
}
class Putter implements Runnable class Putter implements Runnable
{ {
private String key_; private String key_;
@ -203,7 +209,7 @@ public class Memtable implements Comparable<Memtable>
*/ */
public void forceflush() public void forceflush()
{ {
if (columnFamilies_.isEmpty()) if (isClean())
return; return;
try try
@ -355,6 +361,7 @@ public class Memtable implements Comparable<Memtable>
cfStore.onMemtableFlush(cLogCtx); cfStore.onMemtableFlush(cLogCtx);
cfStore.storeLocation( ssTable.getDataFileLocation(), bf ); cfStore.storeLocation( ssTable.getDataFileLocation(), bf );
buffer.close(); buffer.close();
isFlushed_ = true;
} }
private class MemtableThreadPoolExecutor extends DebuggableThreadPoolExecutor private class MemtableThreadPoolExecutor extends DebuggableThreadPoolExecutor
@ -401,4 +408,9 @@ public class Memtable implements Comparable<Memtable>
pq.addAll(keys); pq.addAll(keys);
return new DestructivePQIterator<String>(pq); return new DestructivePQIterator<String>(pq);
} }
public boolean isClean()
{
return columnFamilies_.isEmpty() && executor_.getPendingTasks() == 0;
}
} }

View File

@ -257,6 +257,7 @@ public class ColumnFamilyStoreTest extends ServerTest
rm.apply(); rm.apply();
List<ColumnFamily> families = store.getColumnFamilies("key1", "Super1", new IdentityFilter()); List<ColumnFamily> families = store.getColumnFamilies("key1", "Super1", new IdentityFilter());
assert families.size() == 2 : StringUtils.join(families, ", ");
assert families.get(0).getAllColumns().first().getMarkedForDeleteAt() == 1; // delete marker, just added assert families.get(0).getAllColumns().first().getMarkedForDeleteAt() == 1; // delete marker, just added
assert !families.get(1).getAllColumns().first().isMarkedForDelete(); // flushed old version assert !families.get(1).getAllColumns().first().isMarkedForDelete(); // flushed old version
ColumnFamily resolved = ColumnFamily.resolve(families); ColumnFamily resolved = ColumnFamily.resolve(families);