diff --git a/tests/ImageSharp.Tests/Formats/Tiff/TiffEncoderTests.cs b/tests/ImageSharp.Tests/Formats/Tiff/TiffEncoderTests.cs index 5e663b8f3c..0ac94acb49 100644 --- a/tests/ImageSharp.Tests/Formats/Tiff/TiffEncoderTests.cs +++ b/tests/ImageSharp.Tests/Formats/Tiff/TiffEncoderTests.cs @@ -590,6 +590,20 @@ public class TiffEncoderTests : TiffEncoderBaseTester public void TiffEncoder_EncodeBiColor_WithCcittGroup4FaxCompression_BlackIsZero_Works(TestImageProvider provider) where TPixel : unmanaged, IPixel => TestTiffEncoderCore(provider, TiffBitsPerPixel.Bit1, TiffPhotometricInterpretation.BlackIsZero, TiffCompression.CcittGroup4Fax); + [Fact] + public void TiffEncoder_ReencodeNarrowCcittGroup4Fax_Works() + { + byte[] data = BuildCcittGroup4Tiff([0x80, 0x08, 0x00, 0x80]); + + using Image image = Image.Load(data); + using MemoryStream output = new(); + image.Save(output, new TiffEncoder()); + + output.Position = 0; + using Image decoded = Image.Load(output); + Assert.Equal(new Size(1, 1), decoded.Size); + } + [Theory] [WithFile(Calliphora_BiColorUncompressed, PixelTypes.Rgba32)] public void TiffEncoder_EncodeBiColor_WithModifiedHuffmanCompression_WhiteIsZero_Works(TestImageProvider provider) @@ -647,4 +661,61 @@ public class TiffEncoderTests : TiffEncoderBaseTester TiffEncoder encoder = new() { PhotometricInterpretation = photometricInterpretation }; image.DebugSave(provider, encoder); } + + private static byte[] BuildCcittGroup4Tiff(byte[] strip) + { + (ushort Tag, ushort Type, uint Count, uint Value)[] entries = + [ + (256, 3, 1, 1), + (257, 3, 1, 1), + (258, 3, 1, 1), + (259, 3, 1, 4), + (262, 3, 1, 0), + (273, 4, 1, 0), + (277, 3, 1, 1), + (278, 4, 1, 1), + (279, 4, 1, (uint)strip.Length), + ]; + + using MemoryStream stream = new(); + using BinaryWriter writer = new(stream); + writer.Write((byte)'I'); + writer.Write((byte)'I'); + writer.Write((ushort)42); + writer.Write(8U); + writer.Write((ushort)entries.Length); + + long stripOffsetPosition = 0; + foreach ((ushort tag, ushort type, uint count, uint value) in entries) + { + writer.Write(tag); + writer.Write(type); + writer.Write(count); + if (tag == 273) + { + stripOffsetPosition = stream.Position; + writer.Write(0U); + } + else if (type == 3) + { + writer.Write((ushort)value); + writer.Write((ushort)0); + } + else + { + writer.Write(value); + } + } + + writer.Write(0U); + uint stripOffset = (uint)stream.Position; + writer.Write(strip); + + long endPosition = stream.Position; + stream.Position = stripOffsetPosition; + writer.Write(stripOffset); + stream.Position = endPosition; + + return stream.ToArray(); + } }