| File: Marshallers\ComInterfaceDispatchMarshallingResolver.cs | Web Access |
| Project: src\runtime\src\libraries\System.Runtime.InteropServices\gen\ComInterfaceGenerator\ComInterfaceGenerator.csproj (Microsoft.Interop.ComInterfaceGenerator) |
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. using System; using System.Collections.Generic; using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Syntax; using static Microsoft.CodeAnalysis.CSharp.SyntaxFactory; namespace Microsoft.Interop { internal sealed record ComInterfaceDispatchMarshallingInfo : MarshallingInfo { public static readonly ComInterfaceDispatchMarshallingInfo Instance = new(); } internal sealed class ComInterfaceDispatchMarshallingResolver : IMarshallingGeneratorResolver { public ResolvedGenerator Create(TypePositionInfo info, StubCodeContext context) { if (info.MarshallingAttributeInfo is ComInterfaceDispatchMarshallingInfo) { return context.Direction == MarshalDirection.UnmanagedToManaged ? ResolvedGenerator.Resolved(new Marshaller().Bind(info, context)) : ResolvedGenerator.Resolved(KeepAliveThisMarshaller.Instance.Bind(info, context)); } else { return ResolvedGenerator.UnresolvedGenerator; } } private sealed class Marshaller : IUnboundMarshallingGenerator { public ManagedTypeInfo AsNativeType(TypePositionInfo info) => new PointerTypeInfo( $"{TypeNames.GlobalAlias + TypeNames.System_Runtime_InteropServices_ComWrappers_ComInterfaceDispatch}*", $"{TypeNames.System_Runtime_InteropServices_ComWrappers_ComInterfaceDispatch}*", IsFunctionPointer: false); public IEnumerable<StatementSyntax> Generate(TypePositionInfo info, StubCodeContext codeContext, StubIdentifierContext context) { if (context.CurrentStage != StubIdentifierContext.Stage.Unmarshal) { yield break; } var (managed, native) = context.GetIdentifiers(info); // <managed> = ComWrappers.ComInterfaceDispatch.GetInstance<<managedType>>(<native>); yield return ExpressionStatement( AssignmentExpression(SyntaxKind.SimpleAssignmentExpression, IdentifierName(managed), InvocationExpression( MemberAccessExpression(SyntaxKind.SimpleMemberAccessExpression, TypeSyntaxes.System_Runtime_InteropServices_ComWrappers_ComInterfaceDispatch, GenericName( Identifier("GetInstance"), TypeArgumentList(SingletonSeparatedList(info.ManagedType.Syntax)))), ArgumentList( SingletonSeparatedList( Argument( IdentifierName(native))))))); } public SignatureBehavior GetNativeSignatureBehavior(TypePositionInfo info) => SignatureBehavior.NativeType; public ValueBoundaryBehavior GetValueBoundaryBehavior(TypePositionInfo info, StubCodeContext context) => ValueBoundaryBehavior.NativeIdentifier; public ByValueMarshalKindSupport SupportsByValueMarshalKind(ByValueContentsMarshalKind marshalKind, TypePositionInfo info, out GeneratorDiagnostic? diagnostic) => ByValueMarshalKindSupportDescriptor.Default.GetSupport(marshalKind, info, out diagnostic); public bool UsesNativeIdentifier(TypePositionInfo info, StubCodeContext context) => true; } } }