Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -573,6 +573,7 @@ public static bool ShouldCodeNotBeCompiledIntoFinalImage(InstructionSetSupport i
var handle = ecmaMethod.Handle;

List<TypeDesc> compExactlyDependsOnList = null;
bool hasCompHasFallback = false;

foreach (var attributeHandle in metadataReader.GetMethodDefinition(handle).GetCustomAttributes())
{
Expand Down Expand Up @@ -606,35 +607,41 @@ public static bool ShouldCodeNotBeCompiledIntoFinalImage(InstructionSetSupport i
compExactlyDependsOnList.Add(typeForBypass);
}
}
else if (metadataReader.StringComparer.Equals(nameHandle, "CompHasFallbackAttribute"))
{
hasCompHasFallback = true;
}
}
}

if (compExactlyDependsOnList != null && compExactlyDependsOnList.Count > 0)
{
// Default to true, and set to false if at least one of the types is actually supported in the current environment, and none of the
// intrinsic types are in an opportunistic state.
bool doBypass = true;
bool anySupported = false;

foreach (var intrinsicType in compExactlyDependsOnList)
{
InstructionSet instructionSet = InstructionSetParser.LookupPlatformIntrinsicInstructionSet(intrinsicType.Context.Target.Architecture, intrinsicType);
if (instructionSet == InstructionSet.ILLEGAL)
{
// This instruction set isn't supported on the current platform at all.
continue;
}
if (instructionSetSupport.IsInstructionSetSupported(instructionSet) || instructionSetSupport.IsInstructionSetExplicitlyUnsupported(instructionSet))
{
doBypass = false;
}
else
// If the instruction set is ILLEGAL, it means it is never supported by the current architecture so the behavior at runtime is known
if (instructionSet != InstructionSet.ILLEGAL)
{
// If we reach here this is an instruction set generally supported on this platform, but we don't know what the behavior will be at runtime
return true;
if (instructionSetSupport.IsInstructionSetSupported(instructionSet))
{
anySupported = true;
}
else if (!instructionSetSupport.IsInstructionSetExplicitlyUnsupported(instructionSet))
{
// If we reach here this is an instruction set generally supported on this platform, but we don't know what the behavior will be at runtime
return true;
}
}
}

return doBypass;
if (!anySupported && !hasCompHasFallback)
{
// If none of the instruction sets are supported (all are either illegal or explicitly unsupported),
// skip compilation unless the method has a functional fallback path
return true;
}
}

// No reason to bypass compilation and code generation.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -837,6 +837,7 @@
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CallingConventions.cs" />
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CollectionBuilderAttribute.cs" />
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CompExactlyDependsOnAttribute.cs" />
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CompHasFallbackAttribute.cs" />
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CompilationRelaxations.cs" />
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CompilationRelaxationsAttribute.cs" />
<Compile Include="$(MSBuildThisFileDirectory)System\Runtime\CompilerServices\CompilerFeatureRequiredAttribute.cs" />
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.

using System.Diagnostics;

namespace System.Runtime.CompilerServices
{
// Use this attribute alongside CompExactlyDependsOnAttribute to indicate that a method has
// a functional fallback path and should still be compiled into the Ready2Run image even when
// none of the CompExactlyDependsOn instruction sets are supported.
[AttributeUsage(AttributeTargets.Method | AttributeTargets.Constructor, AllowMultiple = false, Inherited = false)]
#if MONO
[Conditional("unnecessary")] // Mono doesn't use Ready2Run so we can remove this attribute to reduce size
#endif
internal sealed class CompHasFallbackAttribute : Attribute
{
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -301,6 +301,7 @@ internal interface IRuntimeConst
/// </summary>
[MethodImpl(MethodImplOptions.AggressiveInlining)]
[CompExactlyDependsOn(typeof(Ssse3))]
[CompHasFallback]
internal static Vector128<byte> ShuffleNativeModified(Vector128<byte> vector, Vector128<byte> indices)
{
if (Ssse3.IsSupported)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1632,6 +1632,7 @@ private static bool AllCharsInVectorAreAscii<T>(Vector128<T> vector)

[MethodImpl(MethodImplOptions.AggressiveInlining)]
[CompExactlyDependsOn(typeof(Avx))]
[CompHasFallback]
private static bool AllCharsInVectorAreAscii<T>(Vector256<T> vector)
where T : unmanaged
{
Expand Down
Loading