📄 allocextent.java
字号:
extentStatus &= ~HAS_FREE; } protected boolean canAddFreePage(long lastAllocatedPage) { // the last page to be allocated == extentEnd if (extentStart + extentLength <= extentEnd) return true; // else, check to see if this may have any free page if (!mayHaveFreePage()) return false; // we may have a free page, but that is not certain, double check if (lastAllocatedPage < extentStart) return (freePages.anySetBit() != -1); else return ((freePages.anySetBit((int)(lastAllocatedPage-extentStart))) != -1); } /** Return the status of a particular page */ protected int getPageStatus(long pagenum) { if (SanityManager.DEBUG) checkInRange(pagenum); int status = 0; int bitnum = (int)(pagenum-extentStart); if (freePages.isSet(bitnum)) status = FREE_PAGE; else status = ALLOCATED_PAGE; return status; } /** Get the first logical page number managed by this extent. */ protected long getFirstPagenum() { return extentStart; } /** Get the last logical page number managed by this extent. */ protected long getLastPagenum() { return extentStart+extentLength-1; } /** * translate bit position in map to page number. * <p> * * @return The page number of this "bit" in the extent map. * * @exception StandardException Standard exception policy. **/ protected long getPagenum(int bit_pos) { return(extentStart + bit_pos); } /* * page preallocation */ /** * get the last preallocated pagenumber managed by this alloc page */ protected long getLastPreallocPagenum() { if (extentLength > preAllocLength) preAllocLength = extentLength; return extentStart + preAllocLength - 1 ; } /** preallocated N pages, passed in the last preallocated page number. */ protected void setLastPreallocPagenum(long preAllocPagenum) { if (SanityManager.DEBUG) SanityManager.ASSERT(preAllocPagenum >= getLastPreallocPagenum(), "setLastPreallocPagenum set to small prealloc length than before"); // cannot prealloc more than this extent can handle if (preAllocPagenum > extentEnd) preAllocPagenum = extentEnd; preAllocLength = (int)(preAllocPagenum - extentStart + 1); } /* Get the logical page number that is bigger than prevPageNumber and is a valid page. If no such page in this extent, return ContainerHandle.INVALID_PAGE_HANDLE */ protected long getNextValidPageNumber(long prevPageNumber) { long pageNum; long lastpage = getLastPagenum(); if (prevPageNumber < extentStart) pageNum = extentStart; else pageNum = prevPageNumber +1; while(pageNum <= lastpage) { int status = getPageStatus(pageNum); if (status == ALLOCATED_PAGE) break; pageNum++; } if (pageNum > lastpage) pageNum = ContainerHandle.INVALID_PAGE_NUMBER; return pageNum; } protected long getLastValidPageNumber() { long pageNum = getLastPagenum(); while(pageNum >= extentStart) { int status = getPageStatus(pageNum); if (status == ALLOCATED_PAGE) break; pageNum--; } if (pageNum < extentStart) pageNum = ContainerHandle.INVALID_PAGE_NUMBER; return pageNum; } private void checkInRange(long pagenum) { if (SanityManager.DEBUG) if (pagenum < extentStart || pagenum >= extentStart+extentLength) SanityManager.THROWASSERT( "pagenum " + pagenum + " out of range"); } protected void updateUnfilledPageInfo(AllocExtent inputExtent) { if (SanityManager.DEBUG) { if (inputExtent.unFilledPages.getLength() != unFilledPages.getLength()) { SanityManager.THROWASSERT( "inputExtent's unfilled page length " + inputExtent.unFilledPages.getLength() + " != extent's unfilled page length " + unFilledPages.getLength()); } } // just use the passed in inputExtent, we know (wink wink) that the // unfilled page info is being updated just when the allocation cache // is being invalidated. Nobody is going to have a reference to the // inputExtent after this so is it save to share the FormatableBitSet. // if we cannot guarentee that the inputExtent will be unchanged by the // caller, we need to copy it // unFilledPages = new FormatableBitSet(inputExtent.unFilledPages); // Right now, just reference it directly unFilledPages = inputExtent.unFilledPages; if (unFilledPages.anySetBit() >= 0) extentStatus |= HAS_UNFILLED_PAGES; else extentStatus &= ~HAS_UNFILLED_PAGES; } /* Keep track of unfilled pages, if the extent changed, returns true. */ protected boolean trackUnfilledPage(long pagenumber, boolean unfilled) { checkInRange(pagenumber); int bitnum = (int)(pagenumber-extentStart); boolean bitSet = unFilledPages.isSet(bitnum); if (unfilled != bitSet) { if (unfilled) { unFilledPages.set(bitnum); extentStatus |= HAS_UNFILLED_PAGES; } else unFilledPages.clear(bitnum); return true; } return false; } /** Get a page number that is unfilled, pagenum is the last page that was rejected. */ protected long getUnfilledPageNumber(long pagenum) { if ((extentStatus & HAS_UNFILLED_PAGES) == 0) return ContainerHandle.INVALID_PAGE_NUMBER; int i = unFilledPages.anySetBit(); if (i != -1) { if (i+extentStart != pagenum) return i+extentStart; else { // unfortunately, we found the same page number that // was rejected. It would be unwise to unset bit // pagenum because just because it was rejected does not mean // the page is full, the row we are trying to insert may just // be too big. If we unset it, we will never find that page // again even though it may be a perfectly good page for any // other row. Just get the next set bit. i = unFilledPages.anySetBit(i); if (i != -1) return i+extentStart; } } return ContainerHandle.INVALID_PAGE_NUMBER; } /** Get the number of used page in this extent */ protected int getAllocatedPageCount() { // allocated page is one which is not free or deallocated. int allocatedPageCount = extentLength; if (!mayHaveFreePage()) return allocatedPageCount; byte[] free = freePages.getByteArray(); int numBytes = free.length; for (int i = 0; i < numBytes; i++) { if (free[i] != 0) { for (int j = 0; j < 8; j++) { if (((1 << j) & free[i]) != 0) { allocatedPageCount--; } } } } if (SanityManager.DEBUG) { if (allocatedPageCount < 0) { SanityManager.THROWASSERT( "number of allocated page < 0, val =" + allocatedPageCount + "\nextent = " + toDebugString()); } } return allocatedPageCount; } /** Get the number of unfilled pages in this extent */ protected int getUnfilledPageCount() { int unfilledPageCount = 0; int freePagesSize = freePages.size(); for (int i = 0; i < unFilledPages.size(); i++) { if (unFilledPages.isSet(i) && (i >= freePagesSize || !freePages.isSet(i))) unfilledPageCount++; } if (SanityManager.DEBUG) SanityManager.ASSERT(unfilledPageCount >= 0, "number of unfilled pages < 0"); return unfilledPageCount; } /** Get the total number of pages in this extent */ protected int getTotalPageCount() { return extentLength; } protected String toDebugString() { if (SanityManager.DEBUG) { String str = "------------------------------------------------------------------------------\n" + "Extent map of from page " + extentStart + " to page " + extentEnd + "\n"; for (long i = extentStart; i < extentStart+extentLength; i++) { str += "\tpage " + i + ": "; switch(getPageStatus(i)) { case FREE_PAGE: str += "free page\n"; break; case ALLOCATED_PAGE: str += "valid, in use page\n"; break; } // int bitnum = (int)(i-extentStart); // if (unFilledPages.isSet(bitnum)) // str += " page is estimated to be unfilled\n"; } if (getLastPagenum() < extentEnd) str += "\tFrom " + getLastPagenum() + " to " + extentEnd + " are un-allocated pages\n"; str += "------------------------------------------------------------------------------\n"; return str; } else return null; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -