Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTree.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTree.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTree.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTree.java
Mon Feb 10 15:35:18 2014
@@ -24,8 +24,8 @@ import java.io.Closeable;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.FileChannel;
-import java.util.Map;
import java.util.concurrent.ConcurrentLinkedQueue;
+import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.locks.ReentrantLock;
import net.sf.ehcache.Cache;
@@ -45,15 +45,15 @@ import org.slf4j.LoggerFactory;
*
* @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
*/
-public class PersistedBTree<K, V> extends AbstractBTree<K, V> implements Closeable
+public class PersistedBTree<K, V> extends AbstractBTree<K, V> implements TransactionManager,
Closeable
{
/** The LoggerFactory used by this class */
protected static final Logger LOG = LoggerFactory.getLogger( PersistedBTree.class );
- /** The RecordManager if the BTree is managed */
+ /** The RecordManager if the B-tree is managed */
private RecordManager recordManager;
- /** The cache associated with this BTree */
+ /** The cache associated with this B-tree */
protected Cache cache;
/** The default number of pages to keep in memory */
@@ -62,35 +62,33 @@ public class PersistedBTree<K, V> extend
/** The cache size, default to 1000 elements */
protected int cacheSize = DEFAULT_CACHE_SIZE;
- /** A flag indicating if this BTree is a Sub BTree */
- private boolean isSubBtree = false;
-
- /** The number of stored Values before we switch to a BTree */
+ /** The number of stored Values before we switch to a B-tree */
private static final int DEFAULT_VALUE_THRESHOLD_UP = 8;
/** The number of stored Values before we switch back to an array */
private static final int DEFAULT_VALUE_THRESHOLD_LOW = 1;
- /** The configuration for the array <-> BTree switch */
+ /** The configuration for the array <-> B-tree switch */
/*No qualifier*/static int valueThresholdUp = DEFAULT_VALUE_THRESHOLD_UP;
/*No qualifier*/static int valueThresholdLow = DEFAULT_VALUE_THRESHOLD_LOW;
/** A lock to protect the creation of the transaction */
- protected ReentrantLock createTransaction = new ReentrantLock();
+ private ReentrantLock createTransaction = new ReentrantLock();
+ /** A flag set when we initiate an automatic transaction */
+ private AtomicBoolean automaticTransaction = new AtomicBoolean( true );
/**
* Creates a new BTree, with no initialization.
*/
/* no qualifier */PersistedBTree()
{
- btreeHeader = new BTreeHeader();
setType( BTreeTypeEnum.PERSISTED );
}
/**
- * Creates a new persisted BTree using the BTreeConfiguration to initialize the
+ * Creates a new persisted B-tree using the BTreeConfiguration to initialize the
* BTree
*
* @param configuration The configuration to use
@@ -105,22 +103,17 @@ public class PersistedBTree<K, V> extend
throw new IllegalArgumentException( "BTree name cannot be null" );
}
- btreeHeader = new BTreeHeader();
- btreeHeader.setName( name );
- btreeHeader.setPageSize( configuration.getPageSize() );
- isSubBtree = configuration.isSubBtree();
-
- keySerializer = configuration.getKeySerializer();
- btreeHeader.setKeySerializerFQCN( keySerializer.getClass().getName() );
-
- valueSerializer = configuration.getValueSerializer();
- btreeHeader.setValueSerializerFQCN( valueSerializer.getClass().getName() );
+ BTreeHeader<K, V> btreeHeader = getBtreeHeader();
+ setName( name );
+ setPageSize( configuration.getPageSize() );
+ setKeySerializer( configuration.getKeySerializer() );
+ setValueSerializer( configuration.getValueSerializer() );
+ setAllowDuplicates( configuration.isAllowDuplicates() );
+ setType( configuration.getBtreeType() );
readTimeOut = configuration.getReadTimeOut();
writeBufferSize = configuration.getWriteBufferSize();
- btreeHeader.setAllowDuplicates( configuration.isAllowDuplicates() );
cacheSize = configuration.getCacheSize();
- setType( BTreeTypeEnum.PERSISTED );
if ( keySerializer.getComparator() == null )
{
@@ -129,13 +122,14 @@ public class PersistedBTree<K, V> extend
// Create the first root page, with revision 0L. It will be empty
// and increment the revision at the same time
- rootPage = new PersistedLeaf<K, V>( this );
+ // Create the first root page, with revision 0L. It will be empty
+ // and increment the revision at the same time
+ btreeHeader.setRootPage( new PersistedLeaf<K, V>( this ) );
- if ( isSubBtree )
+ if ( btreeType == BTreeTypeEnum.PERSISTED_SUB )
{
// The subBTree inherit its cache from its parent BTree
this.cache = ( ( PersistedBTree<K, V> ) configuration.getParentBTree()
).getCache();
- this.writeLock = ( ( PersistedBTree<K, V> ) configuration.getParentBTree()
).getWriteLock();
readTransactions = new ConcurrentLinkedQueue<ReadTransaction<K, V>>();
}
@@ -151,15 +145,13 @@ public class PersistedBTree<K, V> extend
*/
public void init()
{
- if ( !isSubBtree )
+ if ( btreeType != BTreeTypeEnum.PERSISTED_SUB )
{
// This is not a subBtree, we have to initialize the cache
// Create the queue containing the pending read transactions
readTransactions = new ConcurrentLinkedQueue<ReadTransaction<K, V>>();
- writeLock = new ReentrantLock();
-
// Initialize the caches
CacheConfiguration cacheConfiguration = new CacheConfiguration();
cacheConfiguration.setName( "pages" );
@@ -191,15 +183,6 @@ public class PersistedBTree<K, V> extend
/**
* Return the cache we use in this BTree
*/
- /* No qualifier */ReentrantLock getWriteLock()
- {
- return writeLock;
- }
-
-
- /**
- * Return the cache we use in this BTree
- */
/* No qualifier */ConcurrentLinkedQueue<ReadTransaction<K, V>> getReadTransactions()
{
return readTransactions;
@@ -222,8 +205,6 @@ public class PersistedBTree<K, V> extend
}
cache.dispose();
-
- rootPage = null;
}
@@ -232,7 +213,7 @@ public class PersistedBTree<K, V> extend
*/
/* No qualifier*/long getBtreeOffset()
{
- return btreeHeader.getBTreeOffset();
+ return getBtreeHeader().getBTreeOffset();
}
@@ -241,7 +222,7 @@ public class PersistedBTree<K, V> extend
*/
/* No qualifier*/void setBtreeOffset( long btreeOffset )
{
- btreeHeader.setBTreeOffset( btreeOffset );
+ getBtreeHeader().setBTreeOffset( btreeOffset );
}
@@ -250,7 +231,7 @@ public class PersistedBTree<K, V> extend
*/
/* No qualifier*/long getRootPageOffset()
{
- return btreeHeader.getRootPageOffset();
+ return getBtreeHeader().getRootPageOffset();
}
@@ -259,32 +240,14 @@ public class PersistedBTree<K, V> extend
*/
/* No qualifier*/void setRootPageOffset( long rootPageOffset )
{
- btreeHeader.setRootPageOffset( rootPageOffset );
- }
-
-
- /**
- * @return the nextBTreeOffset
- */
- /* No qualifier*/long getNextBTreeOffset()
- {
- return btreeHeader.getNextBTreeOffset();
- }
-
-
- /**
- * @param nextBTreeOffset the nextBTreeOffset to set
- */
- /* No qualifier*/void setNextBTreeOffset( long nextBTreeOffset )
- {
- btreeHeader.setNextBTreeOffset( nextBTreeOffset );
+ getBtreeHeader().setRootPageOffset( rootPageOffset );
}
/**
* Gets the RecordManager for a managed BTree
*
- * @return The recordManager if the BTree is managed
+ * @return The recordManager if the B-tree is managed
*/
/* No qualifier */RecordManager getRecordManager()
{
@@ -315,81 +278,119 @@ public class PersistedBTree<K, V> extend
* @return
* @throws IOException
*/
- protected Tuple<K, V> delete( K key, V value, long revision ) throws IOException
+ /* no qualifier */ Tuple<K, V> delete( K key, V value, long revision ) throws IOException
{
- writeLock.lock();
+ boolean inTransaction = recordManager.isTransactionStarted();
- try
+ if ( !inTransaction )
{
- // If the key exists, the existing value will be replaced. We store it
- // to return it to the caller.
- Tuple<K, V> tuple = null;
+ recordManager.beginTransaction();
+ }
- // Try to delete the entry starting from the root page. Here, the root
- // page may be either a Node or a Leaf
- DeleteResult<K, V> result = rootPage.delete( revision, key, value, null,
-1 );
+ // Try to delete the entry starting from the root page. Here, the root
+ // page may be either a Node or a Leaf
+ DeleteResult<K, V> result = processDelete( key, value, revision );
- if ( result instanceof NotPresentResult )
+ // Check that we have found the element to delete
+ if ( result instanceof NotPresentResult )
+ {
+ // We haven't found the element in the B-tree, just get out
+ if ( !inTransaction )
{
- // Key not found.
- return null;
+ recordManager.commit();
}
- // Keep the oldRootPage so that we can later access it
- Page<K, V> oldRootPage = rootPage;
+ return null;
+ }
- if ( result instanceof RemoveResult )
- {
- // The element was found, and removed
- RemoveResult<K, V> removeResult = ( RemoveResult<K, V> ) result;
+ // The element was found, and removed
+ AbstractDeleteResult<K, V> deleteResult = ( AbstractDeleteResult<K, V>
) result;
- Page<K, V> modifiedPage = removeResult.getModifiedPage();
+ Tuple<K, V> tuple = deleteResult.getRemovedElement();
- // Write the modified page on disk
- // Note that we don't use the holder, the new root page will
- // remain in memory.
- PageHolder<K, V> holder = writePage( modifiedPage, revision );
-
- // Store the offset on disk in the page in memory
- ( ( AbstractPage<K, V> ) modifiedPage ).setOffset( ( ( PersistedPageHolder<K,
V> ) holder )
- .getOffset() );
-
- // Store the last offset on disk in the page in memory
- ( ( AbstractPage<K, V> ) modifiedPage )
- .setLastOffset( ( ( PersistedPageHolder<K, V> ) holder )
- .getLastOffset() );
-
- // This is a new root
- rootPage = modifiedPage;
- tuple = removeResult.getRemovedElement();
- }
+ // Update the B-tree header, creating a new BtreeHeader page now
+ long newBtreeHeaderOffset = recordManager.updateBtreeHeader( this, ( ( AbstractPage<K,
V> ) getRootPage() ).getOffset() );
- // Decrease the number of elements in the current tree if the deletion is successful
- if ( tuple != null )
- {
- btreeHeader.decrementNbElems();
+ // Update the B-tree of B-trees with this new offset, if we are not already doing
so
+ switch ( btreeType )
+ {
+ case PERSISTED :
+ // We have a new B-tree header to inject into the B-tree of btrees
+ recordManager.addInBtreeOfBtrees( getName(), revision, newBtreeHeaderOffset
);
+ break;
- // We have to update the rootPage on disk
- // Update the BTree header now
- recordManager.updateBtreeHeader( this, ( ( AbstractPage<K, V> ) rootPage
).getOffset() );
- }
+ case PERSISTED_MANAGEMENT :
+ // The B-tree of B-trees or the copiedPages B-tree has been updated, update
the RMheader parameters
+ getBtreeHeader().setBTreeOffset( newBtreeHeaderOffset );
- recordManager.addFreePages( this, result.getCopiedPages() );
+ break;
- // Update the RecordManager header
- recordManager.updateRecordManagerHeader();
+ default:
+ // Nothing to do for sub-btrees
+ break;
+ }
- // Store the created rootPage into the revision BTree, this will be stored in
RecordManager only if revisions are set to keep
- recordManager.storeRootPage( this, rootPage );
+ // We can safely free the copied pages
+ recordManager.freePages( this, revision, result.getCopiedPages() );
- // Return the value we have found if it was modified
- return tuple;
+ // If the B-tree is managed, we have to update the rootPage on disk
+ // Update the RecordManager header
+ if ( !inTransaction )
+ {
+ recordManager.commit();
}
- finally
+
+ // Return the value we have found if it was modified
+ return tuple;
+ }
+
+
+ /**
+ * Insert the tuple into the B-tree rootPage, get back the new rootPage
+ */
+ private DeleteResult<K, V> processDelete( K key, V value, long revision ) throws
IOException
+ {
+ // Try to delete the entry starting from the root page. Here, the root
+ // page may be either a Node or a Leaf
+ DeleteResult<K, V> result = getRootPage().delete( key, value, revision);
+
+ if ( result instanceof NotPresentResult )
{
- // See above
- writeLock.unlock();
+ // Key not found.
+ return result;
}
+
+ // The element was found, and removed
+ AbstractDeleteResult<K, V> removeResult = ( AbstractDeleteResult<K, V>
) result;
+
+ Page<K, V> modifiedPage = removeResult.getModifiedPage();
+
+ // Write the modified page on disk
+ // Note that we don't use the holder, the new root page will
+ // remain in memory.
+ PageHolder<K, V> holder = writePage( modifiedPage, revision );
+
+ // Store the offset on disk in the page in memory
+ ( ( AbstractPage<K, V> ) modifiedPage ).setOffset( ( ( PersistedPageHolder<K,
V> ) holder )
+ .getOffset() );
+
+ // Store the last offset on disk in the page in memory
+ ( ( AbstractPage<K, V> ) modifiedPage )
+ .setLastOffset( ( ( PersistedPageHolder<K, V> ) holder )
+ .getLastOffset() );
+
+ // This is a new root
+ rootPage = modifiedPage;
+
+ // Decrease the number of elements in the current tree
+ getBtreeHeader().decrementNbElems();
+
+ // We have to update the rootPage on disk
+ // Update the B-tree header now
+ recordManager.updateBtreeHeader( this, ( ( AbstractPage<K, V> ) getBtreeHeader().getRootPage()
).getOffset() );
+
+ // Return the value we have found if it was modified
+ return result;
}
@@ -413,31 +414,87 @@ public class PersistedBTree<K, V> extend
throw new IllegalArgumentException( "Key must not be null" );
}
- // If the key exists, the existing value will be replaced. We store it
- // to return it to the caller.
- V modifiedValue = null;
+ // We have to start a new transaction, which will be committed or rollbacked
+ // locally. This will duplicate the current BtreeHeader during this phase.
+ boolean inTransaction = beginTransaction( revision );
+
+ if ( revision == -1L )
+ {
+ revision = currentRevision.get() + 1;
+ }
+
+
+ if ( !inTransaction )
+ {
+ recordManager.beginTransaction();
+ }
// Try to insert the new value in the tree at the right place,
// starting from the root page. Here, the root page may be either
// a Node or a Leaf
- InsertResult<K, V> result = rootPage.insert( revision, key, value );
+ InsertResult<K, V> result = processInsert( key, value, revision );
+
+ // Update the B-tree header, creating a new BtreeHeader page now
+ long newBtreeHeaderOffset = recordManager.updateBtreeHeader( this, ( ( AbstractPage<K,
V> ) getBtreeHeader().getRootPage() ).getOffset() );
+
+ // Update the B-tree of B-trees with this new offset, if we are not already doing
so
+ switch ( btreeType )
+ {
+ case PERSISTED :
+ // We have a new B-tree header to inject into the B-tree of btrees
+ recordManager.addInBtreeOfBtrees( getName(), revision, newBtreeHeaderOffset
);
+ break;
+
+ case PERSISTED_MANAGEMENT :
+ // The B-tree of B-trees or the copiedPages B-tree has been updated, update
the RMheader parameters
+ getBtreeHeader().setBTreeOffset( newBtreeHeaderOffset );
+
+ break;
+
+ default:
+ // Nothing to do for sub-btrees
+ break;
+ }
+
+ // We can safely free the copied pages
+ recordManager.freePages( this, revision, result.getCopiedPages() );
+
+ // If the B-tree is managed, we have to update the rootPage on disk
+ // Update the RecordManager header
+ if ( !inTransaction )
+ {
+ recordManager.commit();
+ }
+
+ // Return the value we have found if it was modified
+ return result;
+ }
+
+
+ /**
+ * Insert the tuple into the B-tree rootPage, get back the new rootPage
+ */
+ private InsertResult<K, V> processInsert( K key, V value, long revision ) throws
IOException
+ {
+ InsertResult<K, V> result = getBtreeHeader().getRootPage().insert( key, value,
revision );
+ Page<K, V> newRootPage;
if ( result instanceof ModifyResult )
{
ModifyResult<K, V> modifyResult = ( ( ModifyResult<K, V> ) result
);
- Page<K, V> modifiedPage = modifyResult.getModifiedPage();
+ newRootPage = modifyResult.getModifiedPage();
- // Write the modified page on disk
+ // Write the new root page on disk
// Note that we don't use the holder, the new root page will
// remain in memory.
- writePage( modifiedPage, revision );
-
- // The root has just been modified, we haven't split it
- // Get it and make it the current root page
- rootPage = modifiedPage;
+ writePage( newRootPage, revision );
- modifiedValue = modifyResult.getModifiedValue();
+ // Increment the counter if we have inserted a new value
+ if ( modifyResult.getModifiedValue() == null )
+ {
+ getBtreeHeader().incrementNbElems();
+ }
}
else
{
@@ -448,9 +505,8 @@ public class PersistedBTree<K, V> extend
K pivot = splitResult.getPivot();
Page<K, V> leftPage = splitResult.getLeftPage();
Page<K, V> rightPage = splitResult.getRightPage();
- Page<K, V> newRootPage = null;
- // If the BTree is managed, we have to write the two pages that were created
+ // If the B-tree is managed, we have to write the two pages that were created
// and to keep a track of the two offsets for the upper node
PageHolder<K, V> holderLeft = writePage( leftPage, revision );
@@ -459,41 +515,20 @@ public class PersistedBTree<K, V> extend
// Create the new rootPage
newRootPage = new PersistedNode<K, V>( this, revision, pivot, holderLeft,
holderRight );
- // If the BTree is managed, we now have to write the page on disk
+ // If the B-tree is managed, we now have to write the page on disk
// and to add this page to the list of modified pages
- PageHolder<K, V> holder = writePage( newRootPage, revision );
+ writePage( newRootPage, revision );
- rootPage = newRootPage;
- }
-
- // Increase the number of element in the current tree if the insertion is successful
- // and does not replace an element
- if ( modifiedValue == null )
- {
- btreeHeader.incrementNbElems();
+ // Always increment the counter : we have added a new value
+ getBtreeHeader().incrementNbElems();
}
- // If the BTree is managed, we have to update the rootPage on disk
- // Update the RecordManager header
- if ( ( writeTransaction == null ) || !writeTransaction.isStarted() )
- {
- recordManager.updateRecordManagerHeader();
-
- // Update the BTree header now
- recordManager.updateBtreeHeader( this, ( ( AbstractPage<K, V> ) rootPage
).getOffset() );
-
- // Moved the free pages into the list of free pages
- recordManager.addFreePages( this, result.getCopiedPages() );
+ // Get the new root page and make it the current root page
+ rootPage = newRootPage;
- // Store the created rootPage into the revision BTree, this will be stored in
RecordManager only if revisions are set to keep
- recordManager.storeRootPage( this, rootPage );
- }
-
- // Return the value we have found if it was modified
return result;
}
-
/**
* Write the data in the ByteBuffer, and eventually on disk if needed.
*
@@ -541,21 +576,9 @@ public class PersistedBTree<K, V> extend
*/
private PageHolder<K, V> writePage( Page<K, V> modifiedPage, long revision
) throws IOException
{
- if ( ( writeTransaction != null ) && writeTransaction.isStarted() )
- {
- Map<Page<?, ?>, BTree<?, ?>> pendingPages = recordManager.getPendingPages();
- pendingPages.put( modifiedPage, this );
-
- PageHolder<K, V> pageHolder = new PageHolder<K, V>( this, modifiedPage
);
-
- return pageHolder;
- }
- else
- {
- PageHolder<K, V> pageHolder = recordManager.writePage( this, modifiedPage,
revision );
+ PageHolder<K, V> pageHolder = recordManager.writePage( this, modifiedPage,
revision );
- return pageHolder;
- }
+ return pageHolder;
}
/**
@@ -573,59 +596,90 @@ public class PersistedBTree<K, V> extend
/**
- * Starts a transaction
+ * Get the current rootPage
+ *
+ * @return The rootPage
*/
- public void beginTransaction()
+ public Page<K, V> getRootPage()
{
- createTransaction.lock();
+ return getBtreeHeader().getRootPage();
+ }
- if ( writeTransaction == null )
- {
- writeTransaction = new WriteTransaction( recordManager );
- }
- createTransaction.unlock();
+ /* no qualifier */void setRootPage( Page<K, V> root )
+ {
+ getBtreeHeader().setRootPage( root );
+ }
- writeTransaction.start();
+
+ /**
+ * Starts a transaction
+ */
+ public void beginTransaction()
+ {
+ automaticTransaction.set( false );
+ beginTransaction( getRevision() + 1 );
}
/**
- * Commits a transaction
+ * Starts a transaction
*/
- public void commit()
+ private boolean beginTransaction( long revision )
{
createTransaction.lock();
if ( writeTransaction == null )
{
- writeTransaction = new WriteTransaction( recordManager );
+ writeTransaction = new WriteTransaction();
+ }
+
+ if ( isTransactionStarted() && !automaticTransaction.get() )
+ {
+ createTransaction.unlock();
+
+ return true;
}
createTransaction.unlock();
- writeTransaction.commit();
+ writeTransaction.start();
+
+ return false;
}
/**
- * Rollback a transaction
+ * Tells if a transaction has been started or not
*/
- public void rollback()
+ private boolean isTransactionStarted()
{
createTransaction.lock();
- if ( writeTransaction == null )
- {
- writeTransaction = new WriteTransaction( recordManager );
- }
+ boolean started = ( writeTransaction != null ) && ( writeTransaction.isStarted()
);
createTransaction.unlock();
- writeTransaction.rollback();
+ return started;
}
+ /**
+ * Commits a transaction
+ */
+ public void commit()
+ {
+ recordManager.commit();
+ }
+
+
+ /**
+ * Rollback a transaction
+ */
+ public void rollback()
+ {
+ recordManager.rollback();
+ }
/**
@@ -636,12 +690,12 @@ public class PersistedBTree<K, V> extend
StringBuilder sb = new StringBuilder();
sb.append( "Managed BTree" );
- sb.append( "[" ).append( btreeHeader.getName() ).append( "]" );
- sb.append( "( pageSize:" ).append( btreeHeader.getPageSize() );
+ sb.append( "[" ).append( getName() ).append( "]" );
+ sb.append( "( pageSize:" ).append( getPageSize() );
- if ( rootPage != null )
+ if ( getBtreeHeader().getRootPage() != null )
{
- sb.append( ", nbEntries:" ).append( btreeHeader.getNbElems() );
+ sb.append( ", nbEntries:" ).append( getBtreeHeader().getNbElems() );
}
else
{
@@ -659,10 +713,10 @@ public class PersistedBTree<K, V> extend
sb.append( keySerializer.getComparator().getClass().getSimpleName() );
}
- sb.append( ", DuplicatesAllowed: " ).append( btreeHeader.isAllowDuplicates() );
+ sb.append( ", DuplicatesAllowed: " ).append( isAllowDuplicates() );
sb.append( ") : \n" );
- sb.append( rootPage.dumpPage( "" ) );
+ sb.append( getBtreeHeader().getRootPage().dumpPage( "" ) );
return sb.toString();
}
Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeBuilder.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeBuilder.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeBuilder.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeBuilder.java
Mon Feb 10 15:35:18 2014
@@ -32,7 +32,7 @@ import org.apache.directory.mavibot.btre
/**
- * A BTree builder that builds a tree from the bottom.
+ * A B-tree builder that builds a tree from the bottom.
*
* @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
*/
@@ -138,7 +138,7 @@ public class PersistedBTreeBuilder<K, V>
rm.updateBtreeHeader( btree, ( ( AbstractPage<K, V> ) rootPage ).getOffset()
);
- rm.addFreePages( btree, Arrays.asList( btree.getRootPage() ) );
+ rm.freePages( btree, btree.getRootPage().getRevision(), Arrays.asList( btree.getRootPage()
) );
( ( AbstractBTree<K, V> ) btree ).setRootPage( rootPage );
Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeConfiguration.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeConfiguration.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeConfiguration.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedBTreeConfiguration.java
Mon Feb 10 15:35:18 2014
@@ -25,11 +25,11 @@ import org.apache.directory.mavibot.btre
/**
* The B+Tree Configuration. This class can be used to store all the configurable
- * parameters used by the BTree class
- *
+ * parameters used by the B-tree class
+ *
* @param <K> The type for the keys
* @param <V> The type for the stored values
- *
+ *
* @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
*/
public class PersistedBTreeConfiguration<K, V>
@@ -40,23 +40,23 @@ public class PersistedBTreeConfiguration
/** The size of the buffer used to write data in disk */
private int writeBufferSize = BTree.DEFAULT_WRITE_BUFFER_SIZE;
- /** The Key and Value serializer used for this tree. If none is provided,
- * the BTree will deduce the serializer to use from the generic type, and
+ /** The Key and Value serializer used for this tree. If none is provided,
+ * the B-tree will deduce the serializer to use from the generic type, and
* use the default Java serialization */
private ElementSerializer<K> keySerializer;
private ElementSerializer<V> valueSerializer;
- /** The BTree name */
+ /** The B-tree name */
private String name;
- /** The path where the BTree file will be stored. Default to the local
+ /** The path where the B-tree file will be stored. Default to the local
* temporary directory.
*/
private String filePath;
- /**
+ /**
* The maximum delay to wait before a revision is considered as unused.
- * This delay is necessary so that a read that does not ends does not
+ * This delay is necessary so that a read that does not ends does not
* hold a revision in memory forever.
* The default value is 10000 (10 seconds). If the value is 0 or below,
* the delay is considered as infinite
@@ -66,13 +66,13 @@ public class PersistedBTreeConfiguration
/** Flag to enable duplicate key support */
private boolean allowDuplicates;
- /** A flag set when the BTree is a sub btree */
- private boolean isSubBtree = false;
+ /** The B-tree type */
+ private BTreeTypeEnum btreeType = BTreeTypeEnum.PERSISTED;
/** The cache size, if it's <= 0, we don't have cache */
private int cacheSize;
- /** The inherited BTree if we create a sub BTree */
+ /** The inherited B-tree if we create a sub B-tree */
private BTree<?, V> parentBTree;
@@ -224,10 +224,10 @@ public class PersistedBTreeConfiguration
/**
* enable duplicate key support
- *
+ *
* @param allowDuplicates
- * @throws IllegalStateException if the btree was already initialized or when tried to
turn off duplicate suport on
- * an existing btree containing duplicate keys
+ * @throws IllegalStateException if the B-tree was already initialized or when tried
to turn off duplicate suport on
+ * an existing B-tree containing duplicate keys
*/
public void setAllowDuplicates( boolean allowDuplicates )
{
@@ -272,19 +272,19 @@ public class PersistedBTreeConfiguration
/**
- * @return True if this is a sub btree, false otherwise
+ * @return The BtreeType for this Btree
*/
- public boolean isSubBtree()
+ public BTreeTypeEnum getBtreeType()
{
- return isSubBtree;
+ return btreeType;
}
/**
- * @param isSubBtree True if the BTree will be a sub btree, false otherwise
+ * @param btreeType The BtreeType
*/
- public void setSubBtree( boolean isSubBtree )
+ public void setBtreeType( BTreeTypeEnum btreeType )
{
- this.isSubBtree = isSubBtree;
+ this.btreeType = btreeType;
}
}
Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedLeaf.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedLeaf.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedLeaf.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedLeaf.java
Mon Feb 10 15:35:18 2014
@@ -71,7 +71,7 @@ import org.apache.directory.mavibot.btre
/**
* {@inheritDoc}
*/
- public InsertResult<K, V> insert( long revision, K key, V value ) throws IOException
+ public InsertResult<K, V> insert( K key, V value, long revision ) throws IOException
{
// Find the key into this leaf
int pos = findPos( key );
@@ -116,7 +116,7 @@ import org.apache.directory.mavibot.btre
* {@inheritDoc}
*/
@SuppressWarnings("unchecked")
- public DeleteResult<K, V> delete( long revision, K key, V value, Page<K, V>
parent, int parentPos )
+ /* no qualifier */ DeleteResult<K, V> delete( K key, V value, long revision, Page<K,
V> parent, int parentPos )
throws IOException
{
// Check that the leaf is not empty
Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedNode.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedNode.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedNode.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedNode.java
Mon Feb 10 15:35:18 2014
@@ -120,7 +120,7 @@ import java.util.List;
/**
* {@inheritDoc}
*/
- public InsertResult<K, V> insert( long revision, K key, V value ) throws IOException
+ public InsertResult<K, V> insert( K key, V value, long revision ) throws IOException
{
// Find the key into this leaf
int pos = findPos( key );
@@ -136,7 +136,7 @@ import java.util.List;
Page<K, V> child = children[pos].getValue();
// and insert the <K, V> into this child
- InsertResult<K, V> result = child.insert( revision, key, value );
+ InsertResult<K, V> result = child.insert( key, value, revision );
// Ok, now, we have injected the <K, V> tuple down the tree. Let's check
// the result to see if we have to split the current page
@@ -567,7 +567,7 @@ import java.util.List;
/**
* {@inheritDoc}
*/
- public DeleteResult<K, V> delete( long revision, K key, V value, Page<K, V>
parent, int parentPos )
+ /* no qualifier */ DeleteResult<K, V> delete( K key, V value, long revision, Page<K,
V> parent, int parentPos )
throws IOException
{
// We first try to delete the element from the child it belongs to
@@ -582,12 +582,12 @@ import java.util.List;
{
index = -( pos + 1 );
child = children[-pos].getValue();
- deleteResult = child.delete( revision, key, value, this, -pos );
+ deleteResult = ((AbstractPage<K, V>)child).delete( key, value, revision,
this, -pos );
}
else
{
child = children[pos].getValue();
- deleteResult = child.delete( revision, key, value, this, pos );
+ deleteResult = ((AbstractPage<K, V>)child).delete( key, value, revision,
this, pos );
}
// If the key is not present in the tree, we simply return
Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedValueHolder.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedValueHolder.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedValueHolder.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/PersistedValueHolder.java
Mon Feb 10 15:35:18 2014
@@ -248,7 +248,7 @@ import org.apache.directory.mavibot.btre
configuration.setName( UUID.randomUUID().toString() );
configuration.setValueSerializer( valueSerializer );
configuration.setParentBTree( parentBtree );
- configuration.setSubBtree( true );
+ configuration.setBtreeType( BTreeTypeEnum.PERSISTED_SUB );
valueBtree = BTreeFactory.createPersistedBTree( configuration );
@@ -655,7 +655,7 @@ import org.apache.directory.mavibot.btre
long offset = LongSerializer.deserialize( raw );
// and reload the sub btree
- valueBtree = parentBtree.getRecordManager().loadDupsBTree( offset );
+ valueBtree = parentBtree.getRecordManager().loadDupsBtree( offset );
}
Modified: directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/ReadTransaction.java
URL: http://svn.apache.org/viewvc/directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/ReadTransaction.java?rev=1566659&r1=1566658&r2=1566659&view=diff
==============================================================================
--- directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/ReadTransaction.java
(original)
+++ directory/mavibot/branches/with-txns/mavibot/src/main/java/org/apache/directory/mavibot/btree/ReadTransaction.java
Mon Feb 10 15:35:18 2014
@@ -35,7 +35,7 @@ import java.util.Date;
* A Transaction can be hold for quite a long time, for instance while doing
* a browse against a big BTree. At some point, transactions which are pending
* for too long will be closed by the transaction manager.
- *
+ *
* @author <a href="mailto:dev@directory.apache.org">Apache Directory Project</a>
*
* @param <K> The type for the Key
@@ -50,7 +50,10 @@ public class ReadTransaction<K, V>
private long creationDate;
/** The revision on which we are having a transaction */
- private volatile Page<K, V> root;
+ private volatile Page<K, V> rootPage;
+
+ /** The associated B-tree header */
+ private BTreeHeader<K, V> btreeHeader;
/** A flag used to tell if a transaction is closed or not */
private volatile boolean closed;
@@ -58,16 +61,15 @@ public class ReadTransaction<K, V>
/**
* Creates a new transaction instance
- *
- * @param root The associated root
- * @param revision The revision this transaction is using
- * @param creationDate The creation date for this transaction
- */
- public ReadTransaction( Page<K, V> root, long revision, long creationDate )
- {
- this.revision = revision;
- this.creationDate = creationDate;
- this.root = root;
+ *
+ * @param btreeHeader The BtreeHeader we will use for this read transaction
+ */
+ public ReadTransaction( BTreeHeader<K, V> btreeHeader )
+ {
+ this.revision = btreeHeader.getRevision();
+ this.creationDate = System.currentTimeMillis();
+ this.rootPage = btreeHeader.getRootPage();
+ this.btreeHeader = btreeHeader;
closed = false;
}
@@ -82,11 +84,11 @@ public class ReadTransaction<K, V>
/**
- * @return the associated root
+ * @return the associated rootPage
*/
- public Page<K, V> getRoot()
+ public Page<K, V> getRootPage()
{
- return root;
+ return rootPage;
}
@@ -100,11 +102,20 @@ public class ReadTransaction<K, V>
/**
+ * @return the btreeHeader
+ */
+ public BTreeHeader<K, V> getBtreeHeader()
+ {
+ return btreeHeader;
+ }
+
+
+ /**
* Close the transaction, releasing the revision it was using.
*/
public void close()
{
- root = null;
+ rootPage = null;
closed = true;
}
|