http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMInteriorFrame.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMInteriorFrame.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMInteriorFrame.java
index 9505f8a..e59523c 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMInteriorFrame.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMInteriorFrame.java
@@ -45,8 +45,8 @@ import 
org.apache.hyracks.storage.common.buffercache.IExtraPageBlockHelper;
 
 public class BTreeNSMInteriorFrame extends TreeIndexNSMFrame implements 
IBTreeInteriorFrame {
 
-    private static final int rightLeafOff = flagOff + 1; // 22
-    private static final int childPtrSize = 4;
+    private static final int RIGHT_LEAF_OFFSET = 
TreeIndexNSMFrame.RESERVED_HEADER_SIZE;
+    private static final int CHILD_PTR_SIZE = 4;
 
     private final ITreeIndexTupleReference cmpFrameTuple;
     private final ITreeIndexTupleReference previousFt;
@@ -61,13 +61,13 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
 
     @Override
     public int getBytesRequiredToWriteTuple(ITupleReference tuple) {
-        return tupleWriter.bytesRequired(tuple) + childPtrSize + 
slotManager.getSlotSize();
+        return tupleWriter.bytesRequired(tuple) + CHILD_PTR_SIZE + 
slotManager.getSlotSize();
     }
 
     @Override
     public void initBuffer(byte level) {
         super.initBuffer(level);
-        buf.putInt(rightLeafOff, -1);
+        buf.putInt(RIGHT_LEAF_OFFSET, -1);
     }
 
     @Override
@@ -82,7 +82,7 @@ public class BTreeNSMInteriorFrame extends TreeIndexNSMFrame 
implements IBTreeIn
 
     @Override
     public FrameOpSpaceStatus hasSpaceInsert(ITupleReference tuple) throws 
HyracksDataException {
-        int tupleSize = tupleWriter.bytesRequired(tuple) + childPtrSize;
+        int tupleSize = tupleWriter.bytesRequired(tuple) + CHILD_PTR_SIZE;
         if (tupleSize > getMaxTupleSize(buf.capacity())) {
             return FrameOpSpaceStatus.TOO_LARGE;
         }
@@ -99,28 +99,29 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
 
     @Override
     public void insert(ITupleReference tuple, int tupleIndex) {
-        int slotOff = slotManager.insertSlot(tupleIndex, 
buf.getInt(freeSpaceOff));
-        int freeSpace = buf.getInt(freeSpaceOff);
+        int slotOff = slotManager.insertSlot(tupleIndex, 
buf.getInt(Constants.FREE_SPACE_OFFSET));
+        int freeSpace = buf.getInt(Constants.FREE_SPACE_OFFSET);
         int bytesWritten = tupleWriter.writeTupleFields(tuple, 0, 
tuple.getFieldCount(), buf.array(), freeSpace);
         System.arraycopy(tuple.getFieldData(tuple.getFieldCount() - 1), 
getLeftChildPageOff(tuple), buf.array(),
-                freeSpace + bytesWritten, childPtrSize);
-        int tupleSize = bytesWritten + childPtrSize;
-        buf.putInt(tupleCountOff, buf.getInt(tupleCountOff) + 1);
-        buf.putInt(freeSpaceOff, buf.getInt(freeSpaceOff) + tupleSize);
-        buf.putInt(totalFreeSpaceOff, buf.getInt(totalFreeSpaceOff) - 
tupleSize - slotManager.getSlotSize());
+                freeSpace + bytesWritten, CHILD_PTR_SIZE);
+        int tupleSize = bytesWritten + CHILD_PTR_SIZE;
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, 
buf.getInt(Constants.TUPLE_COUNT_OFFSET) + 1);
+        buf.putInt(Constants.FREE_SPACE_OFFSET, 
buf.getInt(Constants.FREE_SPACE_OFFSET) + tupleSize);
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET, 
buf.getInt(TOTAL_FREE_SPACE_OFFSET) - tupleSize - slotManager
+                .getSlotSize());
         // Did we insert into the rightmost slot?
         if (slotOff == slotManager.getSlotEndOff()) {
-            System.arraycopy(tuple.getFieldData(tuple.getFieldCount() - 1), 
getLeftChildPageOff(tuple) + childPtrSize,
-                    buf.array(), rightLeafOff, childPtrSize);
+            System.arraycopy(tuple.getFieldData(tuple.getFieldCount() - 1), 
getLeftChildPageOff(tuple) + CHILD_PTR_SIZE,
+                    buf.array(), RIGHT_LEAF_OFFSET, CHILD_PTR_SIZE);
         } else {
             // If slotOff has a right (slot-)neighbor then update its child 
pointer.
             // The only time when this is NOT the case, is when this is the 
very first tuple
             // (or when the splitkey goes into the rightmost slot but that 
case is handled in the if above).
-            if (buf.getInt(tupleCountOff) > 1) {
+            if (buf.getInt(Constants.TUPLE_COUNT_OFFSET) > 1) {
                 int rightNeighborOff = slotOff - slotManager.getSlotSize();
-                frameTuple.resetByTupleOffset(buf, 
slotManager.getTupleOff(rightNeighborOff));
-                System.arraycopy(tuple.getFieldData(0), 
getLeftChildPageOff(tuple) + childPtrSize, buf.array(),
-                        getLeftChildPageOff(frameTuple), childPtrSize);
+                frameTuple.resetByTupleOffset(buf.array(), 
slotManager.getTupleOff(rightNeighborOff));
+                System.arraycopy(tuple.getFieldData(0), 
getLeftChildPageOff(tuple) + CHILD_PTR_SIZE, buf.array(),
+                        getLeftChildPageOff(frameTuple), CHILD_PTR_SIZE);
             }
         }
     }
@@ -142,13 +143,13 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
         int keySize;
         if (tupleIndex == slotManager.getGreatestKeyIndicator()) {
             tupleOff = slotManager.getTupleOff(slotManager.getSlotEndOff());
-            frameTuple.resetByTupleOffset(buf, tupleOff);
+            frameTuple.resetByTupleOffset(buf.array(), tupleOff);
             keySize = frameTuple.getTupleSize();
             // Copy new rightmost pointer.
-            System.arraycopy(buf.array(), tupleOff + keySize, buf.array(), 
rightLeafOff, childPtrSize);
+            System.arraycopy(buf.array(), tupleOff + keySize, buf.array(), 
RIGHT_LEAF_OFFSET, CHILD_PTR_SIZE);
         } else {
             tupleOff = slotManager.getTupleOff(slotOff);
-            frameTuple.resetByTupleOffset(buf, tupleOff);
+            frameTuple.resetByTupleOffset(buf.array(), tupleOff);
             keySize = frameTuple.getTupleSize();
             // Perform deletion (we just do a memcpy to overwrite the slot).
             int slotStartOff = slotManager.getSlotEndOff();
@@ -156,25 +157,25 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
             System.arraycopy(buf.array(), slotStartOff, buf.array(), 
slotStartOff + slotManager.getSlotSize(), length);
         }
         // Maintain space information.
-        buf.putInt(tupleCountOff, buf.getInt(tupleCountOff) - 1);
-        buf.putInt(totalFreeSpaceOff,
-                buf.getInt(totalFreeSpaceOff) + keySize + childPtrSize + 
slotManager.getSlotSize());
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, 
buf.getInt(Constants.TUPLE_COUNT_OFFSET) - 1);
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET,
+                buf.getInt(TOTAL_FREE_SPACE_OFFSET) + keySize + CHILD_PTR_SIZE 
+ slotManager.getSlotSize());
     }
 
     @Override
     public void deleteGreatest() {
         int slotOff = slotManager.getSlotEndOff();
         int tupleOff = slotManager.getTupleOff(slotOff);
-        frameTuple.resetByTupleOffset(buf, tupleOff);
+        frameTuple.resetByTupleOffset(buf.array(), tupleOff);
         int keySize = tupleWriter.bytesRequired(frameTuple);
-        System.arraycopy(buf.array(), tupleOff + keySize, buf.array(), 
rightLeafOff, childPtrSize);
+        System.arraycopy(buf.array(), tupleOff + keySize, buf.array(), 
RIGHT_LEAF_OFFSET, CHILD_PTR_SIZE);
         // Maintain space information.
-        buf.putInt(tupleCountOff, buf.getInt(tupleCountOff) - 1);
-        buf.putInt(totalFreeSpaceOff,
-                buf.getInt(totalFreeSpaceOff) + keySize + childPtrSize + 
slotManager.getSlotSize());
-        int freeSpace = buf.getInt(freeSpaceOff);
-        if (freeSpace == tupleOff + keySize + childPtrSize) {
-            buf.putInt(freeSpace, freeSpace - (keySize + childPtrSize));
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, 
buf.getInt(Constants.TUPLE_COUNT_OFFSET) - 1);
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET,
+                buf.getInt(TOTAL_FREE_SPACE_OFFSET) + keySize + CHILD_PTR_SIZE 
+ slotManager.getSlotSize());
+        int freeSpace = buf.getInt(Constants.FREE_SPACE_OFFSET);
+        if (freeSpace == tupleOff + keySize + CHILD_PTR_SIZE) {
+            buf.putInt(freeSpace, freeSpace - (keySize + CHILD_PTR_SIZE));
         }
     }
 
