private unsafe static void SetBlockHeader(int length, DeltaLogEntryType type, byte *dest) { ref var header = ref GetHeader((long)dest);
/// <summary> /// Get next entry /// </summary> /// <param name="physicalAddress"></param> /// <param name="entryLength"></param> /// <param name="type"></param> /// <returns></returns> public unsafe bool GetNext(out long physicalAddress, out int entryLength, out DeltaLogEntryType type) { while (true) { physicalAddress = 0; entryLength = 0; currentAddress = nextAddress; type = DeltaLogEntryType.DELTA; var _currentPage = currentAddress >> LogPageSizeBits; var _currentFrame = _currentPage % frameSize; var _currentOffset = currentAddress & PageSizeMask; var _headAddress = long.MaxValue; if (disposed) { return(false); } var _endAddress = endAddress; if (tailAddress > _endAddress) { _endAddress = tailAddress; } if (currentAddress >= _endAddress) { return(false); } if (BufferAndLoad(currentAddress, _currentPage, _currentFrame, _headAddress, _endAddress)) { continue; } physicalAddress = frame.GetPhysicalAddress(_currentFrame, _currentOffset); // Get and check entry length entryLength = GetHeader(physicalAddress).Length; type = GetHeader(physicalAddress).Type; if (entryLength == 0) { currentAddress = (1 + (currentAddress >> LogPageSizeBits)) << LogPageSizeBits; if (Utility.MonotonicUpdate(ref nextAddress, currentAddress, out _)) { return(false); } else { continue; } } int recordSize = (int)(Align(_currentOffset + HeaderSize + entryLength) - _currentOffset); if (entryLength < 0 || (_currentOffset + recordSize > PageSize)) { currentAddress = (1 + (currentAddress >> LogPageSizeBits)) << LogPageSizeBits; if (Utility.MonotonicUpdate(ref nextAddress, currentAddress, out _)) { return(false); } else { continue; } } // Verify checksum if (!VerifyBlockChecksum((byte *)physicalAddress, entryLength)) { currentAddress = (1 + (currentAddress >> LogPageSizeBits)) << LogPageSizeBits; if (Utility.MonotonicUpdate(ref nextAddress, currentAddress, out _)) { return(false); } else { continue; } } physicalAddress += HeaderSize; if ((currentAddress & PageSizeMask) + recordSize == PageSize) { currentAddress = (1 + (currentAddress >> LogPageSizeBits)) << LogPageSizeBits; } else { currentAddress += recordSize; } if (Utility.MonotonicUpdate(ref nextAddress, currentAddress, out long oldCurrentAddress)) { currentAddress = oldCurrentAddress; return(true); } } }