|
|
|
@ -4,7 +4,8 @@ |
|
|
|
using System; |
|
|
|
using System.Buffers; |
|
|
|
using System.IO; |
|
|
|
|
|
|
|
using System.Runtime.CompilerServices; |
|
|
|
using System.Runtime.InteropServices; |
|
|
|
using SixLabors.ImageSharp.Memory; |
|
|
|
|
|
|
|
namespace SixLabors.ImageSharp.Formats.Gif |
|
|
|
@ -115,14 +116,14 @@ namespace SixLabors.ImageSharp.Formats.Gif |
|
|
|
int data = 0; |
|
|
|
int first = 0; |
|
|
|
|
|
|
|
Span<int> prefixSpan = this.prefix.Span; |
|
|
|
Span<int> suffixSpan = this.suffix.Span; |
|
|
|
Span<int> pixelStackSpan = this.pixelStack.Span; |
|
|
|
ref int prefixRef = ref MemoryMarshal.GetReference(this.prefix.Span); |
|
|
|
ref int suffixRef = ref MemoryMarshal.GetReference(this.suffix.Span); |
|
|
|
ref int pixelStackRef = ref MemoryMarshal.GetReference(this.pixelStack.Span); |
|
|
|
ref byte pixelsRef = ref MemoryMarshal.GetReference(pixels); |
|
|
|
|
|
|
|
for (code = 0; code < clearCode; code++) |
|
|
|
{ |
|
|
|
prefixSpan[code] = 0; |
|
|
|
suffixSpan[code] = (byte)code; |
|
|
|
Unsafe.Add(ref suffixRef, code) = (byte)code; |
|
|
|
} |
|
|
|
|
|
|
|
byte[] buffer = new byte[255]; |
|
|
|
@ -176,7 +177,7 @@ namespace SixLabors.ImageSharp.Formats.Gif |
|
|
|
|
|
|
|
if (oldCode == NullCode) |
|
|
|
{ |
|
|
|
pixelStackSpan[top++] = suffixSpan[code]; |
|
|
|
Unsafe.Add(ref pixelStackRef, top++) = Unsafe.Add(ref suffixRef, code); |
|
|
|
oldCode = code; |
|
|
|
first = code; |
|
|
|
continue; |
|
|
|
@ -185,27 +186,27 @@ namespace SixLabors.ImageSharp.Formats.Gif |
|
|
|
int inCode = code; |
|
|
|
if (code == availableCode) |
|
|
|
{ |
|
|
|
pixelStackSpan[top++] = (byte)first; |
|
|
|
Unsafe.Add(ref pixelStackRef, top++) = (byte)first; |
|
|
|
|
|
|
|
code = oldCode; |
|
|
|
} |
|
|
|
|
|
|
|
while (code > clearCode) |
|
|
|
{ |
|
|
|
pixelStackSpan[top++] = suffixSpan[code]; |
|
|
|
code = prefixSpan[code]; |
|
|
|
Unsafe.Add(ref pixelStackRef, top++) = Unsafe.Add(ref suffixRef, code); |
|
|
|
code = Unsafe.Add(ref prefixRef, code); |
|
|
|
} |
|
|
|
|
|
|
|
first = suffixSpan[code]; |
|
|
|
|
|
|
|
pixelStackSpan[top++] = suffixSpan[code]; |
|
|
|
int suffixCode = Unsafe.Add(ref suffixRef, code); |
|
|
|
first = suffixCode; |
|
|
|
Unsafe.Add(ref pixelStackRef, top++) = suffixCode; |
|
|
|
|
|
|
|
// Fix for Gifs that have "deferred clear code" as per here :
|
|
|
|
// https://bugzilla.mozilla.org/show_bug.cgi?id=55918
|
|
|
|
if (availableCode < MaxStackSize) |
|
|
|
{ |
|
|
|
prefixSpan[availableCode] = oldCode; |
|
|
|
suffixSpan[availableCode] = first; |
|
|
|
Unsafe.Add(ref prefixRef, availableCode) = oldCode; |
|
|
|
Unsafe.Add(ref suffixRef, availableCode) = first; |
|
|
|
availableCode++; |
|
|
|
if (availableCode == codeMask + 1 && availableCode < MaxStackSize) |
|
|
|
{ |
|
|
|
@ -221,7 +222,7 @@ namespace SixLabors.ImageSharp.Formats.Gif |
|
|
|
top--; |
|
|
|
|
|
|
|
// Clear missing pixels
|
|
|
|
pixels[xyz++] = (byte)pixelStackSpan[top]; |
|
|
|
Unsafe.Add(ref pixelsRef, xyz++) = (byte)Unsafe.Add(ref pixelStackRef, top); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
@ -238,8 +239,9 @@ namespace SixLabors.ImageSharp.Formats.Gif |
|
|
|
/// </summary>
|
|
|
|
/// <param name="buffer">The buffer to store the block in.</param>
|
|
|
|
/// <returns>
|
|
|
|
/// The <see cref="T:byte[]"/>.
|
|
|
|
/// The <see cref="int"/>.
|
|
|
|
/// </returns>
|
|
|
|
[MethodImpl(MethodImplOptions.AggressiveInlining)] |
|
|
|
private int ReadBlock(byte[] buffer) |
|
|
|
{ |
|
|
|
int bufferSize = this.stream.ReadByte(); |
|
|
|
|