Skip to content

Commit cfa1510

Browse files
authored
Merge branch 'main' into issue-exif-null-array-value
2 parents 1d2d717 + 823e785 commit cfa1510

File tree

75 files changed

+2095
-278
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

75 files changed

+2095
-278
lines changed

.github/ISSUE_TEMPLATE/config.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
blank_issues_enabled: false
22
contact_links:
33
- name: Feature Request
4-
url: https://github.com/SixLabors/ImageSharp/discussions?discussions_q=category%3AIdeas
4+
url: https://github.com/SixLabors/ImageSharp/discussions/categories/ideas
55
about: Share ideas for new features for this project.

README.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ Built against [.NET Standard 2.0](https://docs.microsoft.com/en-us/dotnet/standa
2626
## License
2727

2828
- ImageSharp is licensed under the [Apache License, Version 2.0](https://opensource.org/licenses/Apache-2.0)
29-
- An alternative Commercial Support License can be purchased **for projects and applications requiring support**.
29+
- An alternative Six Labors License can be purchased **for projects and applications requiring developer support**.
3030
Please visit https://sixlabors.com/pricing for details.
3131

3232
## Support Six Labors
@@ -43,7 +43,8 @@ Support the efforts of the development of the Six Labors projects.
4343

4444
## Questions
4545

46-
- Do you have questions? We are happy to help! Please [join our Discussions Forum](https://github.com/SixLabors/ImageSharp/discussions/category_choices), or ask them on [Stack Overflow](https://stackoverflow.com) using the `ImageSharp` tag. Please do not open issues for questions.
46+
- Do you have questions? We are happy to help! Simply purchase a [Six Labors License](https://sixlabors.com/pricing) for developer support. Please do not open issues for questions or misuse our [Discussions Forum](https://github.com/SixLabors/ImageSharp/discussions).
47+
- For feature ideas please [join our Discussions Forum](https://github.com/SixLabors/ImageSharp/discussions/categories/ideas) and we'll be happy to discuss.
4748
- Please read our [Contribution Guide](https://github.com/SixLabors/ImageSharp/blob/main/.github/CONTRIBUTING.md) before opening issues or pull requests!
4849

4950
## Code of Conduct

src/ImageSharp/Formats/Jpeg/Components/Encoder/LuminanceForwardConverter{TPixel}.cs

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,13 @@
22
// Licensed under the Apache License, Version 2.0.
33

44
using System;
5+
using System.Diagnostics;
56
using System.Runtime.CompilerServices;
67
using System.Runtime.InteropServices;
8+
#if SUPPORTS_RUNTIME_INTRINSICS
9+
using System.Runtime.Intrinsics;
10+
using System.Runtime.Intrinsics.X86;
11+
#endif
712
using SixLabors.ImageSharp.Advanced;
813
using SixLabors.ImageSharp.PixelFormats;
914

@@ -74,6 +79,44 @@ public void Convert(int x, int y, ref RowOctet<TPixel> currentRows)
7479
ref Block8x8F yBlock = ref this.Y;
7580
ref L8 l8Start = ref MemoryMarshal.GetReference(this.l8Span);
7681

82+
if (RgbToYCbCrConverterVectorized.IsSupported)
83+
{
84+
ConvertAvx(ref l8Start, ref yBlock);
85+
}
86+
else
87+
{
88+
ConvertScalar(ref l8Start, ref yBlock);
89+
}
90+
}
91+
92+
/// <summary>
93+
/// Converts 8x8 L8 pixel matrix to 8x8 Block of floats using Avx2 Intrinsics.
94+
/// </summary>
95+
/// <param name="l8Start">Start of span of L8 pixels with size of 64</param>
96+
/// <param name="yBlock">8x8 destination matrix of Luminance(Y) converted data</param>
97+
private static void ConvertAvx(ref L8 l8Start, ref Block8x8F yBlock)
98+
{
99+
Debug.Assert(RgbToYCbCrConverterVectorized.IsSupported, "AVX2 is required to run this converter");
100+
101+
#if SUPPORTS_RUNTIME_INTRINSICS
102+
ref Vector128<byte> l8ByteSpan = ref Unsafe.As<L8, Vector128<byte>>(ref l8Start);
103+
ref Vector256<float> destRef = ref yBlock.V0;
104+
105+
const int bytesPerL8Stride = 8;
106+
for (nint i = 0; i < 8; i++)
107+
{
108+
Unsafe.Add(ref destRef, i) = Avx2.ConvertToVector256Single(Avx2.ConvertToVector256Int32(Unsafe.AddByteOffset(ref l8ByteSpan, bytesPerL8Stride * i)));
109+
}
110+
#endif
111+
}
112+
113+
/// <summary>
114+
/// Converts 8x8 L8 pixel matrix to 8x8 Block of floats.
115+
/// </summary>
116+
/// <param name="l8Start">Start of span of L8 pixels with size of 64</param>
117+
/// <param name="yBlock">8x8 destination matrix of Luminance(Y) converted data</param>
118+
private static void ConvertScalar(ref L8 l8Start, ref Block8x8F yBlock)
119+
{
77120
for (int i = 0; i < Block8x8F.Size; i++)
78121
{
79122
ref L8 c = ref Unsafe.Add(ref l8Start, i);

src/ImageSharp/Formats/Jpeg/Components/Encoder/RgbForwardConverter{TPixel}.cs

Lines changed: 53 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,13 @@
22
// Licensed under the Apache License, Version 2.0.
33

44
using System;
5+
using System.Diagnostics;
56
using System.Runtime.CompilerServices;
67
using System.Runtime.InteropServices;
8+
#if SUPPORTS_RUNTIME_INTRINSICS
9+
using System.Runtime.Intrinsics;
10+
using System.Runtime.Intrinsics.X86;
11+
#endif
712
using SixLabors.ImageSharp.Advanced;
813
using SixLabors.ImageSharp.PixelFormats;
914

@@ -94,10 +99,56 @@ public void Convert(int x, int y, ref RowOctet<TPixel> currentRows)
9499
ref Block8x8F greenBlock = ref this.G;
95100
ref Block8x8F blueBlock = ref this.B;
96101

97-
CopyToBlock(this.rgbSpan, ref redBlock, ref greenBlock, ref blueBlock);
102+
if (RgbToYCbCrConverterVectorized.IsSupported)
103+
{
104+
ConvertAvx(this.rgbSpan, ref redBlock, ref greenBlock, ref blueBlock);
105+
}
106+
else
107+
{
108+
ConvertScalar(this.rgbSpan, ref redBlock, ref greenBlock, ref blueBlock);
109+
}
110+
}
111+
112+
/// <summary>
113+
/// Converts 8x8 RGB24 pixel matrix to 8x8 Block of floats using Avx2 Intrinsics.
114+
/// </summary>
115+
/// <param name="rgbSpan">Span of Rgb24 pixels with size of 64</param>
116+
/// <param name="rBlock">8x8 destination matrix of Red converted data</param>
117+
/// <param name="gBlock">8x8 destination matrix of Blue converted data</param>
118+
/// <param name="bBlock">8x8 destination matrix of Green converted data</param>
119+
private static void ConvertAvx(Span<Rgb24> rgbSpan, ref Block8x8F rBlock, ref Block8x8F gBlock, ref Block8x8F bBlock)
120+
{
121+
Debug.Assert(RgbToYCbCrConverterVectorized.IsSupported, "AVX2 is required to run this converter");
122+
123+
#if SUPPORTS_RUNTIME_INTRINSICS
124+
ref Vector256<byte> rgbByteSpan = ref Unsafe.As<Rgb24, Vector256<byte>>(ref MemoryMarshal.GetReference(rgbSpan));
125+
ref Vector256<float> redRef = ref rBlock.V0;
126+
ref Vector256<float> greenRef = ref gBlock.V0;
127+
ref Vector256<float> blueRef = ref bBlock.V0;
128+
var zero = Vector256.Create(0).AsByte();
129+
130+
var extractToLanesMask = Unsafe.As<byte, Vector256<uint>>(ref MemoryMarshal.GetReference(RgbToYCbCrConverterVectorized.MoveFirst24BytesToSeparateLanes));
131+
var extractRgbMask = Unsafe.As<byte, Vector256<byte>>(ref MemoryMarshal.GetReference(RgbToYCbCrConverterVectorized.ExtractRgb));
132+
Vector256<byte> rgb, rg, bx;
133+
134+
const int bytesPerRgbStride = 24;
135+
for (nint i = 0; i < 8; i++)
136+
{
137+
rgb = Avx2.PermuteVar8x32(Unsafe.AddByteOffset(ref rgbByteSpan, bytesPerRgbStride * i).AsUInt32(), extractToLanesMask).AsByte();
138+
139+
rgb = Avx2.Shuffle(rgb, extractRgbMask);
140+
141+
rg = Avx2.UnpackLow(rgb, zero);
142+
bx = Avx2.UnpackHigh(rgb, zero);
143+
144+
Unsafe.Add(ref redRef, i) = Avx.ConvertToVector256Single(Avx2.UnpackLow(rg, zero).AsInt32());
145+
Unsafe.Add(ref greenRef, i) = Avx.ConvertToVector256Single(Avx2.UnpackHigh(rg, zero).AsInt32());
146+
Unsafe.Add(ref blueRef, i) = Avx.ConvertToVector256Single(Avx2.UnpackLow(bx, zero).AsInt32());
147+
}
148+
#endif
98149
}
99150

100-
private static void CopyToBlock(Span<Rgb24> rgbSpan, ref Block8x8F redBlock, ref Block8x8F greenBlock, ref Block8x8F blueBlock)
151+
private static void ConvertScalar(Span<Rgb24> rgbSpan, ref Block8x8F redBlock, ref Block8x8F greenBlock, ref Block8x8F blueBlock)
101152
{
102153
ref Rgb24 rgbStart = ref MemoryMarshal.GetReference(rgbSpan);
103154

src/ImageSharp/Formats/Jpeg/Components/Encoder/RgbToYCbCrConverterVectorized.cs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -60,13 +60,13 @@ public static int AvxCompatibilityPadding
6060

6161
#if SUPPORTS_RUNTIME_INTRINSICS
6262

63-
private static ReadOnlySpan<byte> MoveFirst24BytesToSeparateLanes => new byte[]
63+
internal static ReadOnlySpan<byte> MoveFirst24BytesToSeparateLanes => new byte[]
6464
{
6565
0, 0, 0, 0, 1, 0, 0, 0, 2, 0, 0, 0, 6, 0, 0, 0,
6666
3, 0, 0, 0, 4, 0, 0, 0, 5, 0, 0, 0, 7, 0, 0, 0
6767
};
6868

69-
private static ReadOnlySpan<byte> ExtractRgb => new byte[]
69+
internal static ReadOnlySpan<byte> ExtractRgb => new byte[]
7070
{
7171
0, 3, 6, 9, 1, 4, 7, 10, 2, 5, 8, 11, 0xFF, 0xFF, 0xFF, 0xFF,
7272
0, 3, 6, 9, 1, 4, 7, 10, 2, 5, 8, 11, 0xFF, 0xFF, 0xFF, 0xFF

0 commit comments

Comments
 (0)