Skip to content
This repository has been archived by the owner on Jan 23, 2023. It is now read-only.

Commit

Permalink
CoreFX #24343 Vector using Span
Browse files Browse the repository at this point in the history
dotnet/corefx#24343
  • Loading branch information
WinCPP committed Mar 4, 2018
1 parent f5a4248 commit 957113f
Show file tree
Hide file tree
Showing 4 changed files with 88 additions and 1 deletion.
3 changes: 3 additions & 0 deletions src/mscorlib/Resources/Strings.resx
Original file line number Diff line number Diff line change
Expand Up @@ -3718,4 +3718,7 @@
<data name="Argument_OverlapAlignmentMismatch" xml:space="preserve">
<value>Overlapping spans have mismatching alignment.</value>
</data>
<data name="Arg_InsufficientNumberOfElements" xml:space="preserve">
<value>At least {0} element(s) are expected in the parameter "{1}".</value>
</data>
</root>
27 changes: 26 additions & 1 deletion src/mscorlib/shared/System/Numerics/GenerationConfig.ttinclude
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
<#@ import namespace="System.Linq" #>
<#@ import namespace="System.Collections.Generic" #>
<#@ import namespace="System.Text" #>
<#+
/* This file includes static data used as compilation configuration for the rest of the code generation.
It is shared here to ensure that all generated code compiles with the same constants and configurations. */
Expand Down Expand Up @@ -144,4 +145,28 @@
string keyword = (type == allTypes.ToArray()[0]) ? "if" : "else if";
return string.Format("{0} (typeof(T) == typeof({1}))", keyword, type.Name);
}
#>

public string MakeTypeComparisonCondition(Type type)
{
return string.Format("(typeof(T) == typeof({0}))", type.Name);
}

public string GenerateIfConditionAllTypes(IEnumerable<Type> allTypes)
{
StringBuilder sbuilder = new StringBuilder();
var arrAllTypes = allTypes.ToArray();
for (int index = 0; index < arrAllTypes.Length; ++index)
{
if (index == 0)
{
sbuilder.Append("if (").Append(MakeTypeComparisonCondition(arrAllTypes[index]));
}
else
{
sbuilder.AppendLine().Append(" || ").Append(MakeTypeComparisonCondition(arrAllTypes[index]));
}
}
sbuilder.Append(")");
return sbuilder.ToString();
}
#>
34 changes: 34 additions & 0 deletions src/mscorlib/shared/System/Numerics/Vector.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,13 @@
// The .NET Foundation licenses this file to you under the MIT license.
// See the LICENSE file in the project root for more information.

#if !netstandard
using Internal.Runtime.CompilerServices;
#endif
using System.Globalization;
using System.Numerics.Hashing;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Text;

namespace System.Numerics
Expand Down Expand Up @@ -763,6 +767,36 @@ private Vector(ref Register existingRegister)
{
this.register = existingRegister;
}

/// <summary>
/// Constructs a vector from the given span. The span must contain at least Vector'T.Count elements.
/// </summary>
[Intrinsic]
public unsafe Vector(Span<T> values)
: this()
{
if ((typeof(T) == typeof(Byte))
|| (typeof(T) == typeof(SByte))
|| (typeof(T) == typeof(UInt16))
|| (typeof(T) == typeof(Int16))
|| (typeof(T) == typeof(UInt32))
|| (typeof(T) == typeof(Int32))
|| (typeof(T) == typeof(UInt64))
|| (typeof(T) == typeof(Int64))
|| (typeof(T) == typeof(Single))
|| (typeof(T) == typeof(Double)))
{
if (values.Length < Count)
{
throw new IndexOutOfRangeException(SR.Format(SR.Arg_InsufficientNumberOfElements, Vector<T>.Count, nameof(values)));
}
this = Unsafe.ReadUnaligned<Vector<T>>(ref Unsafe.As<T, byte>(ref MemoryMarshal.GetReference(values)));
}
else
{
throw new NotSupportedException(SR.Arg_TypeNotSupported);
}
}
#endregion Constructors

#region Public Instance Methods
Expand Down
25 changes: 25 additions & 0 deletions src/mscorlib/shared/System/Numerics/Vector.tt
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,13 @@
<#@ import namespace="System.Runtime.InteropServices" #>
<#@ include file="GenerationConfig.ttinclude" #><# GenerateCopyrightHeader(); #>

#if !netstandard
using Internal.Runtime.CompilerServices;
#endif
using System.Globalization;
using System.Numerics.Hashing;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Text;

namespace System.Numerics
Expand Down Expand Up @@ -283,6 +287,27 @@ namespace System.Numerics
{
this.register = existingRegister;
}

/// <summary>
/// Constructs a vector from the given span. The span must contain at least Vector'T.Count elements.
/// </summary>
[Intrinsic]
public unsafe Vector(Span<T> values)
: this()
{
<#=GenerateIfConditionAllTypes(supportedTypes)#>
{
if (values.Length < Count)
{
throw new IndexOutOfRangeException(SR.Format(SR.Arg_InsufficientNumberOfElements, Vector<T>.Count, nameof(values)));
}
this = Unsafe.ReadUnaligned<Vector<T>>(ref Unsafe.As<T, byte>(ref MemoryMarshal.GetReference(values)));
}
else
{
throw new NotSupportedException(SR.Arg_TypeNotSupported);
}
}
#endregion Constructors

#region Public Instance Methods
Expand Down

0 comments on commit 957113f

Please sign in to comment.