@@ -185,17 +186,19 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
 
     @Override
     public void insertSorted(ITupleReference tuple) {
-        int freeSpace = buf.getInt(freeSpaceOff);
+        int freeSpace = buf.getInt(Constants.FREE_SPACE_OFFSET);
         slotManager.insertSlot(slotManager.getGreatestKeyIndicator(), 
freeSpace);
         int bytesWritten = tupleWriter.writeTuple(tuple, buf, freeSpace);
         System.arraycopy(tuple.getFieldData(tuple.getFieldCount() - 1), 
getLeftChildPageOff(tuple), buf.array(),
-                freeSpace + bytesWritten, childPtrSize);
-        int tupleSize = bytesWritten + childPtrSize;
-        buf.putInt(tupleCountOff, buf.getInt(tupleCountOff) + 1);
-        buf.putInt(freeSpaceOff, buf.getInt(freeSpaceOff) + tupleSize);
-        buf.putInt(totalFreeSpaceOff, buf.getInt(totalFreeSpaceOff) - 
tupleSize - slotManager.getSlotSize());
-        System.arraycopy(tuple.getFieldData(0), getLeftChildPageOff(tuple) + 
childPtrSize, buf.array(), rightLeafOff,
-                childPtrSize);
+                freeSpace + bytesWritten, CHILD_PTR_SIZE);
+        int tupleSize = bytesWritten + CHILD_PTR_SIZE;
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, 
buf.getInt(Constants.TUPLE_COUNT_OFFSET) + 1);
+        buf.putInt(Constants.FREE_SPACE_OFFSET, 
buf.getInt(Constants.FREE_SPACE_OFFSET) + tupleSize);
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET, 
buf.getInt(TOTAL_FREE_SPACE_OFFSET) - tupleSize - slotManager
+                .getSlotSize());
+        System.arraycopy(tuple.getFieldData(0), getLeftChildPageOff(tuple) + 
CHILD_PTR_SIZE, buf.array(),
+                RIGHT_LEAF_OFFSET,
+                CHILD_PTR_SIZE);
     }
 
     @Override
@@ -219,7 +222,7 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
             int i;
             for (i = 0; i < tupleCount; ++i) {
                 frameTuple.resetByTupleIndex(this, i);
-                totalSize += tupleWriter.bytesRequired(frameTuple) + 
childPtrSize + slotManager.getSlotSize();
+                totalSize += tupleWriter.bytesRequired(frameTuple) + 
CHILD_PTR_SIZE + slotManager.getSlotSize();
                 if (totalSize >= halfPageSize) {
                     break;
                 }
@@ -243,11 +246,11 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
                     + tuplesToLeft * rightFrame.getSlotManager().getSlotSize();
             int length = rightFrame.getSlotManager().getSlotSize() * 
tuplesToRight;
             System.arraycopy(right.array(), src, right.array(), dest, length);
-            right.putInt(tupleCountOff, tuplesToRight);
+            right.putInt(Constants.TUPLE_COUNT_OFFSET, tuplesToRight);
 
             // On the left page, remove the highest key and make its child 
pointer
             // the rightmost child pointer.
-            buf.putInt(tupleCountOff, tuplesToLeft);
+            buf.putInt(Constants.TUPLE_COUNT_OFFSET, tuplesToLeft);
         }
         // Copy the split key to be inserted.
         // We must do so because setting the new split key will overwrite the
@@ -256,16 +259,16 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
 
         // Set split key to be highest value in left page.
         int tupleOff = slotManager.getTupleOff(slotManager.getSlotEndOff());
-        frameTuple.resetByTupleOffset(buf, tupleOff);
+        frameTuple.resetByTupleOffset(buf.array(), tupleOff);
         int splitKeySize = tupleWriter.bytesRequired(frameTuple, 0, 
cmp.getKeyFieldCount());
         splitKey.initData(splitKeySize);
         tupleWriter.writeTuple(frameTuple, splitKey.getBuffer(), 0);
-        splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer(), 0);
+        splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer().array(), 
0);
 
         int deleteTupleOff = 
slotManager.getTupleOff(slotManager.getSlotEndOff());
-        frameTuple.resetByTupleOffset(buf, deleteTupleOff);
-        buf.putInt(rightLeafOff, buf.getInt(getLeftChildPageOff(frameTuple)));
-        buf.putInt(tupleCountOff, tuplesToLeft - 1);
+        frameTuple.resetByTupleOffset(buf.array(), deleteTupleOff);
+        buf.putInt(RIGHT_LEAF_OFFSET, 
buf.getInt(getLeftChildPageOff(frameTuple)));
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, tuplesToLeft - 1);
 
         // Compact both pages.
         rightFrame.compact();
@@ -284,10 +287,10 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
     @Override
     public boolean compact() {
         resetSpaceParams();
-        int tupleCount = buf.getInt(tupleCountOff);
-        int freeSpace = buf.getInt(freeSpaceOff);
+        int tupleCount = buf.getInt(Constants.TUPLE_COUNT_OFFSET);
+        int freeSpace = buf.getInt(Constants.FREE_SPACE_OFFSET);
         // Sort the slots by the tuple offset they point to.
-        ArrayList<SlotOffTupleOff> sortedTupleOffs = new 
ArrayList<SlotOffTupleOff>();
+        ArrayList<SlotOffTupleOff> sortedTupleOffs = new ArrayList<>();
         sortedTupleOffs.ensureCapacity(tupleCount);
         for (int i = 0; i < tupleCount; i++) {
             int slotOff = slotManager.getSlotOff(i);
@@ -299,25 +302,25 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
         // the left, reclaiming free space.
         for (int i = 0; i < sortedTupleOffs.size(); i++) {
             int tupleOff = sortedTupleOffs.get(i).tupleOff;
-            frameTuple.resetByTupleOffset(buf, tupleOff);
+            frameTuple.resetByTupleOffset(buf.array(), tupleOff);
             int tupleEndOff = 
frameTuple.getFieldStart(frameTuple.getFieldCount() - 1)
                     + frameTuple.getFieldLength(frameTuple.getFieldCount() - 
1);
-            int tupleLength = tupleEndOff - tupleOff + childPtrSize;
+            int tupleLength = tupleEndOff - tupleOff + CHILD_PTR_SIZE;
             System.arraycopy(buf.array(), tupleOff, buf.array(), freeSpace, 
tupleLength);
             slotManager.setSlot(sortedTupleOffs.get(i).slotOff, freeSpace);
             freeSpace += tupleLength;
         }
         // Update contiguous free space pointer and total free space indicator.
-        buf.putInt(freeSpaceOff, freeSpace);
-        buf.putInt(totalFreeSpaceOff, buf.capacity() - freeSpace - tupleCount 
* slotManager.getSlotSize());
+        buf.putInt(Constants.FREE_SPACE_OFFSET, freeSpace);
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET, buf.capacity() - freeSpace - 
tupleCount * slotManager.getSlotSize());
         return false;
     }
 
     @Override
     public int getChildPageId(RangePredicate pred) throws HyracksDataException 
{
         // Trivial case where there is only a child pointer (and no key).
-        if (buf.getInt(tupleCountOff) == 0) {
-            return buf.getInt(rightLeafOff);
+        if (buf.getInt(Constants.TUPLE_COUNT_OFFSET) == 0) {
+            return buf.getInt(RIGHT_LEAF_OFFSET);
         }
         // Trivial cases where no low key or high key was given (e.g. during an
         // index scan).
@@ -340,7 +343,7 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
         int slotOff = slotManager.getSlotOff(tupleIndex);
         // Follow the rightmost (greatest) child pointer.
         if (tupleIndex == slotManager.getGreatestKeyIndicator()) {
-            return buf.getInt(rightLeafOff);
+            return buf.getInt(RIGHT_LEAF_OFFSET);
         }
         // Deal with prefix searches.
         // slotManager.findTupleIndex() will return an arbitrary tuple matching
@@ -348,7 +351,7 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
         // To make sure we traverse the right path, we must find the
         // leftmost or rightmost tuple that matches the prefix.
         int origTupleOff = slotManager.getTupleOff(slotOff);
-        cmpFrameTuple.resetByTupleOffset(buf, origTupleOff);
+        cmpFrameTuple.resetByTupleOffset(buf.array(), origTupleOff);
         int cmpTupleOff = origTupleOff;
         // The answer set begins with the lowest key matching the prefix.
         // We must follow the child pointer of the lowest (leftmost) key
@@ -357,14 +360,14 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
         slotOff += slotManager.getSlotSize();
         while (slotOff < maxSlotOff) {
             cmpTupleOff = slotManager.getTupleOff(slotOff);
-            frameTuple.resetByTupleOffset(buf, cmpTupleOff);
+            frameTuple.resetByTupleOffset(buf.array(), cmpTupleOff);
             if (targetCmp.compare(cmpFrameTuple, frameTuple) != 0) {
                 break;
             }
             slotOff += slotManager.getSlotSize();
         }
         slotOff -= slotManager.getSlotSize();
-        frameTuple.resetByTupleOffset(buf, slotManager.getTupleOff(slotOff));
+        frameTuple.resetByTupleOffset(buf.array(), 
slotManager.getTupleOff(slotOff));
         int childPageOff = getLeftChildPageOff(frameTuple);
 
         return buf.getInt(childPageOff);
@@ -373,24 +376,24 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
     @Override
     public int getLeftmostChildPageId() {
         int tupleOff = slotManager.getTupleOff(slotManager.getSlotStartOff());
-        frameTuple.resetByTupleOffset(buf, tupleOff);
+        frameTuple.resetByTupleOffset(buf.array(), tupleOff);
         int childPageOff = getLeftChildPageOff(frameTuple);
         return buf.getInt(childPageOff);
     }
 
     @Override
     public int getRightmostChildPageId() {
-        return buf.getInt(rightLeafOff);
+        return buf.getInt(RIGHT_LEAF_OFFSET);
     }
 
     @Override
     public void setRightmostChildPageId(int pageId) {
-        buf.putInt(rightLeafOff, pageId);
+        buf.putInt(RIGHT_LEAF_OFFSET, pageId);
     }
 
     @Override
     public int getPageHeaderSize() {
-        return rightLeafOff + 4;
+        return RIGHT_LEAF_OFFSET + 4;
     }
 
     private int getLeftChildPageOff(ITupleReference tuple) {
@@ -414,25 +417,27 @@ public class BTreeNSMInteriorFrame extends 
TreeIndexNSMFrame implements IBTreeIn
 
     // For debugging.
     public ArrayList<Integer> getChildren(MultiComparator cmp) {
-        ArrayList<Integer> ret = new ArrayList<Integer>();
+        ArrayList<Integer> ret = new ArrayList<>();
         frameTuple.setFieldCount(cmp.getKeyFieldCount());
-        int tupleCount = buf.getInt(tupleCountOff);
+        int tupleCount = buf.getInt(Constants.TUPLE_COUNT_OFFSET);
         for (int i = 0; i < tupleCount; i++) {
             int tupleOff = slotManager.getTupleOff(slotManager.getSlotOff(i));
-            frameTuple.resetByTupleOffset(buf, tupleOff);
+            frameTuple.resetByTupleOffset(buf.array(), tupleOff);
             int intVal = IntegerPointable.getInteger(buf.array(),
                     frameTuple.getFieldStart(frameTuple.getFieldCount() - 1)
                             + 
frameTuple.getFieldLength(frameTuple.getFieldCount() - 1));
             ret.add(intVal);
         }
         if (!isLeaf()) {
-            int rightLeaf = buf.getInt(rightLeafOff);
-            if (rightLeaf > 0)
-                ret.add(buf.getInt(rightLeafOff));
+            int rightLeaf = buf.getInt(RIGHT_LEAF_OFFSET);
+            if (rightLeaf > 0) {
+                ret.add(buf.getInt(RIGHT_LEAF_OFFSET));
+            }
         }
         return ret;
     }
 
+    @Override
     public void validate(PageValidationInfo pvi) throws HyracksDataException {
         int tupleCount = getTupleCount();
         for (int i = 0; i < tupleCount; i++) {

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMLeafFrame.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMLeafFrame.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMLeafFrame.java
index f7af7ad..6a957b5 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMLeafFrame.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/frames/BTreeNSMLeafFrame.java
@@ -41,7 +41,7 @@ import 
org.apache.hyracks.storage.common.buffercache.IBufferCache;
 import org.apache.hyracks.storage.common.buffercache.IExtraPageBlockHelper;
 
 public class BTreeNSMLeafFrame extends TreeIndexNSMFrame implements 
IBTreeLeafFrame {
-    protected static final int nextLeafOff = flagOff + 1; // 22
+    protected static final int NEXT_LEAF_OFFSET = 
TreeIndexNSMFrame.RESERVED_HEADER_SIZE;
 
     private MultiComparator cmp;
 
@@ -54,7 +54,7 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
 
     @Override
     public int getPageHeaderSize() {
-        return nextLeafOff + 4;
+        return NEXT_LEAF_OFFSET + 4;
     }
 
     @Override
@@ -65,17 +65,17 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
     @Override
     public void initBuffer(byte level) {
         super.initBuffer(level);
-        buf.putInt(nextLeafOff, -1);
+        buf.putInt(NEXT_LEAF_OFFSET, -1);
     }
 
     @Override
     public void setNextLeaf(int page) {
-        buf.putInt(nextLeafOff, page);
+        buf.putInt(NEXT_LEAF_OFFSET, page);
     }
 
     @Override
     public int getNextLeaf() {
-        return buf.getInt(nextLeafOff);
+        return buf.getInt(NEXT_LEAF_OFFSET);
     }
 
     @Override
@@ -161,12 +161,13 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
 
     @Override
     public void insert(ITupleReference tuple, int tupleIndex) {
-        int freeSpace = buf.getInt(freeSpaceOff);
+        int freeSpace = buf.getInt(Constants.FREE_SPACE_OFFSET);
         slotManager.insertSlot(tupleIndex, freeSpace);
         int bytesWritten = tupleWriter.writeTuple(tuple, buf.array(), 
freeSpace);
-        buf.putInt(tupleCountOff, buf.getInt(tupleCountOff) + 1);
-        buf.putInt(freeSpaceOff, buf.getInt(freeSpaceOff) + bytesWritten);
-        buf.putInt(totalFreeSpaceOff, buf.getInt(totalFreeSpaceOff) - 
bytesWritten - slotManager.getSlotSize());
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, 
buf.getInt(Constants.TUPLE_COUNT_OFFSET) + 1);
+        buf.putInt(Constants.FREE_SPACE_OFFSET, 
buf.getInt(Constants.FREE_SPACE_OFFSET) + bytesWritten);
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET, 
buf.getInt(TOTAL_FREE_SPACE_OFFSET) - bytesWritten - slotManager
+                .getSlotSize());
     }
 
     @Override
@@ -261,10 +262,10 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
                     + tuplesToLeft * rightFrame.getSlotManager().getSlotSize();
             int length = rightFrame.getSlotManager().getSlotSize() * 
tuplesToRight;
             System.arraycopy(right.array(), src, right.array(), dest, length);
-            right.putInt(tupleCountOff, tuplesToRight);
+            right.putInt(Constants.TUPLE_COUNT_OFFSET, tuplesToRight);
 
             // On left page only change the tupleCount indicator.
-            buf.putInt(tupleCountOff, tuplesToLeft);
+            buf.putInt(Constants.TUPLE_COUNT_OFFSET, tuplesToLeft);
 
             // Compact both pages.
             rightFrame.compact();
@@ -288,13 +289,14 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
 
         // Set the split key to be highest key in the left page.
         int tupleOff = slotManager.getTupleOff(slotManager.getSlotEndOff());
-        frameTuple.resetByTupleOffset(buf, tupleOff);
+        frameTuple.resetByTupleOffset(buf.array(), tupleOff);
         int splitKeySize = tupleWriter.bytesRequired(frameTuple, 0, 
cmp.getKeyFieldCount());
         splitKey.initData(splitKeySize);
         tupleWriter.writeTupleFields(frameTuple, 0, cmp.getKeyFieldCount(), 
splitKey.getBuffer().array(), 0);
-        splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer(), 0);
+        splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer().array(), 
0);
     }
 
+    @Override
     public void ensureCapacity(IBufferCache bufferCache, ITupleReference tuple,
                                IExtraPageBlockHelper extraPageBlockHelper) 
throws HyracksDataException {
         // we call ensureCapacity() for large tuples- ensure large flag is set
@@ -323,7 +325,8 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
         System.arraycopy(buf.array(), oldSlotEnd, buf.array(), 
slotManager.getSlotEndOff(), oldSlotStart - oldSlotEnd);
 
         // fixup total free space counter
-        buf.putInt(totalFreeSpaceOff, buf.getInt(totalFreeSpaceOff) + 
(bufferCache.getPageSize() * deltaPages));
+        buf.putInt(TOTAL_FREE_SPACE_OFFSET, 
buf.getInt(TOTAL_FREE_SPACE_OFFSET) + (bufferCache.getPageSize()
+                * deltaPages));
     }
 
     @Override
@@ -342,6 +345,7 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
         this.cmp = cmp;
     }
 
