Browse Source

Fix #2924

pull/2926/head
James Jackson-South 12 months ago
parent
commit
edc9b52b45
  1. 17
      src/ImageSharp/Formats/Png/PngDecoderCore.cs
  2. 12
      tests/ImageSharp.Tests/Formats/Png/PngDecoderTests.cs
  3. 3
      tests/ImageSharp.Tests/TestImages.cs
  4. 3
      tests/Images/External/ReferenceOutput/PngDecoderTests/CanDecode_Issue2924_Rgba32_Issue_2924.png
  5. 3
      tests/Images/Input/Png/issues/Issue_2924.png

17
src/ImageSharp/Formats/Png/PngDecoderCore.cs

@ -131,6 +131,11 @@ internal sealed class PngDecoderCore : ImageDecoderCore
/// </summary>
private readonly int maxUncompressedLength;
/// <summary>
/// A value indicating whether the image data has been read.
/// </summary>
private bool hasImageData;
/// <summary>
/// Initializes a new instance of the <see cref="PngDecoderCore"/> class.
/// </summary>
@ -749,7 +754,11 @@ internal sealed class PngDecoderCore : ImageDecoderCore
where TPixel : unmanaged, IPixel<TPixel>
{
using ZlibInflateStream inflateStream = new(this.currentStream, getData);
inflateStream.AllocateNewBytes(chunkLength, true);
if (!inflateStream.AllocateNewBytes(chunkLength, !this.hasImageData))
{
return;
}
DeflateStream dataStream = inflateStream.CompressedStream!;
if (this.header.InterlaceMethod is PngInterlaceMode.Adam7)
@ -803,7 +812,7 @@ internal sealed class PngDecoderCore : ImageDecoderCore
int bytesRead = compressedStream.Read(scanSpan, currentRowBytesRead, bytesPerFrameScanline - currentRowBytesRead);
if (bytesRead <= 0)
{
return;
goto EXIT;
}
currentRowBytesRead += bytesRead;
@ -848,6 +857,7 @@ internal sealed class PngDecoderCore : ImageDecoderCore
}
EXIT:
this.hasImageData = true;
blendMemory?.Dispose();
}
@ -906,7 +916,7 @@ internal sealed class PngDecoderCore : ImageDecoderCore
int bytesRead = compressedStream.Read(this.scanline.GetSpan(), currentRowBytesRead, bytesPerInterlaceScanline - currentRowBytesRead);
if (bytesRead <= 0)
{
return;
goto EXIT;
}
currentRowBytesRead += bytesRead;
@ -979,6 +989,7 @@ internal sealed class PngDecoderCore : ImageDecoderCore
}
EXIT:
this.hasImageData = true;
blendMemory?.Dispose();
}

12
tests/ImageSharp.Tests/Formats/Png/PngDecoderTests.cs

@ -719,10 +719,20 @@ public partial class PngDecoderTests
[Theory]
[WithFile(TestImages.Png.Issue2752, PixelTypes.Rgba32)]
public void CanDecodeJustOneFrame<TPixel>(TestImageProvider<TPixel> provider)
where TPixel : unmanaged, IPixel<TPixel>
where TPixel : unmanaged, IPixel<TPixel>
{
DecoderOptions options = new() { MaxFrames = 1 };
using Image<TPixel> image = provider.GetImage(PngDecoder.Instance, options);
Assert.Equal(1, image.Frames.Count);
}
[Theory]
[WithFile(TestImages.Png.Issue2924, PixelTypes.Rgba32)]
public void CanDecode_Issue2924<TPixel>(TestImageProvider<TPixel> provider)
where TPixel : unmanaged, IPixel<TPixel>
{
using Image<TPixel> image = provider.GetImage(PngDecoder.Instance);
image.DebugSave(provider);
image.CompareToReferenceOutput(provider);
}
}

3
tests/ImageSharp.Tests/TestImages.cs

@ -160,6 +160,9 @@ public static class TestImages
// Issue 2752: https://github.com/SixLabors/ImageSharp/issues/2752
public const string Issue2752 = "Png/issues/Issue_2752.png";
// Issue 2924: https://github.com/SixLabors/ImageSharp/issues/2924
public const string Issue2924 = "Png/issues/Issue_2924.png";
public static class Bad
{
public const string MissingDataChunk = "Png/xdtn0g01.png";

3
tests/Images/External/ReferenceOutput/PngDecoderTests/CanDecode_Issue2924_Rgba32_Issue_2924.png

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:4347cd89196c09496288724afdd876b227063149bba33615c338ebb474a0cb19
size 47260

3
tests/Images/Input/Png/issues/Issue_2924.png

@ -0,0 +1,3 @@
version https://git-lfs.github.com/spec/v1
oid sha256:fd366a2de522041c706729b01a6030df6c82a4e87ea3509cc78a47486f097044
size 49376
Loading…
Cancel
Save