Skip to content
Merged
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 @@ -40,21 +40,18 @@ protected static Marshaller CreateMarshaller(MarshallerKind kind)
}
}

public static Marshaller[] GetMarshallersForMethod(MethodDesc targetMethod)
private static Marshaller[] GetMarshallers(
MethodSignature methodSig,
PInvokeFlags flags,
ParameterMetadata[] parameterMetadataArray)
{
Debug.Assert(targetMethod.IsPInvoke);

MarshalDirection direction = MarshalDirection.Forward;
MethodSignature methodSig = targetMethod.Signature;
PInvokeFlags flags = targetMethod.GetPInvokeMethodMetadata().Flags;

ParameterMetadata[] parameterMetadataArray = targetMethod.GetParameterMetadata();
Marshaller[] marshallers = new Marshaller[methodSig.Length + 1];
ParameterMetadata parameterMetadata;

for (int i = 0, parameterIndex = 0; i < marshallers.Length; i++)
{
Debug.Assert(parameterIndex == parameterMetadataArray.Length || i <= parameterMetadataArray[parameterIndex].Index);

ParameterMetadata parameterMetadata;
if (parameterIndex == parameterMetadataArray.Length || i < parameterMetadataArray[parameterIndex].Index)
{
// if we don't have metadata for the parameter, create a dummy one
Expand All @@ -72,7 +69,7 @@ public static Marshaller[] GetMarshallersForMethod(MethodDesc targetMethod)
methodSig.GetEmbeddedSignatureData(),
MarshallerType.Argument,
parameterMetadata.MarshalAsDescriptor,
direction,
MarshalDirection.Forward,
marshallers,
parameterMetadata.Index,
flags,
Expand All @@ -84,6 +81,24 @@ public static Marshaller[] GetMarshallersForMethod(MethodDesc targetMethod)
return marshallers;
}


public static Marshaller[] GetMarshallersForMethod(MethodDesc targetMethod)
{
Debug.Assert(targetMethod.IsPInvoke);
return GetMarshallers(
targetMethod.Signature,
targetMethod.GetPInvokeMethodMetadata().Flags,
targetMethod.GetParameterMetadata());
}

public static Marshaller[] GetMarshallersForSignature(MethodSignature methodSig, ParameterMetadata[] paramMetadata)
{
return GetMarshallers(
methodSig,
new PInvokeFlags(PInvokeAttributes.None),
paramMetadata);
}

public static bool IsMarshallingRequired(MethodDesc targetMethod)
{
Debug.Assert(targetMethod.IsPInvoke);
Expand Down Expand Up @@ -115,25 +130,10 @@ public static bool IsMarshallingRequired(MethodDesc targetMethod)

public static bool IsMarshallingRequired(MethodSignature methodSig, ParameterMetadata[] paramMetadata)
{
for (int i = 0, paramIndex = 0; i < methodSig.Length + 1; i++)
Marshaller[] marshallers = GetMarshallersForSignature(methodSig, paramMetadata);
for (int i = 0; i < marshallers.Length; i++)
{
ParameterMetadata parameterMetadata = (paramIndex == paramMetadata.Length || i < paramMetadata[paramIndex].Index) ?
new ParameterMetadata(i, ParameterMetadataAttributes.None, null) :
paramMetadata[paramIndex++];

TypeDesc parameterType = (i == 0) ? methodSig.ReturnType : methodSig[i - 1]; //first item is the return type

MarshallerKind marshallerKind = MarshalHelpers.GetMarshallerKind(
parameterType,
parameterIndex: i,
customModifierData: methodSig.GetEmbeddedSignatureData(),
parameterMetadata.MarshalAsDescriptor,
parameterMetadata.Return,
isAnsi: true,
MarshallerType.Argument,
out MarshallerKind elementMarshallerKind);

if (IsMarshallingRequired(marshallerKind))
if (marshallers[i].IsMarshallingRequired())
return true;
}

Expand Down
27 changes: 27 additions & 0 deletions src/tests/JIT/Regression/JitBlue/Runtime_58259/Runtime_58259.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.

public unsafe class Runtime_58259
{
public static int Main()
{
M(out _);
return 100;
}

static delegate* unmanaged<out int, void> _f;

public static void M(out int index)
{
if (_f != null)
{
_f(out index);
_f(out index);
}
else
{
index = 0;
}
}
}

Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<AllowUnsafeBlocks>True</AllowUnsafeBlocks>
<CLRTestPriority>1</CLRTestPriority> <!-- This is a regression test for a crossgen only scenario -->
</PropertyGroup>
<PropertyGroup>
<DebugType>None</DebugType>
<Optimize>True</Optimize>
</PropertyGroup>
<ItemGroup>
<Compile Include="$(MSBuildProjectName).cs" />
</ItemGroup>
</Project>