+    @Override
     public void validate(PageValidationInfo pvi) throws HyracksDataException {
         int tupleCount = getTupleCount();
         for (int i = 0; i < tupleCount; i++) {
@@ -364,7 +368,7 @@ public class BTreeNSMLeafFrame extends TreeIndexNSMFrame 
implements IBTreeLeafFr
     @Override
     public String printHeader() {
         StringBuilder strBuilder = new StringBuilder(super.printHeader());
-        strBuilder.append("nextLeafOff:       " + nextLeafOff + "\n");
+        strBuilder.append("nextLeafOff:       " + NEXT_LEAF_OFFSET + "\n");
         return strBuilder.toString();
     }
 }

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTree.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTree.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTree.java
index b6a64fa..5fdd943 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTree.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTree.java
@@ -1041,7 +1041,7 @@ public class BTree extends AbstractTreeIndex {
                         splitKey.initData(splitKeySize);
                         tupleWriter.writeTupleFields(leafFrontier.lastTuple, 
0, cmp.getKeyFieldCount(),
                                 splitKey.getBuffer().array(), 0);
-                        
splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer(), 0);
+                        
splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer().array(), 0);
                         splitKey.setLeftPage(leafFrontier.pageId);
 
                         propagateBulk(1, pagesToWrite);
@@ -1137,7 +1137,7 @@ public class BTree extends AbstractTreeIndex {
                 splitKey.initData(splitKeySize);
                 tupleWriter.writeTupleFields(frontier.lastTuple, 0, 
cmp.getKeyFieldCount(),
                         splitKey.getBuffer().array(), 0);
-                splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer(), 
0);
+                
splitKey.getTuple().resetByTupleOffset(splitKey.getBuffer().array(), 0);
 
                 ((IBTreeInteriorFrame) interiorFrame).deleteGreatest();
                 int finalPageId = freePageManager.takePage(metaFrame);

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeOpContext.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeOpContext.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeOpContext.java
index 3de9a0c..3c5d0e5 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeOpContext.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeOpContext.java
@@ -38,7 +38,7 @@ import 
org.apache.hyracks.storage.am.common.api.IModificationOperationCallback;
 import org.apache.hyracks.storage.am.common.api.ISearchOperationCallback;
 import org.apache.hyracks.storage.am.common.api.ITreeIndexCursor;
 import org.apache.hyracks.storage.am.common.api.ITreeIndexFrameFactory;
-import org.apache.hyracks.storage.am.common.api.ITreeIndexMetaDataFrame;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexMetadataFrame;
 import org.apache.hyracks.storage.am.common.api.ITreeIndexTupleReference;
 import org.apache.hyracks.storage.am.common.ophelpers.IndexOperation;
 import org.apache.hyracks.storage.am.common.ophelpers.MultiComparator;
@@ -56,7 +56,7 @@ public class BTreeOpContext implements 
IIndexOperationContext, IExtraPageBlockHe
     public IBTreeLeafFrame leafFrame;
     public IBTreeInteriorFrame interiorFrame;
     public final IPageManager freePageManager;
-    public final ITreeIndexMetaDataFrame metaFrame;
+    public final ITreeIndexMetadataFrame metaFrame;
     public IndexOperation op;
     public ITreeIndexCursor cursor;
     public BTreeCursorInitialState cursorInitialState;

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeSplitKey.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeSplitKey.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeSplitKey.java
index f500a1a..4700ea3 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeSplitKey.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/BTreeSplitKey.java
@@ -35,6 +35,7 @@ public class BTreeSplitKey implements ISplitKey {
         this.tuple = tuple;
     }
 
+    @Override
     public void initData(int keySize) {
         // try to reuse existing memory from a lower-level split if possible
         this.keySize = keySize;
@@ -48,49 +49,58 @@ public class BTreeSplitKey implements ISplitKey {
             buf = ByteBuffer.wrap(data);
         }
 
-        tuple.resetByTupleOffset(buf, 0);
+        tuple.resetByTupleOffset(buf.array(), 0);
     }
 
+    @Override
     public void reset() {
         data = null;
         buf = null;
     }
 
+    @Override
     public ByteBuffer getBuffer() {
         return buf;
     }
 
+    @Override
     public ITreeIndexTupleReference getTuple() {
         return tuple;
     }
 
+    @Override
     public int getLeftPage() {
         return buf.getInt(keySize);
     }
 
+    @Override
     public int getRightPage() {
         return buf.getInt(keySize + 4);
     }
 
+    @Override
     public void setLeftPage(int leftPage) {
         buf.putInt(keySize, leftPage);
     }
 
+    @Override
     public void setRightPage(int rightPage) {
         buf.putInt(keySize + 4, rightPage);
     }
 
+    @Override
     public void setPages(int leftPage, int rightPage) {
         buf.putInt(keySize, leftPage);
         buf.putInt(keySize + 4, rightPage);
     }
 
+    @Override
     public BTreeSplitKey duplicate(ITreeIndexTupleReference copyTuple) {
         BTreeSplitKey copy = new BTreeSplitKey(copyTuple);
         copy.data = data.clone();
         copy.buf = ByteBuffer.wrap(copy.data);
         copy.tuple.setFieldCount(tuple.getFieldCount());
-        copy.tuple.resetByTupleOffset(copy.buf, 0);
+        copy.tuple.resetByTupleOffset(copy.buf.array(), 0);
         return copy;
     }
 }

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixPrefixTupleReference.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixPrefixTupleReference.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixPrefixTupleReference.java
index e110370..b767537 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixPrefixTupleReference.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixPrefixTupleReference.java
@@ -40,7 +40,7 @@ public class FieldPrefixPrefixTupleReference extends 
TypeAwareTupleReference {
         int prefixSlot = concreteFrame.getBuffer().getInt(prefixSlotOff);
         setFieldCount(slotManager.decodeFirstSlotField(prefixSlot));
         tupleStartOff = slotManager.decodeSecondSlotField(prefixSlot);
-        buf = concreteFrame.getBuffer();
+        buf = concreteFrame.getBuffer().array();
         resetByTupleOffset(buf, tupleStartOff);
     }
 }

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixTupleReference.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixTupleReference.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixTupleReference.java
index a249fbb..566947d 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixTupleReference.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-btree/src/main/java/org/apache/hyracks/storage/am/btree/impls/FieldPrefixTupleReference.java
@@ -18,8 +18,6 @@
  */
 package org.apache.hyracks.storage.am.btree.impls;
 
-import java.nio.ByteBuffer;
-
 import org.apache.hyracks.storage.am.btree.api.IPrefixSlotManager;
 import org.apache.hyracks.storage.am.btree.frames.BTreeFieldPrefixNSMLeafFrame;
 import org.apache.hyracks.storage.am.common.api.ITreeIndexFrame;
@@ -84,11 +82,11 @@ public class FieldPrefixTupleReference implements 
ITreeIndexTupleReference {
     public int getFieldLength(int fIdx) {
         if (fIdx < numPrefixFields) {
             helperTuple.setFieldCount(numPrefixFields);
-            helperTuple.resetByTupleOffset(frame.getBuffer(), 
prefixTupleStartOff);
+            helperTuple.resetByTupleOffset(frame.getBuffer().array(), 
prefixTupleStartOff);
             return helperTuple.getFieldLength(fIdx);
         } else {
             helperTuple.setFieldCount(numPrefixFields, fieldCount - 
numPrefixFields);
-            helperTuple.resetByTupleOffset(frame.getBuffer(), 
suffixTupleStartOff);
+            helperTuple.resetByTupleOffset(frame.getBuffer().array(), 
suffixTupleStartOff);
             return helperTuple.getFieldLength(fIdx - numPrefixFields);
         }
     }
@@ -97,18 +95,18 @@ public class FieldPrefixTupleReference implements 
ITreeIndexTupleReference {
     public int getFieldStart(int fIdx) {
         if (fIdx < numPrefixFields) {
             helperTuple.setFieldCount(numPrefixFields);
-            helperTuple.resetByTupleOffset(frame.getBuffer(), 
prefixTupleStartOff);
+            helperTuple.resetByTupleOffset(frame.getBuffer().array(), 
prefixTupleStartOff);
             return helperTuple.getFieldStart(fIdx);
         } else {
             helperTuple.setFieldCount(numPrefixFields, fieldCount - 
numPrefixFields);
-            helperTuple.resetByTupleOffset(frame.getBuffer(), 
suffixTupleStartOff);
+            helperTuple.resetByTupleOffset(frame.getBuffer().array(), 
suffixTupleStartOff);
             return helperTuple.getFieldStart(fIdx - numPrefixFields);
         }
     }
 
     // unsupported operation
     @Override
-    public void resetByTupleOffset(ByteBuffer buf, int tupleStartOffset) {
+    public void resetByTupleOffset(byte[] buf, int tupleStartOffset) {
         throw new UnsupportedOperationException("Resetting this type of frame 
by offset is not supported.");
     }
 
@@ -119,15 +117,16 @@ public class FieldPrefixTupleReference implements 
ITreeIndexTupleReference {
 
     public int getSuffixTupleSize() {
         helperTuple.setFieldCount(numPrefixFields, fieldCount - 
numPrefixFields);
-        helperTuple.resetByTupleOffset(frame.getBuffer(), suffixTupleStartOff);
+        helperTuple.resetByTupleOffset(frame.getBuffer().array(), 
suffixTupleStartOff);
         return helperTuple.getTupleSize();
     }
 
     public int getPrefixTupleSize() {
-        if (numPrefixFields == 0)
+        if (numPrefixFields == 0) {
             return 0;
+        }
         helperTuple.setFieldCount(numPrefixFields);
-        helperTuple.resetByTupleOffset(frame.getBuffer(), prefixTupleStartOff);
+        helperTuple.resetByTupleOffset(frame.getBuffer().array(), 
prefixTupleStartOff);
         return helperTuple.getTupleSize();
     }
 

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/pom.xml
----------------------------------------------------------------------
diff --git a/hyracks-fullstack/hyracks/hyracks-storage-am-common/pom.xml 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/pom.xml
index 7ebd27f..1d69439 100644
--- a/hyracks-fullstack/hyracks/hyracks-storage-am-common/pom.xml
+++ b/hyracks-fullstack/hyracks/hyracks-storage-am-common/pom.xml
@@ -80,5 +80,10 @@
       <artifactId>hyracks-data-std</artifactId>
       <version>${project.version}</version>
     </dependency>
+    <dependency>
+      <groupId>junit</groupId>
+      <artifactId>junit</artifactId>
+      <scope>test</scope>
+    </dependency>
   </dependencies>
 </project>

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IMetadataPageManager.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IMetadataPageManager.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IMetadataPageManager.java
index 02390c8..58c837b 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IMetadataPageManager.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IMetadataPageManager.java
@@ -19,55 +19,38 @@
 package org.apache.hyracks.storage.am.common.api;
 
 import org.apache.hyracks.api.exceptions.HyracksDataException;
-import org.apache.hyracks.storage.common.buffercache.ICachedPage;
+import org.apache.hyracks.data.std.api.IPointable;
+import org.apache.hyracks.data.std.api.IValueReference;
 
 /**
  * Used to read from and write to index metadata.
- * The index metadata contains information such as:
- * --The LSN of the index.
- * --Free page information {Set of free pages}
- * --Filter information.
- * TODO: This interface needs to change to have calls to request memory space 
and write to those bytes
+ * The index metadata contains key-value pairs
  */
 public interface IMetadataPageManager extends IPageManager {
-    public static class Constants {
-        public static final long INVALID_LSN_OFFSET = -1;
-        private Constants() {
-        }
-    }
-
-    /**
-     * Locate the filter page in an index file
-     *
-     * @return The offset of the filter page if it exists, or less than zero 
if no filter page exists yet
-     * @throws HyracksDataException
-     */
-    int getFilterPageId() throws HyracksDataException;
-    void setFilterPageId(int filterPageId) throws HyracksDataException;
-    long getLSN() throws HyracksDataException;
-    void setLSN(long lsn) throws HyracksDataException;
-
     /**
-     * Set the cached page to manage for filter data
-     *
-     * @param page
-     *            The page to manage
+     * put the key value pair in the metadata page using the passed frame
+     * @param frame
+     * @param key
+     * @param value
      * @throws HyracksDataException
      */
-    void setFilterPage(ICachedPage page) throws HyracksDataException;
+    void put(ITreeIndexMetadataFrame frame, IValueReference key, 
IValueReference value) throws HyracksDataException;
 
     /**
-     * Get filter page if exists, create and return a new one if it doesn't
-     * @return
+     * get the value of the key from the metadata page using the passed frame
+     * @param frame
+     * @param key
+     * @param value
      * @throws HyracksDataException
      */
-    ICachedPage getFilterPage() throws HyracksDataException;
+    void get(ITreeIndexMetadataFrame frame, IValueReference key, IPointable 
value) throws HyracksDataException;
 
     /**
-     * @return The LSN byte offset in the LSM disk component if the index is 
valid,
-     *         otherwise {@link #INVALID_LSN_OFFSET}.
+     * @param frame
+     * @param key
+     * @return The byte offset in the index file for the entry with the passed 
key if the index is valid and the key
+     *         exists, returns -1 otherwise. use the passed frame to read the 
metadata page
      * @throws HyracksDataException
      */
-    long getLSNOffset() throws HyracksDataException;
-    long getLastMarkerLSN() throws HyracksDataException;
+    long getFileOffset(ITreeIndexMetadataFrame frame, IValueReference key) 
throws HyracksDataException;
 }

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IPageManager.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IPageManager.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IPageManager.java
index 2aee403..b7987f8 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IPageManager.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/IPageManager.java
@@ -50,7 +50,7 @@ public interface IPageManager {
      * Create a metadata frame to be used for reading and writing to metadata 
pages
      * @return a new metadata frame
      */
-    ITreeIndexMetaDataFrame createMetadataFrame();
+    ITreeIndexMetadataFrame createMetadataFrame();
 
     /**
      * Determines where the main metadata page is located in an index file
@@ -82,7 +82,7 @@ public interface IPageManager {
      * @return A page location, or -1 if no free page could be found or 
allocated
      * @throws HyracksDataException
      */
-    int takePage(ITreeIndexMetaDataFrame frame) throws HyracksDataException;
+    int takePage(ITreeIndexMetadataFrame frame) throws HyracksDataException;
 
     /**
      * Get the location of a block of free pages to use for index operations
@@ -92,7 +92,7 @@ public interface IPageManager {
      * @return The starting page location, or -1 if a block of free pages 
could be found or allocated
      * @throws HyracksDataException
      */
-    int takeBlock(ITreeIndexMetaDataFrame frame, int count) throws 
HyracksDataException;
+    int takeBlock(ITreeIndexMetadataFrame frame, int count) throws 
HyracksDataException;
 
     /**
      * Add a page back to the pool of free pages within an index file
@@ -103,7 +103,7 @@ public interface IPageManager {
      *            The page to be returned to the set of free pages
      * @throws HyracksDataException
      */
-    void releasePage(ITreeIndexMetaDataFrame frame, int page) throws 
HyracksDataException;
+    void releasePage(ITreeIndexMetadataFrame frame, int page) throws 
HyracksDataException;
 
     /**
      * Add a page back to the pool of free pages within an index file
@@ -115,7 +115,7 @@ public interface IPageManager {
      *            the number of regular sized pages in the free pages block
      * @throws HyracksDataException
      */
-    void releaseBlock(ITreeIndexMetaDataFrame frame, int page, int count) 
throws HyracksDataException;
+    void releaseBlock(ITreeIndexMetadataFrame frame, int page, int count) 
throws HyracksDataException;
 
     /**
      * Gets the highest page offset according to the metadata
@@ -125,7 +125,7 @@ public interface IPageManager {
      * @return The locaiton of the highest offset page
      * @throws HyracksDataException
      */
-    int getMaxPageId(ITreeIndexMetaDataFrame frame) throws 
HyracksDataException;
+    int getMaxPageId(ITreeIndexMetadataFrame frame) throws 
HyracksDataException;
 
     /**
      * Check whether the index is empty or not.

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexFrame.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexFrame.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexFrame.java
index 037c183..8e7834f 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexFrame.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexFrame.java
@@ -31,6 +31,21 @@ import 
org.apache.hyracks.storage.common.buffercache.IExtraPageBlockHelper;
 
 public interface ITreeIndexFrame {
 
+    public static class Constants {
+        /*
+         * Storage version #. Change this if you alter any tree frame formats 
to stop
+         * possible corruption from old versions reading new formats.
+         */
+        public static final int VERSION = 5;
+        public static final int TUPLE_COUNT_OFFSET = 0;
+        public static final int FREE_SPACE_OFFSET = TUPLE_COUNT_OFFSET + 4;
+        public static final int LEVEL_OFFSET = FREE_SPACE_OFFSET + 4;
+        public static final int RESERVED_HEADER_SIZE = LEVEL_OFFSET + 1;
+
+        private Constants() {
+        }
+    }
+
     public void initBuffer(byte level);
 
     public FrameOpSpaceStatus hasSpaceInsert(ITupleReference tuple) throws 
HyracksDataException;
@@ -73,7 +88,7 @@ public interface ITreeIndexFrame {
     public String printHeader();
 
     public void split(ITreeIndexFrame rightFrame, ITupleReference tuple, 
ISplitKey splitKey,
-                      IExtraPageBlockHelper extraPageBlockHelper, IBufferCache 
bufferCache)
+            IExtraPageBlockHelper extraPageBlockHelper, IBufferCache 
bufferCache)
             throws HyracksDataException, TreeIndexException;
 
     public ISlotManager getSlotManager();

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrame.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrame.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrame.java
deleted file mode 100644
index f49972c..0000000
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrame.java
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-
-package org.apache.hyracks.storage.am.common.api;
-
-import org.apache.hyracks.storage.common.buffercache.ICachedPage;
-
-public interface ITreeIndexMetaDataFrame {
-
-    // Storage version #. Change this if you alter any tree frame formats to 
stop
-    // possible corruption from old versions reading new formats.
-    int VERSION = 4;
-
-    public void initBuffer();
-
-    public void setPage(ICachedPage page);
-
-    public ICachedPage getPage();
-
-    public byte getLevel();
-
-    public void setLevel(byte level);
-
-    public int getNextMetadataPage();
-
-    public void setNextPage(int nextPage);
-
-    public int getMaxPage();
-
-    public void setMaxPage(int maxPage);
-
-    public int getFreePage();
-
-    public boolean hasSpace();
-
-    public void addFreePage(int freePage);
-
-    // Special flag for LSM-Components to mark whether they are valid or not.
-    public boolean isValid();
-
-    // Set special validity flag.
-    public void setValid(boolean isValid);
-
-    // Return the lsm component filter page id.
-    public int getLSMComponentFilterPageId();
-
-    // Set the lsm component filter page id.
-    public void setLSMComponentFilterPageId(int filterPage);
-
-    // Special placeholder for LSN information. Used for transactional LSM 
indexes.
-    public long getLSN();
-
-    public void setLSN(long lsn);
-
-    public int getVersion();
-
-    // Special placeholder for LSN information of a marker log. used for 
rollback information
-    public long getLastMarkerLSN();
-
-    public void setLastMarkerLSN(long lsn);
-
-    void setRootPageNumber(int rootPage);
-
-    int getRootPageNumber();
-
-    boolean isMetadataPage();
-
-    boolean isFreePage();
-}

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrameFactory.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrameFactory.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrameFactory.java
deleted file mode 100644
index ff7deaf..0000000
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetaDataFrameFactory.java
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License.  You may obtain a copy of the License at
- *
- *   http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied.  See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-
-package org.apache.hyracks.storage.am.common.api;
-
-public interface ITreeIndexMetaDataFrameFactory {
-    public ITreeIndexMetaDataFrame createFrame();
-}

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrame.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrame.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrame.java
new file mode 100644
index 0000000..7efc469
--- /dev/null
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrame.java
@@ -0,0 +1,165 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.hyracks.storage.am.common.api;
+
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.api.IPointable;
+import org.apache.hyracks.data.std.api.IValueReference;
+import org.apache.hyracks.storage.common.buffercache.ICachedPage;
+
+/**
+ * A frame for reading and writing metadata pages of an index
+ * It can also be used to read metadata of non metadata pages
+ */
+public interface ITreeIndexMetadataFrame {
+    /**
+     * initialize the metadata page
+     */
+    void init();
+
+    /**
+     * Set the page in the frame
+     * @param page
+     */
+    void setPage(ICachedPage page);
+
+    /**
+     * @return the page set in this frame
+     */
+    ICachedPage getPage();
+
+    /**
+     * The page level.
+     * This method can be run on any type of page
+     */
+    byte getLevel();
+
+    /**
+     * Set the page level
+     * @param level
+     */
+    void setLevel(byte level);
+
+    /**
+     * Get the next metadata page if this page is linked to other metadata 
pages
+     * Return a negative value otherwise
+     * @return
+     */
+    int getNextMetadataPage();
+
+    /**
+     * Link this metadata page to another one
+     * @param nextPage
+     */
+    void setNextMetadataPage(int nextPage);
+
+    /**
+     * @return the max index file page as indicated by the current metadata 
page
+     */
+    int getMaxPage();
+
+    /**
+     * Set the max page of the file
+     * @param maxPage
+     */
+    void setMaxPage(int maxPage);
+
+    /**
+     * Get a free page from the page
+     * @return
+     */
+    int getFreePage();
+
+    /**
+     * Get the remaining space in the metadata page
+     * @return
+     */
+    int getSpace();
+
+    /**
+     * add a new free page to the metadata page
+     * @param freePage
+     */
+    void addFreePage(int freePage);
+
+    /**
+     * get the value with the key = key
+     * @param key
+     * @param value
+     */
+    void get(IValueReference key, IPointable value);
+
+    /**
+     * set the value with the key = key
+     * @param key
+     * @param value
+     * @throws HyracksDataException
+     */
+    void put(IValueReference key, IValueReference value) throws 
HyracksDataException;
+
+    /**
+     * @return true if the index is valid according to the metadata page, 
false otherwise
+     */
+    boolean isValid();
+
+    /**
+     * Sets the index to be valid in the metadata page
+     * @param valid
+     */
+    void setValid(boolean valid);
+
+    /**
+     * Get the storage version associated with this index
+     * @return
+     */
+    int getVersion();
+
+    /**
+     * Set the index root page id
+     * @param rootPage
+     */
+    void setRootPageId(int rootPage);
+
+    /**
+     * @return the index root page id
+     */
+    int getRootPageId();
+
+    /**
+     * @return the number of key value pairs
+     */
+    int getTupleCount();
+
+    /**
+     * return the offset to the entry of the passed key, -1, otherwise
+     * @param key
+     */
+    int getOffset(IValueReference key);
+
+    /**
+     * @return true if the inspected page is a metadata page, false otherwise
+     */
+    boolean isMetadataPage();
+
+    /**
+     * @return true if the inspected page is a free page, false otherwise
+     */
+    boolean isFreePage();
+}

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrameFactory.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrameFactory.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrameFactory.java
new file mode 100644
index 0000000..7018743
--- /dev/null
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexMetadataFrameFactory.java
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.hyracks.storage.am.common.api;
+
+@FunctionalInterface
+public interface ITreeIndexMetadataFrameFactory {
+    ITreeIndexMetadataFrame createFrame();
+}

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexTupleReference.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexTupleReference.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexTupleReference.java
index 6b041eb..42f0ed5 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexTupleReference.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/api/ITreeIndexTupleReference.java
@@ -19,8 +19,6 @@
 
 package org.apache.hyracks.storage.am.common.api;
 
-import java.nio.ByteBuffer;
-
 import org.apache.hyracks.dataflow.common.data.accessors.ITupleReference;
 
 public interface ITreeIndexTupleReference extends ITupleReference {
@@ -28,7 +26,7 @@ public interface ITreeIndexTupleReference extends 
ITupleReference {
 
     public void setFieldCount(int fieldStartIndex, int fieldCount);
 
-    public void resetByTupleOffset(ByteBuffer buf, int tupleStartOffset);
+    public void resetByTupleOffset(byte[] buf, int tupleStartOffset);
 
     public void resetByTupleIndex(ITreeIndexFrame frame, int tupleIndex);
 

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/dataflow/IndexDataflowHelper.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/dataflow/IndexDataflowHelper.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/dataflow/IndexDataflowHelper.java
index 5099df1..c6d4e35 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/dataflow/IndexDataflowHelper.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/dataflow/IndexDataflowHelper.java
@@ -30,7 +30,7 @@ import org.apache.hyracks.storage.am.common.api.IIndex;
 import org.apache.hyracks.storage.am.common.api.IIndexDataflowHelper;
 import org.apache.hyracks.storage.am.common.api.IPageManagerFactory;
 import org.apache.hyracks.storage.am.common.api.IResourceLifecycleManager;
-import org.apache.hyracks.storage.am.common.frames.LIFOMetaDataFrame;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexFrame;
 import org.apache.hyracks.storage.common.file.ILocalResourceFactory;
 import org.apache.hyracks.storage.common.file.ILocalResourceRepository;
 import org.apache.hyracks.storage.common.file.IResourceIdFactory;
@@ -99,7 +99,7 @@ public abstract class IndexDataflowHelper implements 
IIndexDataflowHelper {
                         .getLocalResourceFactory();
                 
localResourceRepository.insert(localResourceFactory.createLocalResource(resourceID,
 resourceRef
                         .getRelativePath(),
-                        LIFOMetaDataFrame.VERSION, partition));
+                        ITreeIndexFrame.Constants.VERSION, partition));
             } catch (IOException e) {
                 throw new HyracksDataException(e);
             }

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrame.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrame.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrame.java
index 7d33519..de890c4 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrame.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrame.java
@@ -16,44 +16,40 @@
  * specific language governing permissions and limitations
  * under the License.
  */
-
 package org.apache.hyracks.storage.am.common.frames;
 
 import java.nio.ByteBuffer;
 
-import org.apache.hyracks.storage.am.common.api.ITreeIndexMetaDataFrame;
+import org.apache.hyracks.api.exceptions.HyracksDataException;
+import org.apache.hyracks.data.std.api.IPointable;
+import org.apache.hyracks.data.std.api.IValueReference;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexFrame;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexFrame.Constants;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexMetadataFrame;
 import org.apache.hyracks.storage.common.buffercache.ICachedPage;
 
-// all meta pages of this kind have a negative level
-// the first meta page has level -1, all other meta pages have level -2
-// the first meta page is special because it guarantees to have a correct max 
page
-// other meta pages (i.e., with level -2) have junk in the max page field
-
-public class LIFOMetaDataFrame implements ITreeIndexMetaDataFrame {
+/**
+ * Frame content
+ * [ Headers defined in {@link ITreeIndexFrame}][max page][next page][valid]
+ * [storage version][root page][free page count][k1 length][k1][v1 length][v1]
+ * [k2 length][k2][v2 length][v2].......
+ * ....
+ * ....
+ * [free page 5][free page 4][free page 3][free page 2][free page 1]
+ *
+ */
+public class LIFOMetaDataFrame implements ITreeIndexMetadataFrame {
 
     private static final byte META_PAGE_LEVEL_INDICATOR = -1;
     private static final byte FREE_PAGE_LEVEL_INDICATOR = -2;
-
-    // Arbitrarily chosen magic integer.
-    protected static final int OBSOLETE_MAGIC_VALID_INT = 0x5bd1e995;
     protected static final int MAGIC_VALID_INT = 0x1B16DA7A;
-
-    protected static final int TUPLE_COUNT_OFFSET = 0; //0
-    protected static final int FREE_SPACE_OFFSET = TUPLE_COUNT_OFFSET + 4; //4
-    protected static final int MAX_PAGE_OFFSET = FREE_SPACE_OFFSET + 4; //8
-    protected static final int LEVEL_OFFSET = MAX_PAGE_OFFSET + 12; //20
-    protected static final int NEXT_PAGE_OFFSET = LEVEL_OFFSET + 1; // 21
-    protected static final int VALID_OFFSET = NEXT_PAGE_OFFSET + 4; // 25
-
-    // The ADDITIONAL_FILTERING_PAGE_OFF is used only for LSM indexes.
-    // We store the page id that will be used to store the information of the 
the filter that is associated with a disk component.
-    // It is only set in the first meta page other meta pages (i.e., with 
level -2) have junk in the max page field.
-    private static final int ADDITIONAL_FILTERING_PAGE_OFFSET = VALID_OFFSET + 
4; // 29
-    public static final int LSN_OFFSET = ADDITIONAL_FILTERING_PAGE_OFFSET + 4; 
// 33
-    private static final int LAST_MARKER_LSN_OFFSET = LSN_OFFSET + 8; // 41
-    public static final int STORAGE_VERSION_OFFSET = LAST_MARKER_LSN_OFFSET + 
4; //45
-    public static final int ROOT_PAGE_NUMBER = STORAGE_VERSION_OFFSET + 4; //49
-    private static final int HEADER_END_OFFSET = ROOT_PAGE_NUMBER + 4; // 53
+    protected static final int MAX_PAGE_OFFSET = 
ITreeIndexFrame.Constants.RESERVED_HEADER_SIZE;
+    protected static final int NEXT_PAGE_OFFSET = MAX_PAGE_OFFSET + 4;
+    protected static final int VALID_OFFSET = NEXT_PAGE_OFFSET + 4;
+    protected static final int STORAGE_VERSION_OFFSET = VALID_OFFSET + 4;
+    protected static final int ROOT_PAGE_OFFSET = STORAGE_VERSION_OFFSET + 4;
+    protected static final int FREE_PAGE_COUNT_OFFSET = ROOT_PAGE_OFFSET + 4;
+    protected static final int HEADER_END_OFFSET = FREE_PAGE_COUNT_OFFSET + 4;
 
     protected ICachedPage page = null;
     protected ByteBuffer buf = null;
@@ -70,44 +66,35 @@ public class LIFOMetaDataFrame implements 
ITreeIndexMetaDataFrame {
 
     @Override
     public int getFreePage() {
-        int tupleCount = buf.getInt(TUPLE_COUNT_OFFSET);
-        if (tupleCount > 0) {
-            // return the last page from the linked list of free pages
-            // TODO: this is a dumb policy, but good enough for now
-            int lastPageOff = buf.getInt(FREE_SPACE_OFFSET) - 4;
-            buf.putInt(FREE_SPACE_OFFSET, lastPageOff);
-            buf.putInt(TUPLE_COUNT_OFFSET, tupleCount - 1);
-            return buf.getInt(lastPageOff);
-        } else {
-            return -1;
+        int freePages = buf.getInt(FREE_PAGE_COUNT_OFFSET);
+        if (freePages > 0) {
+            decrement(FREE_PAGE_COUNT_OFFSET);
+            return buf.getInt(buf.array().length - Integer.BYTES * freePages);
         }
+        return -1;
     }
 
-    // must be checked before adding free page
-    // user of this class is responsible for getting a free page as a new meta
-    // page, latching it, etc. if there is no space on this page
     @Override
-    public boolean hasSpace() {
-        return buf.getInt(FREE_SPACE_OFFSET) + 4 < buf.capacity();
+    public int getSpace() {
+        return buf.array().length - buf.getInt(Constants.FREE_SPACE_OFFSET) - 
(Integer.BYTES * buf.getInt(
+                FREE_PAGE_COUNT_OFFSET));
     }
 
-    // no bounds checking is done, there must be free space
     @Override
     public void addFreePage(int freePage) {
-        int freeSpace = buf.getInt(FREE_SPACE_OFFSET);
-        buf.putInt(freeSpace, freePage);
-        buf.putInt(FREE_SPACE_OFFSET, freeSpace + 4);
-        buf.putInt(TUPLE_COUNT_OFFSET, buf.getInt(TUPLE_COUNT_OFFSET) + 1);
+        increment(FREE_PAGE_COUNT_OFFSET);
+        int numFreePages = buf.getInt(FREE_PAGE_COUNT_OFFSET);
+        buf.putInt(buf.array().length - (Integer.BYTES * numFreePages), 
freePage);
     }
 
     @Override
     public byte getLevel() {
-        return buf.get(LEVEL_OFFSET);
+        return buf.get(Constants.LEVEL_OFFSET);
     }
 
     @Override
     public void setLevel(byte level) {
-        buf.put(LEVEL_OFFSET, level);
+        buf.put(Constants.LEVEL_OFFSET, level);
     }
 
     @Override
@@ -122,16 +109,15 @@ public class LIFOMetaDataFrame implements 
ITreeIndexMetaDataFrame {
     }
 
     @Override
-    public void initBuffer() {
-        buf.putInt(TUPLE_COUNT_OFFSET, 0);
-        buf.putInt(FREE_SPACE_OFFSET, HEADER_END_OFFSET);
+    public void init() {
+        buf.putInt(Constants.TUPLE_COUNT_OFFSET, 0);
+        buf.putInt(Constants.FREE_SPACE_OFFSET, HEADER_END_OFFSET);
         buf.putInt(MAX_PAGE_OFFSET, 0);
-        buf.put(LEVEL_OFFSET, META_PAGE_LEVEL_INDICATOR);
+        buf.put(Constants.LEVEL_OFFSET, META_PAGE_LEVEL_INDICATOR);
         buf.putInt(NEXT_PAGE_OFFSET, -1);
-        buf.putInt(ADDITIONAL_FILTERING_PAGE_OFFSET, -1);
-        buf.putLong(LAST_MARKER_LSN_OFFSET, -1L);
-        buf.putInt(ROOT_PAGE_NUMBER, 1);
-        buf.putInt(STORAGE_VERSION_OFFSET, VERSION);
+        buf.putInt(ROOT_PAGE_OFFSET, 1);
+        buf.putInt(FREE_PAGE_COUNT_OFFSET, 0);
+        buf.putInt(STORAGE_VERSION_OFFSET, ITreeIndexFrame.Constants.VERSION);
         setValid(false);
     }
 
@@ -141,80 +127,191 @@ public class LIFOMetaDataFrame implements 
ITreeIndexMetaDataFrame {
     }
 
     @Override
-    public void setNextPage(int nextPage) {
+    public void setNextMetadataPage(int nextPage) {
         buf.putInt(NEXT_PAGE_OFFSET, nextPage);
     }
 
     @Override
     public boolean isValid() {
-        return buf.getInt(VALID_OFFSET) == MAGIC_VALID_INT || 
buf.getInt(VALID_OFFSET) == OBSOLETE_MAGIC_VALID_INT;
+        return buf.getInt(VALID_OFFSET) == MAGIC_VALID_INT;
     }
 
     @Override
     public void setValid(boolean isValid) {
-        if (isValid) {
-            buf.putInt(VALID_OFFSET, MAGIC_VALID_INT);
-        } else {
-            buf.putInt(VALID_OFFSET, 0);
-        }
+        buf.putInt(VALID_OFFSET, isValid ? MAGIC_VALID_INT : 0);
     }
 
     @Override
-    public long getLSN() {
-        return buf.getLong(LSN_OFFSET);
+    public int getVersion() {
+        return buf.getInt(STORAGE_VERSION_OFFSET);
     }
 
     @Override
-    public void setLSN(long lsn) {
-        buf.putLong(LSN_OFFSET, lsn);
+    public void setRootPageId(int rootPage) {
+        buf.putInt(ROOT_PAGE_OFFSET, rootPage);
     }
 
     @Override
-    public int getVersion() {
-        if (buf.getInt(VALID_OFFSET) == OBSOLETE_MAGIC_VALID_INT) {
-            return VERSION * -1;
-        } else {
-            return buf.getInt(STORAGE_VERSION_OFFSET);
-        }
+    public int getRootPageId() {
+        return buf.getInt(ROOT_PAGE_OFFSET);
     }
 
     @Override
-    public long getLastMarkerLSN() {
-        return buf.getLong(LAST_MARKER_LSN_OFFSET);
+    public boolean isMetadataPage() {
+        return getLevel() == META_PAGE_LEVEL_INDICATOR;
     }
 
     @Override
-    public void setLastMarkerLSN(long lsn) {
-        buf.putLong(LAST_MARKER_LSN_OFFSET, lsn);
+    public boolean isFreePage() {
+        return getLevel() == FREE_PAGE_LEVEL_INDICATOR;
     }
 
     @Override
-    public int getLSMComponentFilterPageId() {
-        return buf.getInt(ADDITIONAL_FILTERING_PAGE_OFFSET);
+    public void get(IValueReference key, IPointable value) {
+        int tupleCount = getTupleCount();
+        int tupleStart = getTupleStart(0);
+        for (int i = 0; i < tupleCount; i++) {
+            if (isInner(key, tupleStart)) {
+                get(tupleStart + key.getLength() + Integer.BYTES, value);
+                return;
+            }
+            tupleStart = getNextTupleStart(tupleStart);
+        }
+        value.set(null, 0, 0);
     }
 
-    @Override
-    public void setLSMComponentFilterPageId(int filterPage) {
-        buf.putInt(ADDITIONAL_FILTERING_PAGE_OFFSET, filterPage);
+    private int find(IValueReference key) {
+        int tupleCount = getTupleCount();
+        int tupleStart = getTupleStart(0);
+        for (int i = 0; i < tupleCount; i++) {
+            if (isInner(key, tupleStart)) {
+                return i;
+            }
+            tupleStart = getNextTupleStart(tupleStart);
+        }
+        return -1;
+    }
+
+    private void get(int offset, IPointable value) {
+        int valueLength = buf.getInt(offset);
+        value.set(buf.array(), offset + Integer.BYTES, valueLength);
+    }
+
+    private static final int compare(byte[] b1, int s1, byte[] b2, int s2, int 
l) {
+        for (int i = 0; i < l; i++) {
+            if (b1[s1 + i] != b2[s2 + i]) {
+                return b1[s1 + i] - b2[s2 + i];
+            }
+        }
+        return 0;
+    }
+
+    private boolean isInner(IValueReference key, int tupleOffset) {
+        int keySize = buf.getInt(tupleOffset);
+        if (keySize == key.getLength()) {
+            return LIFOMetaDataFrame.compare(key.getByteArray(), 
key.getStartOffset(), buf.array(), tupleOffset
+                    + Integer.BYTES, keySize) == 0;
+        }
+        return false;
+    }
+
+    private int getTupleStart(int index) {
+        int offset = HEADER_END_OFFSET;
+        int i = 0;
+        while (i < index) {
+            i++;
+            offset = getNextTupleStart(offset);
+        }
+        return offset;
+    }
+
+    private int getNextTupleStart(int prevTupleOffset) {
+        int keyLength = buf.getInt(prevTupleOffset);
+        int offset = prevTupleOffset + keyLength + Integer.BYTES;
+        return offset + buf.getInt(offset) + Integer.BYTES;
+    }
+
+    private void put(int index, IValueReference value) throws 
HyracksDataException {
+        int offset = getTupleStart(index);
+        int length = buf.getInt(offset);
+        offset += Integer.BYTES + length;
+        length = buf.getInt(offset);
+        if (length != value.getLength()) {
+            throw new HyracksDataException("This frame doesn't support 
overwriting dynamically sized values");
+        }
+        offset += Integer.BYTES;
+        System.arraycopy(value.getByteArray(), value.getStartOffset(), 
buf.array(), offset, value.getLength());
     }
 
     @Override
-    public void setRootPageNumber(int rootPage) {
-        buf.putInt(ROOT_PAGE_NUMBER, rootPage);
+    public void put(IValueReference key, IValueReference value) throws 
HyracksDataException {
+        int index = find(key);
+        if (index >= 0) {
+            put(index, value);
+        } else {
+            int offset = buf.getInt(Constants.FREE_SPACE_OFFSET);
+            int available = getSpace();
+            int required = key.getLength() + Integer.BYTES + Integer.BYTES + 
value.getLength();
+            if (available < required) {
+                throw new HyracksDataException("Available space in the page ("
+                        + available + ") is not enough to store the key value 
pair(" + required + ")");
+            }
+            buf.putInt(offset, key.getLength());
+            offset += Integer.BYTES;
+            System.arraycopy(key.getByteArray(), key.getStartOffset(), 
buf.array(), offset, key.getLength());
+            offset += key.getLength();
+            buf.putInt(offset, value.getLength());
+            offset += Integer.BYTES;
+            System.arraycopy(value.getByteArray(), value.getStartOffset(), 
buf.array(), offset, value.getLength());
+            offset += value.getLength();
+            increment(Constants.TUPLE_COUNT_OFFSET);
+            buf.putInt(Constants.FREE_SPACE_OFFSET, offset);
+        }
     }
 
     @Override
-    public int getRootPageNumber() {
-        return buf.getInt(ROOT_PAGE_NUMBER);
+    public int getTupleCount() {
+        return buf.getInt(Constants.TUPLE_COUNT_OFFSET);
+    }
+
+    private void increment(int offset) {
+        buf.putInt(offset, buf.getInt(offset) + 1);
+    }
+
+    private void decrement(int offset) {
+        buf.putInt(offset, buf.getInt(offset) - 1);
     }
 
     @Override
-    public boolean isMetadataPage() {
-        return getLevel() == META_PAGE_LEVEL_INDICATOR;
+    public int getOffset(IValueReference key) {
+        int index = find(key);
+        if (index >= 0) {
+            int offset = getTupleStart(index);
+            return offset + key.getLength() + 2 * Integer.BYTES;
+        }
+        return -1;
     }
 
     @Override
-    public boolean isFreePage() {
-        return getLevel() == FREE_PAGE_LEVEL_INDICATOR;
+    public String toString() {
+        StringBuilder aString = new 
StringBuilder(this.getClass().getSimpleName()).append('\n').
+                append("Tuple Count: " + getTupleCount()).append('\n').
+                append("Free Space offset: " + 
buf.getInt(Constants.FREE_SPACE_OFFSET)).append('\n').
+                append("Level: " + 
buf.get(Constants.LEVEL_OFFSET)).append('\n').
+                append("Version: " + 
buf.getInt(STORAGE_VERSION_OFFSET)).append('\n').
+                append("Max Page: " + 
buf.getInt(MAX_PAGE_OFFSET)).append('\n').
+                append("Root Page: " + 
buf.getInt(ROOT_PAGE_OFFSET)).append('\n').
+                append("Number of free pages: " + 
buf.getInt(FREE_PAGE_COUNT_OFFSET));
+        int tupleCount = getTupleCount();
+        int offset;
+        for (int i = 0; i < tupleCount; i++) {
+            offset = getTupleStart(i);
+            int keyLength = buf.getInt(offset);
+            aString.append('\n').append("Key " + i + " size = " + keyLength);
+            offset += Integer.BYTES + keyLength;
+            int valueLength = buf.getInt(offset);
+            aString.append(", Value " + i + " size = " + valueLength);
+        }
+        return aString.toString();
     }
 }

http://git-wip-us.apache.org/repos/asf/asterixdb/blob/90cdbac7/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrameFactory.java
----------------------------------------------------------------------
diff --git 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrameFactory.java
 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrameFactory.java
index b0406c2..4dbba02 100644
--- 
a/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrameFactory.java
+++ 
b/hyracks-fullstack/hyracks/hyracks-storage-am-common/src/main/java/org/apache/hyracks/storage/am/common/frames/LIFOMetaDataFrameFactory.java
@@ -18,12 +18,12 @@
  */
 package org.apache.hyracks.storage.am.common.frames;
 
-import org.apache.hyracks.storage.am.common.api.ITreeIndexMetaDataFrame;
-import org.apache.hyracks.storage.am.common.api.ITreeIndexMetaDataFrameFactory;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexMetadataFrame;
+import org.apache.hyracks.storage.am.common.api.ITreeIndexMetadataFrameFactory;
 
-public class LIFOMetaDataFrameFactory implements 
ITreeIndexMetaDataFrameFactory {
+public class LIFOMetaDataFrameFactory implements 
ITreeIndexMetadataFrameFactory {
     @Override
-    public ITreeIndexMetaDataFrame createFrame() {
+    public ITreeIndexMetadataFrame createFrame() {
         return new LIFOMetaDataFrame();
     }
 }

Reply via email to