Browse Source

Move undoing zip compression into base class

pull/3124/head
Brian Popow 3 weeks ago
parent
commit
a85fe63d31
  1. 29
      src/ImageSharp/Formats/Exr/Compression/Decompressors/Pxr24Compression.cs
  2. 29
      src/ImageSharp/Formats/Exr/Compression/Decompressors/ZipExrCompression.cs
  3. 43
      src/ImageSharp/Formats/Exr/Compression/ExrBaseDecompressor.cs

29
src/ImageSharp/Formats/Exr/Compression/Decompressors/Pxr24Compression.cs

@ -51,33 +51,8 @@ internal class Pxr24Compression : ExrBaseDecompressor
Span<uint> outputBufferFloat = MemoryMarshal.Cast<byte, uint>(buffer);
Span<uint> outputBufferUint = MemoryMarshal.Cast<byte, uint>(buffer);
long pos = stream.Position;
using ZlibInflateStream inflateStream = new(
stream,
() =>
{
int left = (int)(compressedBytes - (stream.Position - pos));
return left > 0 ? left : 0;
});
inflateStream.AllocateNewBytes((int)this.BytesPerBlock, true);
using DeflateStream dataStream = inflateStream.CompressedStream!;
int totalRead = 0;
while (totalRead < buffer.Length)
{
int bytesRead = dataStream.Read(uncompressed, totalRead, buffer.Length - totalRead);
if (bytesRead <= 0)
{
break;
}
totalRead += bytesRead;
}
if (totalRead == 0)
{
ExrThrowHelper.ThrowInvalidImageContentException("Could not read enough data for zip compressed image data!");
}
uint uncompressedBytes = this.BytesPerBlock;
UndoZipCompression(stream, compressedBytes, uncompressed, uncompressedBytes);
int lastIn = 0;
int outputOffset = 0;

29
src/ImageSharp/Formats/Exr/Compression/Decompressors/ZipExrCompression.cs

@ -31,33 +31,8 @@ internal class ZipExrCompression : ExrBaseDecompressor
{
Span<byte> uncompressed = this.tmpBuffer.GetSpan();
long pos = stream.Position;
using ZlibInflateStream inflateStream = new(
stream,
() =>
{
int left = (int)(compressedBytes - (stream.Position - pos));
return left > 0 ? left : 0;
});
inflateStream.AllocateNewBytes((int)this.BytesPerBlock, true);
using DeflateStream dataStream = inflateStream.CompressedStream!;
int totalRead = 0;
while (totalRead < buffer.Length)
{
int bytesRead = dataStream.Read(uncompressed, totalRead, buffer.Length - totalRead);
if (bytesRead <= 0)
{
break;
}
totalRead += bytesRead;
}
if (totalRead == 0)
{
ExrThrowHelper.ThrowInvalidImageContentException("Could not read enough data for zip compressed image data!");
}
uint uncompressedBytes = (uint)buffer.Length;
int totalRead = UndoZipCompression(stream, compressedBytes, uncompressed, uncompressedBytes);
Reconstruct(uncompressed, (uint)totalRead);
Interleave(uncompressed, (uint)totalRead, buffer);

43
src/ImageSharp/Formats/Exr/Compression/ExrBaseDecompressor.cs

@ -1,6 +1,8 @@
// Copyright (c) Six Labors.
// Licensed under the Six Labors Split License.
using System.IO.Compression;
using SixLabors.ImageSharp.Compression.Zlib;
using SixLabors.ImageSharp.IO;
using SixLabors.ImageSharp.Memory;
@ -31,6 +33,47 @@ internal abstract class ExrBaseDecompressor : ExrBaseCompression
/// <param name="buffer">The buffer to write the decompressed data to.</param>
public abstract void Decompress(BufferedReadStream stream, uint compressedBytes, Span<byte> buffer);
/// <summary>
/// Decompresses zip compressed data.
/// </summary>
/// <param name="stream">The buffered stream to decompress.</param>
/// <param name="compressedBytes">The compressed bytes.</param>
/// <param name="uncompressed">The buffer to write the uncompressed data to.</param>
/// <param name="uncompressedBytes">The uncompressed bytes.</param>
/// <returns>The total bytes read from the stream.</returns>
protected static int UndoZipCompression(BufferedReadStream stream, uint compressedBytes, Span<byte> uncompressed, uint uncompressedBytes)
{
long pos = stream.Position;
using ZlibInflateStream inflateStream = new(
stream,
() =>
{
int left = (int)(compressedBytes - (stream.Position - pos));
return left > 0 ? left : 0;
});
inflateStream.AllocateNewBytes((int)uncompressedBytes, true);
using DeflateStream dataStream = inflateStream.CompressedStream!;
int totalRead = 0;
while (totalRead < uncompressedBytes)
{
int bytesRead = dataStream.Read(uncompressed, totalRead, (int)uncompressedBytes - totalRead);
if (bytesRead <= 0)
{
break;
}
totalRead += bytesRead;
}
if (totalRead == 0)
{
ExrThrowHelper.ThrowInvalidImageContentException("Could not read enough data for zip compressed image data!");
}
return totalRead;
}
/// <summary>
/// Integrate over all differences to the previous value in order to
/// reconstruct sample values.

Loading…
Cancel
Save