protected override void WriteImpl(ReadOnlySpan <byte> source, long offset) { long blockIndex = offset / SectorSize; long hashPos = blockIndex * DigestSize; int toWrite = (int)Math.Min(source.Length, GetSize() - offset); byte[] dataBuffer = ArrayPool <byte> .Shared.Rent(SectorSize); try { source.CopyTo(dataBuffer); byte[] hash = DoHash(dataBuffer, 0, toWrite); if (Type == IntegrityStorageType.Save && source.IsEmpty()) { Array.Clear(hash, 0, DigestSize); } BaseStorage.Write(source, offset); HashStorage.Write(hash, hashPos); BlockValidities[blockIndex] = Validity.Unchecked; } finally { ArrayPool <byte> .Shared.Return(dataBuffer); } }
protected override Result WriteImpl(long offset, ReadOnlySpan <byte> source) { long blockIndex = offset / SectorSize; long hashPos = blockIndex * DigestSize; Result rc = GetSize(out long storageSize); if (rc.IsFailure()) { return(rc); } int toWrite = (int)Math.Min(source.Length, storageSize - offset); byte[] dataBuffer = ArrayPool <byte> .Shared.Rent(SectorSize); try { source.CopyTo(dataBuffer); byte[] hash = DoHash(dataBuffer, 0, toWrite); if (Type == IntegrityStorageType.Save && source.IsEmpty()) { Array.Clear(hash, 0, DigestSize); } BaseStorage.Write(offset, source); HashStorage.Write(hashPos, hash); BlockValidities[blockIndex] = Validity.Unchecked; } finally { ArrayPool <byte> .Shared.Return(dataBuffer); } return(Result.Success); }