private byte[] GetLargeItemSegment(PageHeaderBase header, IPage page, long startIndex, long endIndex) { if (PageFormatter.ReadMultipageItemLength(page) <= endIndex) { throw new ArgumentOutOfRangeException(nameof(endIndex)); } var length = endIndex - startIndex + 1; var result = new byte[length]; long sourceOffset = 0; long destOffset = 0; // navigate through large item while (true) { var readBytes = PageFormatter.ReadMultipageItemBlock(page, Math.Min(_pageManager.PageSize, (int)(endIndex + 1 - sourceOffset))); sourceOffset += readBytes.Length; if (sourceOffset > startIndex) { var ssi = sourceOffset - startIndex - 1 < readBytes.Length ? startIndex + readBytes.Length - sourceOffset : 0; var l = readBytes.Length - Math.Max(0, sourceOffset - endIndex - 1) - ssi; Array.Copy(readBytes, ssi, result, destOffset, l); destOffset += l; if (sourceOffset >= endIndex) { return(result); } } var nextPageIndex = ((MultipageItemPageHeader)header).NextPageIndex; if (nextPageIndex != -1) { page = _pageManager.FetchPage(nextPageIndex); header = PageFormatter.GetPageHeader(page); } } }
private byte[] GetFixedSizeItemSegment(PageHeaderBase header, IPage page, DbItemReference reference, long startIndex, long endIndex) { if (!PageFormatter.IsFixedSizeItemAllocated(page, reference.ItemIndex)) { return new byte[] { } } ; var item = PageFormatter.ReadFixedSizeItem(page, reference.ItemIndex); if (item.RawData.Length >= endIndex) { throw new ArgumentOutOfRangeException(nameof(endIndex)); } var length = endIndex - startIndex + 1; var result = new byte[length]; Array.Copy(item.RawData, startIndex, result, 0, length); return(result); }
public void CorrectWriteAndReadAllHeaders() { int pageSize = 4096; var dummyPageManager = new FileSystemPageManager(pageSize); var p = new Page(dummyPageManager, 0, new byte[pageSize]); var hph = new HeadingPageHeader(); PageFormatter.InitPage(p, hph); PageHeaderBase phb = PageFormatter.GetPageHeader(p); Assert.IsInstanceOf <HeadingPageHeader>(phb); Assert.AreEqual(hph.Length, phb.Length); Assert.AreEqual(hph.PageType, phb.PageType); Assert.AreEqual(hph.SizeRange, phb.SizeRange); var fsiph = new FixedSizeItemsPageHeader(); PageFormatter.InitPage(p, fsiph); phb = PageFormatter.GetPageHeader(p); Assert.IsInstanceOf <FixedSizeItemsPageHeader>(phb); Assert.AreEqual(fsiph.Length, phb.Length); Assert.AreEqual(fsiph.PageType, phb.PageType); Assert.AreEqual(fsiph.SizeRange, phb.SizeRange); var mpph = new MultipageItemPageHeader(); PageFormatter.InitPage(p, mpph); phb = PageFormatter.GetPageHeader(p); Assert.IsInstanceOf <MultipageItemPageHeader>(phb); Assert.AreEqual(mpph.Length, phb.Length); Assert.AreEqual(mpph.PageType, phb.PageType); Assert.AreEqual(mpph.SizeRange, phb.SizeRange); Assert.AreEqual(mpph.StartPageIndex, ((MultipageItemPageHeader)phb).StartPageIndex); Assert.AreEqual(mpph.PreviousPageIndex, ((MultipageItemPageHeader)phb).PreviousPageIndex); Assert.AreEqual(mpph.NextPageIndex, ((MultipageItemPageHeader)phb).NextPageIndex); var fsmph = new FreeSpaceMapPageHeader(); PageFormatter.InitPage(p, fsmph); phb = PageFormatter.GetPageHeader(p); Assert.IsInstanceOf <FreeSpaceMapPageHeader>(phb); Assert.AreEqual(fsmph.Length, phb.Length); Assert.AreEqual(fsmph.PageType, phb.PageType); Assert.AreEqual(fsmph.SizeRange, phb.SizeRange); Assert.AreEqual(fsmph.BasePageIndex, ((FreeSpaceMapPageHeader)phb).BasePageIndex); var tnph = new BPlusTreeNodePageHeader(); PageFormatter.InitPage(p, tnph); phb = PageFormatter.GetPageHeader(p); Assert.IsInstanceOf <BPlusTreeNodePageHeader>(phb); Assert.AreEqual(tnph.Length, phb.Length); Assert.AreEqual(tnph.PageType, phb.PageType); Assert.AreEqual(tnph.SizeRange, phb.SizeRange); Assert.AreEqual(tnph.ParentPageIndex, ((BPlusTreeNodePageHeader)phb).ParentPageIndex); Assert.AreEqual(tnph.PreviousPageIndex, ((BPlusTreeNodePageHeader)phb).PreviousPageIndex); Assert.AreEqual(tnph.NextPageIndex, ((BPlusTreeNodePageHeader)phb).NextPageIndex); var rtnph = new RadixTreeNodesPageHeader(); PageFormatter.InitPage(p, rtnph); phb = PageFormatter.GetPageHeader(p); Assert.IsInstanceOf <RadixTreeNodesPageHeader>(phb); Assert.AreEqual(rtnph.Length, phb.Length); Assert.AreEqual(rtnph.PageType, phb.PageType); Assert.AreEqual(rtnph.SizeRange, phb.SizeRange); Assert.AreEqual(rtnph.FreeSpace, ((RadixTreeNodesPageHeader)phb).FreeSpace); }