@Override public void insertKey(Key key) throws JasDBStorageException { if(isLeave) { addKey(key); modified = true; if(treeNodes.size() > persister.getMaxKeys()) { List<TreeNode>[] leaveValues = treeNodes.split(); List<TreeNode> leftLeaves = leaveValues[0]; List<TreeNode> rightLeaves = leaveValues[1]; treeNodes.reset(); LeaveBlockImpl leftLeaveBlock = (LeaveBlockImpl) persister.createBlock(BlockTypes.LEAVEBLOCK, getPosition()); LeaveBlockImpl rightLeaveBlock = (LeaveBlockImpl) persister.createBlock(BlockTypes.LEAVEBLOCK, getPosition()); leftLeaveBlock.setNext(rightLeaveBlock.getPosition()); rightLeaveBlock.setPrevious(leftLeaveBlock.getPosition()); addKeys(leftLeaves, leftLeaveBlock); addKeys(rightLeaves, rightLeaveBlock); Key promoteKey = leftLeaves.get(leftLeaves.size() - 1).getKey(); TreeNode rootNode = new TreeNode(promoteKey, leftLeaveBlock.getPosition(), rightLeaveBlock.getPosition()); treeNodes.put(promoteKey, rootNode); isLeave = false; RootBlockFactory.writeHeader(getDataBlock(), false); } } else { throw new JasDBStorageException("Unable to store key, root is not a leave"); } }
private void handleBlockOverflow() throws JasDBStorageException { if(treeNodes.size() > persister.getMaxKeys()) { List<TreeNode>[] blockNodeSplit = treeNodes.split(); List<TreeNode> leftBlockNodes = blockNodeSplit[0]; List<TreeNode> rightBlockNodes = blockNodeSplit[1]; treeNodes.reset(); Key promoteKey = rightBlockNodes.get(0).getKey(); TreeBlock leftBlock = (TreeBlock) persister.createBlock(BlockTypes.NODEBLOCK, getParentPointer()); leftBlock.addNodes(leftBlockNodes, null, leftBlock.getPosition()); if(parentPointer != -1) { //add the nodes, we use -1 as parent does not need to be changed addNodes(rightBlockNodes, promoteKey, getPosition()); TreeBlock parentBlock = (TreeBlock) persister.loadBlock(parentPointer); parentBlock.insertBlock(promoteKey, leftBlock, this); } else { //we are at the root TreeBlock rightBlock = (TreeBlock) persister.createBlock(BlockTypes.NODEBLOCK, getPosition()); rightBlock.addNodes(rightBlockNodes, promoteKey, rightBlock.getPosition()); TreeNode node = new TreeNode(promoteKey, leftBlock.getPosition(), rightBlock.getPosition()); treeNodes.put(node.getKey(), node); } } }
@Override public void insertIntoIndex(Key key) throws JasDBStorageException { openIndex(); StatRecord btreeInsertRecord = StatisticsMonitor.createRecord("btree:insert"); resourceLockManager.sharedLock(); lockManager.startLockChain(); lockManager.acquireLock(LockIntentType.LEAVELOCK_OPTIMISTIC, rootBlock); try { LeaveBlock leaveBlock = rootBlock.findLeaveBlock(LockIntentType.LEAVELOCK_OPTIMISTIC, key); if(leaveBlock.size() == persister.getMaxKeys()) { lockManager.releaseLockChain(); lockManager.startLockChain(); lockManager.acquireLock(LockIntentType.WRITE_EXCLUSIVE, rootBlock); leaveBlock = rootBlock.findLeaveBlock(LockIntentType.WRITE_EXCLUSIVE, key); doLeaveBlockInsert(leaveBlock, key); } else { //no overflow, we can just write into the leave doLeaveBlockInsert(leaveBlock, key); } } finally { lockManager.releaseLockChain(); resourceLockManager.sharedUnlock(); btreeInsertRecord.stop(); } }
private void handleBlockOverflow() throws JasDBStorageException { if(leaves.size() > persister.getMaxKeys()) { List<Key>[] splittedKeys = leaves.split(); this.leaves.reset(); /* this block keeps representing the right half, the last current block key == max right */ List<Key> rightKeys = splittedKeys[1]; addKeys(rightKeys); List<Key> leftKeys = splittedKeys[0]; long currentPrevious = leaveProperties.getPreviousBlock(); LeaveBlockImpl leftLeaveBlock = (LeaveBlockImpl) persister.createBlock(BlockTypes.LEAVEBLOCK, leaveProperties.getParentPointer()); leftLeaveBlock.setPrevious(currentPrevious); leftLeaveBlock.setNext(getPosition()); leftLeaveBlock.addKeys(leftKeys); this.recalculateMemorySize(); leftLeaveBlock.recalculateMemorySize(); if(currentPrevious != -1) { //we need to relink, there is a previous block present LeaveBlockImpl previousBlock = (LeaveBlockImpl) persister.loadBlock(currentPrevious); previousBlock.setNext(leftLeaveBlock.getPosition()); } leaveProperties.setPreviousBlock(leftLeaveBlock.getPosition()); TreeBlock parentBlock = (TreeBlock) persister.loadBlock(leaveProperties.getParentPointer()); parentBlock.insertBlock(leftLeaveBlock.getLast(), leftLeaveBlock, this); } }