Skip to content

Decoding failes on slow streams #1268

@pekspro

Description

@pekspro

Prerequisites

  • I have written a descriptive issue title
  • I have verified that I am running the latest version of ImageSharp
  • I have verified if the problem exist in both DEBUG and RELEASE mode
  • I have searched open and closed issues to ensure it has not already been reported

Description

As it is mentioned on the documentation for Stream.Read

An implementation is free to return fewer bytes than requested even if the end of the stream has not been reached.

But if you have a stream that is on very bad mood and for instance just reads one byte at the time reading will throw an SixLabors.ImageSharp.UnknownImageFormatException. If you let some reads work as normal, and then starts to read one byte at the time other exceptions will be thrown or just a part of the image till be loaded (at least for PNG-images, have not tried other formats).

My gut feeling is that is something like this that causes the problem in #926, but I haven't been able to replicate exactly that.

Steps to Reproduce

This code tries to read images from a folder with one byte read at the time:

using SixLabors.ImageSharp;
using System;
using System.IO;

namespace EvilStreamConsoleApp
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Hello World!");

            Directory.CreateDirectory(".\\outputimages");
            var files = Directory.EnumerateFiles(".\\inputimages", "*.*");

            foreach(var file in files)
            {
                using EvilStream evilStream = new EvilStream(file, FileMode.Open);

                var image = Image.Load(evilStream);

                string outputFileName = ".\\outputimages\\" + Path.GetFileName(file);
                image.Save(outputFileName);
            }
        }
    }

    class EvilStream : FileStream
    {
        public EvilStream(string path, FileMode mode)
            : base(path, mode)
        {

        }

        int beNiceCount = 0;

        public override int Read(byte[] array, int offset, int count)
        {
            if (beNiceCount > 0)
            {
                beNiceCount--;

                return base.Read(array, offset, count);
            }

            return base.Read(array, offset, 1);

            //return base.Read(array, offset, Math.Min(256 * 20 - 1, count));
        }
    }
}
  • ImageSharp version: 1.0.0-rc0003
  • Environment (Operating system, version and so on): Windows 10
  • .NET Framework version: .NET Core 3.1

Metadata

Metadata

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions