Skip to content

Adding support for decltype #389

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Sep 18, 2022
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
16 changes: 16 additions & 0 deletions sources/ClangSharp.PInvokeGenerator/PInvokeGenerator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2092,6 +2092,10 @@ private CallingConvention GetCallingConvention(Cursor? cursor, Cursor? context,
}
}
}
else if (type is DecltypeType decltypeType)
{
return GetCallingConvention(cursor, context, decltypeType.UnderlyingType, ref wasRemapped);
}
else if (type is FunctionType functionType)
{
var callingConv = functionType.CallConv;
Expand Down Expand Up @@ -3021,6 +3025,10 @@ private string GetTypeName(Cursor? cursor, Cursor? context, Type rootType, Type
}
}
}
else if (type is DecltypeType decltypeType)
{
result.typeName = GetTypeName(cursor, context, rootType, decltypeType.UnderlyingType, ignoreTransparentStructsWhereRequired, out _);
}
else if (type is DeducedType deducedType)
{
result.typeName = GetTypeName(cursor, context, rootType, deducedType.CanonicalType, ignoreTransparentStructsWhereRequired, out _);
Expand Down Expand Up @@ -3536,6 +3544,10 @@ private void GetTypeSize(Cursor cursor, Type type, ref long alignment32, ref lon
}
}
}
else if (type is DecltypeType decltypeType)
{
GetTypeSize(cursor, decltypeType.UnderlyingType, ref alignment32, ref alignment64, ref has8BytePrimitiveField, out size32, out size64);
}
else if (type is ElaboratedType elaboratedType)
{
GetTypeSize(cursor, elaboratedType.NamedType, ref alignment32, ref alignment64, ref has8BytePrimitiveField, out size32, out size64);
Expand Down Expand Up @@ -4465,6 +4477,10 @@ private bool IsFixedSize(Cursor cursor, Type type)
{
return true;
}
else if (type is DecltypeType decltypeType)
{
return IsFixedSize(cursor, decltypeType.UnderlyingType);
}
else if (type is ElaboratedType elaboratedType)
{
return IsFixedSize(cursor, elaboratedType.NamedType);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,9 @@ public abstract class StructDeclarationTest : PInvokeGeneratorTest
[Test]
public Task BitfieldTest() => BitfieldTestImpl();

[Test]
public Task DeclTypeTest() => DeclTypeTestImpl();

[Test]
public Task ExcludeTest() => ExcludeTestImpl();

Expand Down Expand Up @@ -216,6 +219,8 @@ public abstract class StructDeclarationTest : PInvokeGeneratorTest

protected abstract Task BitfieldTestImpl();

protected abstract Task DeclTypeTestImpl();

protected abstract Task ExcludeTestImpl();

protected abstract Task FixedSizedBufferNonPrimitiveTestImpl(string nativeType, string expectedManagedType);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -320,6 +320,37 @@ public uint o0_b1_1
return ValidateGeneratedCSharpCompatibleUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"using System;
using System.Runtime.InteropServices;

namespace ClangSharp.Test
{
public partial struct MyStruct
{
[NativeTypeName(""decltype(&MyFunction)"")]
public IntPtr _callback;
}

public static partial class Methods
{
[DllImport(""ClangSharpPInvokeGenerator"", CallingConvention = CallingConvention.Cdecl, ExactSpelling = true)]
public static extern void MyFunction();
}
}
";
return ValidateGeneratedCSharpCompatibleUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -324,6 +324,37 @@ public uint o0_b1_1
return ValidateGeneratedCSharpCompatibleWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"using System;
using System.Runtime.InteropServices;

namespace ClangSharp.Test
{
public partial struct MyStruct
{
[NativeTypeName(""decltype(&MyFunction)"")]
public IntPtr _callback;
}

public static partial class Methods
{
[DllImport(""ClangSharpPInvokeGenerator"", CallingConvention = CallingConvention.Cdecl, ExactSpelling = true)]
public static extern void MyFunction();
}
}
";
return ValidateGeneratedCSharpCompatibleWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -320,6 +320,36 @@ public uint o0_b1_1
return ValidateGeneratedCSharpLatestUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"using System.Runtime.InteropServices;

namespace ClangSharp.Test
{
public unsafe partial struct MyStruct
{
[NativeTypeName(""decltype(&MyFunction)"")]
public delegate* unmanaged[Cdecl]<void> _callback;
}

public static partial class Methods
{
[DllImport(""ClangSharpPInvokeGenerator"", CallingConvention = CallingConvention.Cdecl, ExactSpelling = true)]
public static extern void MyFunction();
}
}
";
return ValidateGeneratedCSharpLatestUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -324,6 +324,36 @@ public uint o0_b1_1
return ValidateGeneratedCSharpLatestWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"using System.Runtime.InteropServices;

namespace ClangSharp.Test
{
public unsafe partial struct MyStruct
{
[NativeTypeName(""decltype(&MyFunction)"")]
public delegate* unmanaged[Cdecl]<void> _callback;
}

public static partial class Methods
{
[DllImport(""ClangSharpPInvokeGenerator"", CallingConvention = CallingConvention.Cdecl, ExactSpelling = true)]
public static extern void MyFunction();
}
}
";
return ValidateGeneratedCSharpLatestWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -320,6 +320,36 @@ public uint o0_b1_1
return ValidateGeneratedCSharpPreviewUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"using System.Runtime.InteropServices;

namespace ClangSharp.Test
{
public unsafe partial struct MyStruct
{
[NativeTypeName(""decltype(&MyFunction)"")]
public delegate* unmanaged[Cdecl]<void> _callback;
}

public static partial class Methods
{
[DllImport(""ClangSharpPInvokeGenerator"", CallingConvention = CallingConvention.Cdecl, ExactSpelling = true)]
public static extern void MyFunction();
}
}
";
return ValidateGeneratedCSharpPreviewUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -324,6 +324,36 @@ public uint o0_b1_1
return ValidateGeneratedCSharpPreviewWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"using System.Runtime.InteropServices;

namespace ClangSharp.Test
{
public unsafe partial struct MyStruct
{
[NativeTypeName(""decltype(&MyFunction)"")]
public delegate* unmanaged[Cdecl]<void> _callback;
}

public static partial class Methods
{
[DllImport(""ClangSharpPInvokeGenerator"", CallingConvention = CallingConvention.Cdecl, ExactSpelling = true)]
public static extern void MyFunction();
}
}
";
return ValidateGeneratedCSharpPreviewWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -296,6 +296,35 @@ struct MyStruct3
return ValidateGeneratedXmlCompatibleUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"<?xml version=""1.0"" encoding=""UTF-8"" standalone=""yes"" ?>
<bindings>
<namespace name=""ClangSharp.Test"">
<struct name=""MyStruct"" access=""public"">
<field name=""_callback"" access=""public"">
<type native=""decltype(&amp;MyFunction)"">IntPtr</type>
</field>
</struct>
<class name=""Methods"" access=""public"" static=""true"">
<function name=""MyFunction"" access=""public"" lib=""ClangSharpPInvokeGenerator"" convention=""Cdecl"" static=""true"">
<type>void</type>
</function>
</class>
</namespace>
</bindings>
";
return ValidateGeneratedXmlCompatibleUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -302,6 +302,35 @@ struct MyStruct3
return ValidateGeneratedXmlCompatibleWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"<?xml version=""1.0"" encoding=""UTF-8"" standalone=""yes"" ?>
<bindings>
<namespace name=""ClangSharp.Test"">
<struct name=""MyStruct"" access=""public"">
<field name=""_callback"" access=""public"">
<type native=""decltype(&amp;MyFunction)"">IntPtr</type>
</field>
</struct>
<class name=""Methods"" access=""public"" static=""true"">
<function name=""MyFunction"" access=""public"" lib=""ClangSharpPInvokeGenerator"" convention=""Cdecl"" static=""true"">
<type>void</type>
</function>
</class>
</namespace>
</bindings>
";
return ValidateGeneratedXmlCompatibleWindowsBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -296,6 +296,35 @@ struct MyStruct3
return ValidateGeneratedXmlLatestUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task DeclTypeTestImpl()
{
var inputContents = @"extern ""C"" void MyFunction();

typedef struct
{
decltype(&MyFunction) _callback;
} MyStruct;
";

var expectedOutputContents = @"<?xml version=""1.0"" encoding=""UTF-8"" standalone=""yes"" ?>
<bindings>
<namespace name=""ClangSharp.Test"">
<struct name=""MyStruct"" access=""public"" unsafe=""true"">
<field name=""_callback"" access=""public"">
<type native=""decltype(&amp;MyFunction)"">delegate* unmanaged[Cdecl]&lt;void&gt;</type>
</field>
</struct>
<class name=""Methods"" access=""public"" static=""true"">
<function name=""MyFunction"" access=""public"" lib=""ClangSharpPInvokeGenerator"" convention=""Cdecl"" static=""true"">
<type>void</type>
</function>
</class>
</namespace>
</bindings>
";
return ValidateGeneratedXmlLatestUnixBindingsAsync(inputContents, expectedOutputContents);
}

protected override Task ExcludeTestImpl()
{
var inputContents = "typedef struct MyStruct MyStruct;";
Expand Down
Loading