diff --git a/src/libraries/System.Runtime.InteropServices/gen/ComInterfaceGenerator/ComInterfaceGenerator.cs b/src/libraries/System.Runtime.InteropServices/gen/ComInterfaceGenerator/ComInterfaceGenerator.cs index 25113c404853f5..79fb7e1982ba9f 100644 --- a/src/libraries/System.Runtime.InteropServices/gen/ComInterfaceGenerator/ComInterfaceGenerator.cs +++ b/src/libraries/System.Runtime.InteropServices/gen/ComInterfaceGenerator/ComInterfaceGenerator.cs @@ -185,6 +185,18 @@ public void Initialize(IncrementalGeneratorInitializationContext context) using StringWriter source = new(); source.WriteLine("// "); source.WriteLine("#pragma warning disable CS0612, CS0618"); // Suppress warnings about [Obsolete] member usage in generated code. + + // If the user has specified 'ManagedObjectWrapper', it means that the COM interface will never be used to marshal a native + // object as an RCW (eg. the IDIC vtable will also not be generated, nor any additional supporting code). To reduce binary + // size, we're not emitting the interface methods on the implementation interface that has '[DynamicInterfaceCastableImplementation]' + // on it. However, doing so will cause the CA2256 warning to be produced. We can't remove the attribute, as that would cause + // the wrong exception to be thrown when trying an IDIC cast with this interface (not 'InvalidCastException'). Because this is + // a niche scenario, and we don't want to regress perf or size, we can just disable the warning instead. + if (interfaceContext.Options is ComInterfaceOptions.ManagedObjectWrapper) + { + source.WriteLine("#pragma warning disable CA2256"); + } + interfaceInfo.WriteTo(source); // Two newlines looks cleaner than one source.WriteLine(); diff --git a/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/Marshalling/ComInterfaceOptions.cs b/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/Marshalling/ComInterfaceOptions.cs index b7df97381e1fca..a4e952483dc03a 100644 --- a/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/Marshalling/ComInterfaceOptions.cs +++ b/src/libraries/System.Runtime.InteropServices/src/System/Runtime/InteropServices/Marshalling/ComInterfaceOptions.cs @@ -23,6 +23,17 @@ public enum ComInterfaceOptions /// /// Generate a wrapper for managed objects to enable exposing them through the COM interface. /// + /// + /// + /// When this flag is the only one specified on a given COM interface, no implementation methods will be generated + /// to support casts. In such a scenario, + /// attempting to cast to that interface type will still succeed, but any calls to interface methods will fail. + /// + /// + /// Using only this flag is purely a binary size optimization. If calling methods via this interface on native + /// object is required, the flag should also be used instead. + /// + /// ManagedObjectWrapper = 0x1, /// /// Generate a wrapper for COM objects to enable exposing them through the managed interface.