Skip to content

Commit

Permalink
Improved TreePrinter
Browse files Browse the repository at this point in the history
Added possibility to
- print individual node
- also print tree state
  • Loading branch information
burqen committed Mar 9, 2017
1 parent 525d36a commit 5aad59c
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 20 deletions.
Expand Up @@ -738,16 +738,16 @@ public void prepareForRecovery() throws IOException

void printTree() throws IOException
{
printTree( true, true );
printTree( true, true, true );
}

// Utility method
void printTree( boolean printValues, boolean printPosition ) throws IOException
void printTree( boolean printValues, boolean printPosition, boolean printState ) throws IOException
{
try ( PageCursor cursor = openRootCursor( PagedFile.PF_SHARED_READ_LOCK ) )
{
new TreePrinter<>( bTreeNode, layout, stableGeneration( generation ), unstableGeneration( generation ) )
.printTree( cursor, System.out, printValues, printPosition );
.printTree( cursor, System.out, printValues, printPosition, printState );
}
}

Expand Down
Expand Up @@ -19,11 +19,14 @@
*/
package org.neo4j.index.internal.gbptree;

import org.apache.commons.lang3.tuple.Pair;

import java.io.IOException;
import java.io.PrintStream;

import org.neo4j.io.pagecache.PageCursor;

import static java.lang.String.format;
import static org.neo4j.index.internal.gbptree.ConsistencyChecker.assertOnTreeNode;
import static org.neo4j.index.internal.gbptree.GenSafePointerPair.pointer;

Expand Down Expand Up @@ -53,10 +56,21 @@ class TreePrinter<KEY,VALUE>
* @param cursor {@link PageCursor} placed at root of tree or sub-tree.
* @param out target to print tree at.
* @param printPosition whether or not to include positional (slot number) information.
* @param printState
* @throws IOException on page cache access error.
*/
void printTree( PageCursor cursor, PrintStream out, boolean printValues, boolean printPosition ) throws IOException
void printTree( PageCursor cursor, PrintStream out, boolean printValues, boolean printPosition, boolean printState )
throws IOException
{
if ( printState )
{
long currentPage = cursor.getCurrentPageId();
Pair<TreeState,TreeState> statePair = TreeStatePair.readStatePages(
cursor, IdSpace.STATE_PAGE_A, IdSpace.STATE_PAGE_B );
node.goTo( cursor, "back to tree node from reading state", currentPage );
out.println( "StateA: " + statePair.getLeft() );
out.println( "StateB: " + statePair.getRight() );
}
assertOnTreeNode( cursor );

// Traverse the tree
Expand All @@ -77,10 +91,38 @@ void printTree( PageCursor cursor, PrintStream out, boolean printValues, boolean
while ( goToLeftmostChild( cursor ) );
}

private void printTreeNode( PageCursor cursor, int keyCount, boolean isLeaf, PrintStream out, boolean printValues,
boolean printPosition ) throws IOException
void printTreeNode( PageCursor cursor, PrintStream out, boolean printValues, boolean printPosition,
boolean printHeader ) throws IOException
{
out.print( "{" + cursor.getCurrentPageId() + "} " );
boolean isLeaf;
int keyCount;
do
{
isLeaf = TreeNode.isLeaf( cursor );
keyCount = node.keyCount( cursor );
if ( keyCount < 0 || (keyCount > node.internalMaxKeyCount() && keyCount > node.leafMaxKeyCount()) )
{
cursor.setCursorException( "Unexpected keyCount " + keyCount );
}
} while ( cursor.shouldRetry() );

if ( printHeader )
{
//[TYPE][GEN][KEYCOUNT] ([RIGHTSIBLING][LEFTSIBLING][NEWGEN]))
long generation = -1;
do
{
generation = node.gen( cursor );

} while ( cursor.shouldRetry() );
String treeNodeType = isLeaf ? "leaf" : "internal";
out.print( format( "{%d,%s,gen=%d,keyCount=%d}",
cursor.getCurrentPageId(), treeNodeType, generation, keyCount ) );
}
else
{
out.print( "{" + cursor.getCurrentPageId() + "} " );
}
KEY key = layout.newKey();
VALUE value = layout.newValue();
for ( int i = 0; i < keyCount; i++ )
Expand Down Expand Up @@ -161,26 +203,18 @@ private boolean goToLeftmostChild( PageCursor cursor ) throws IOException
private void printLevel( PageCursor cursor, PrintStream out, boolean printValues, boolean printPosition )
throws IOException
{
int keyCount;
long rightSibling = -1;
boolean isLeaf;
do
{

printTreeNode( cursor, out, printValues, printPosition, false );

do
{
isLeaf = TreeNode.isLeaf( cursor );
keyCount = node.keyCount( cursor );
if ( keyCount < 0 || (keyCount > node.internalMaxKeyCount() && keyCount > node.leafMaxKeyCount()) )
{
cursor.setCursorException( "Unexpected keyCount " + keyCount );
continue;
}
rightSibling = node.rightSibling( cursor, stableGeneration, unstableGeneration );
}
while ( cursor.shouldRetry() );

printTreeNode( cursor, keyCount, isLeaf, out, printValues, printPosition );

if ( TreeNode.isNode( rightSibling ) )
{
node.goTo( cursor, "right sibling", rightSibling );
Expand Down
Expand Up @@ -174,7 +174,7 @@ private void doShouldRecoverFromAnything( boolean replayRecoveryExactlyFromCheck
}
else
{
recoveryActions = recoveryActions( load, random.nextInt( lastCheckPointIndex ) );
recoveryActions = recoveryActions( load, random.nextInt( lastCheckPointIndex + 1) );
}

// first crashing during recovery
Expand Down
Expand Up @@ -1487,7 +1487,7 @@ private void printTree() throws IOException
{
long currentPageId = cursor.getCurrentPageId();
cursor.next( rootId );
new TreePrinter<>( node, layout, stableGen, unstableGen ).printTree( cursor, System.out, true, true );
new TreePrinter<>( node, layout, stableGen, unstableGen ).printTree( cursor, System.out, true, true, true );
cursor.next( currentPageId );
}

Expand Down

0 comments on commit 5aad59c

Please sign in to comment.