Skip to content

Commit cf2786c

Browse files
authored
Use StrategyBasedComWrappers for all IError* interfaces in OleDb (#118513)
1 parent d39490d commit cf2786c

File tree

7 files changed

+55
-204
lines changed

7 files changed

+55
-204
lines changed

src/libraries/System.Data.OleDb/src/DbPropSet.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,7 @@ private void SetLastErrorInfo(OleDbHResult lastErrorHr)
111111
}
112112
finally
113113
{
114-
UnsafeNativeMethods.ReleaseErrorInfoObject(errorInfo);
114+
UnsafeNativeMethods.ReleaseComWrappersObject(errorInfo);
115115
}
116116
}
117117

src/libraries/System.Data.OleDb/src/OleDbComWrappers.cs

Lines changed: 0 additions & 124 deletions
This file was deleted.

src/libraries/System.Data.OleDb/src/OleDbConnection.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -615,7 +615,7 @@ internal bool SupportSchemaRowset(Guid schema)
615615
}
616616
finally
617617
{
618-
UnsafeNativeMethods.ReleaseErrorInfoObject(errorInfo);
618+
UnsafeNativeMethods.ReleaseComWrappersObject(errorInfo);
619619
}
620620
}
621621
else if (0 < hresult)

src/libraries/System.Data.OleDb/src/OleDbError.cs

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ internal OleDbError(UnsafeNativeMethods.IErrorRecords errorRecords, int index)
2424

2525
if (OleDbHResult.DB_E_NOLOCALE == hr)
2626
{
27-
Marshal.ReleaseComObject(errorInfo);
27+
UnsafeNativeMethods.ReleaseComWrappersObject(errorInfo);
2828
lcid = Interop.Kernel32.GetUserDefaultLCID();
2929
errorInfo = errorRecords.GetErrorInfo(index, lcid);
3030

@@ -43,7 +43,7 @@ internal OleDbError(UnsafeNativeMethods.IErrorRecords errorRecords, int index)
4343

4444
if (OleDbHResult.DB_E_NOLOCALE == hr)
4545
{
46-
Marshal.ReleaseComObject(errorInfo);
46+
UnsafeNativeMethods.ReleaseComWrappersObject(errorInfo);
4747
lcid = Interop.Kernel32.GetUserDefaultLCID();
4848
errorInfo = errorRecords.GetErrorInfo(index, lcid);
4949

@@ -56,7 +56,7 @@ internal OleDbError(UnsafeNativeMethods.IErrorRecords errorRecords, int index)
5656
{
5757
this.source = ODB.FailedGetSource(hr);
5858
}
59-
Marshal.ReleaseComObject(errorInfo!);
59+
UnsafeNativeMethods.ReleaseComWrappersObject(errorInfo);
6060
}
6161
}
6262

@@ -66,7 +66,7 @@ internal OleDbError(UnsafeNativeMethods.IErrorRecords errorRecords, int index)
6666
if (null != sqlErrorInfo)
6767
{
6868
this.nativeError = sqlErrorInfo.GetSQLInfo(out this.sqlState);
69-
Marshal.ReleaseComObject(sqlErrorInfo);
69+
UnsafeNativeMethods.ReleaseComWrappersObject(sqlErrorInfo);
7070
}
7171
}
7272

src/libraries/System.Data.OleDb/src/System.Data.OleDb.csproj

Lines changed: 19 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,8 @@
88
<NoWarn>$(NoWarn);CA2249</NoWarn>
99
<!-- Suppress SYSLIB0004: 'RuntimeHelpers.PrepareConstrainedRegions()' is obsolete to avoid ifdefs. -->
1010
<NoWarn>$(NoWarn);SYSLIB0004</NoWarn>
11+
<!-- Suppress CS3016: Arrays as attribute arguments is not CLS-compliant to work around https://github.com/dotnet/roslyn/issues/68526 in generated code -->
12+
<NoWarn>$(NoWarn);CS3016</NoWarn>
1113
<UseCompilerGeneratedDocXmlFile>false</UseCompilerGeneratedDocXmlFile>
1214
<IsPackable>true</IsPackable>
1315
<PackageDescription>Provides a collection of classes for OLEDB.
@@ -32,36 +34,21 @@ System.Data.OleDb.OleDbTransaction</PackageDescription>
3234
</PropertyGroup>
3335

3436
<ItemGroup Condition="'$(TargetPlatformIdentifier)' == 'windows'">
35-
<Compile Include="$(CommonPath)Interop\Windows\Interop.Libraries.cs"
36-
Link="Common\Interop\Windows\Interop.Libraries.cs" />
37-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.GetUserDefaultLCID.cs"
38-
Link="Common\Interop\Windows\Kernel32\Interop.GetUserDefaultLCID.cs" />
39-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.GetCurrentProcessId.cs"
40-
Link="Common\Interop\Windows\Kernel32\Interop.GetCurrentProcessId.cs" />
41-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.LocalAlloc.cs"
42-
Link="Common\Interop\Windows\Kernel32\Interop.LocalAlloc.cs" />
43-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.LocalFree.cs"
44-
Link="Common\Interop\Windows\Kernel32\Interop.LocalFree.cs" />
45-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.Semaphore.cs"
46-
Link="Common\Interop\Windows\Kernel32\Interop.Semaphore.cs" />
47-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.WaitForSingleObject.cs"
48-
Link="Common\Interop\Windows\Kernel32\Interop.WaitForSingleObject.cs" />
49-
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.WaitForMultipleObjects.cs"
50-
Link="Common\Interop\Windows\Kernel32\Interop.WaitForMultipleObjects.cs" />
51-
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.SysAllocStringLen.cs"
52-
Link="Common\Interop\Windows\OleAut32\Interop.SysAllocStringLen.cs" />
53-
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.SetErrorInfo.cs"
54-
Link="Common\Interop\Windows\OleAut32\Interop.SetErrorInfo.cs" />
55-
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.SysFreeString.cs"
56-
Link="Common\Interop\Windows\OleAut32\Interop.SysFreeString.cs" />
57-
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.VariantClear.cs"
58-
Link="Common\Interop\Windows\OleAut32\Interop.VariantClear.cs" />
59-
<Compile Include="$(CommonPath)Interop\Windows\Ole32\Interop.CoTaskMemAlloc.cs"
60-
Link="Common\Interop\Windows\Ole32\Interop.CoTaskMemAlloc.cs" />
61-
<Compile Include="$(CommonPath)Interop\Windows\Ole32\Interop.PropVariantClear.cs"
62-
Link="Common\Interop\Windows\Ole32\Interop.PropVariantClear.cs" />
63-
<Compile Include="$(CommonPath)System\Data\Common\MultipartIdentifier.cs"
64-
Link="Common\System\Data\Common\MultipartIdentifier.cs" />
37+
<Compile Include="$(CommonPath)Interop\Windows\Interop.Libraries.cs" Link="Common\Interop\Windows\Interop.Libraries.cs" />
38+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.GetUserDefaultLCID.cs" Link="Common\Interop\Windows\Kernel32\Interop.GetUserDefaultLCID.cs" />
39+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.GetCurrentProcessId.cs" Link="Common\Interop\Windows\Kernel32\Interop.GetCurrentProcessId.cs" />
40+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.LocalAlloc.cs" Link="Common\Interop\Windows\Kernel32\Interop.LocalAlloc.cs" />
41+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.LocalFree.cs" Link="Common\Interop\Windows\Kernel32\Interop.LocalFree.cs" />
42+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.Semaphore.cs" Link="Common\Interop\Windows\Kernel32\Interop.Semaphore.cs" />
43+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.WaitForSingleObject.cs" Link="Common\Interop\Windows\Kernel32\Interop.WaitForSingleObject.cs" />
44+
<Compile Include="$(CommonPath)Interop\Windows\Kernel32\Interop.WaitForMultipleObjects.cs" Link="Common\Interop\Windows\Kernel32\Interop.WaitForMultipleObjects.cs" />
45+
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.SysAllocStringLen.cs" Link="Common\Interop\Windows\OleAut32\Interop.SysAllocStringLen.cs" />
46+
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.SetErrorInfo.cs" Link="Common\Interop\Windows\OleAut32\Interop.SetErrorInfo.cs" />
47+
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.SysFreeString.cs" Link="Common\Interop\Windows\OleAut32\Interop.SysFreeString.cs" />
48+
<Compile Include="$(CommonPath)Interop\Windows\OleAut32\Interop.VariantClear.cs" Link="Common\Interop\Windows\OleAut32\Interop.VariantClear.cs" />
49+
<Compile Include="$(CommonPath)Interop\Windows\Ole32\Interop.CoTaskMemAlloc.cs" Link="Common\Interop\Windows\Ole32\Interop.CoTaskMemAlloc.cs" />
50+
<Compile Include="$(CommonPath)Interop\Windows\Ole32\Interop.PropVariantClear.cs" Link="Common\Interop\Windows\Ole32\Interop.PropVariantClear.cs" />
51+
<Compile Include="$(CommonPath)System\Data\Common\MultipartIdentifier.cs" Link="Common\System\Data\Common\MultipartIdentifier.cs" />
6552
<Compile Include="AdapterSwitches.cs" />
6653
<Compile Include="ColumnBinding.cs" />
6754
<Compile Include="DbBindings.cs" />
@@ -136,18 +123,15 @@ System.Data.OleDb.OleDbTransaction</PackageDescription>
136123
<Compile Include="System\Data\ProviderBase\DbMetaDataFactory.cs" />
137124
<Compile Include="System\Data\ProviderBase\DbReferenceCollection.cs" />
138125
<Compile Include="System\Data\ProviderBase\WrappedIUnknown.cs" />
139-
<Compile Include="$(CommonPath)System\Obsoletions.cs"
140-
Link="Common\System\Obsoletions.cs" />
126+
<Compile Include="$(CommonPath)System\Obsoletions.cs" Link="Common\System\Obsoletions.cs" />
141127
</ItemGroup>
142128

143129
<ItemGroup Condition="'$(TargetPlatformIdentifier)' == 'windows'">
144130
<Compile Include="UnsafeNativeMethods.COMWrappers.cs" />
145-
<Compile Include="OleDbComWrappers.cs" />
146131
</ItemGroup>
147132

148133
<ItemGroup>
149-
<EmbeddedResource Include="Resources\System.Data.OleDb.OleDbMetaData.xml"
150-
LogicalName="System.Data.OleDb.OleDbMetaData.xml" />
134+
<EmbeddedResource Include="Resources\System.Data.OleDb.OleDbMetaData.xml" LogicalName="System.Data.OleDb.OleDbMetaData.xml" />
151135
</ItemGroup>
152136

153137
<ItemGroup Condition="'$(TargetFrameworkIdentifier)' == '.NETCoreApp'">

src/libraries/System.Data.OleDb/src/UnsafeNativeMethods.COMWrappers.cs

Lines changed: 6 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33

44
using System.Data.OleDb;
55
using System.Runtime.InteropServices;
6+
using System.Runtime.InteropServices.Marshalling;
67

78
namespace System.Data.Common
89
{
@@ -15,27 +16,15 @@ internal static partial class UnsafeNativeMethods
1516
[LibraryImport(Interop.Libraries.OleAut32)]
1617
internal static unsafe partial OleDbHResult GetErrorInfo(
1718
int dwReserved,
18-
System.IntPtr* ppIErrorInfo);
19+
[MarshalUsing(typeof(UniqueComInterfaceMarshaller<IErrorInfo>))]
20+
out IErrorInfo? ppIErrorInfo);
1921

20-
internal static unsafe OleDbHResult GetErrorInfo(
21-
int dwReserved,
22-
out UnsafeNativeMethods.IErrorInfo? ppIErrorInfo)
22+
internal static void ReleaseComWrappersObject(object? obj)
2323
{
24-
ppIErrorInfo = null;
25-
IntPtr pErrorInfo;
26-
var hr = GetErrorInfo(dwReserved, &pErrorInfo);
27-
if (hr == OleDbHResult.S_OK)
24+
if (obj is not null)
2825
{
29-
ppIErrorInfo = (UnsafeNativeMethods.IErrorInfo)OleDbComWrappers.Instance
30-
.GetOrCreateObjectForComInstance(pErrorInfo, CreateObjectFlags.UniqueInstance);
26+
((ComObject)obj).FinalRelease();
3127
}
32-
33-
return hr;
34-
}
35-
36-
internal static void ReleaseErrorInfoObject(UnsafeNativeMethods.IErrorInfo errorInfo)
37-
{
38-
((IDisposable)errorInfo).Dispose();
3928
}
4029
}
4130
}

src/libraries/System.Data.OleDb/src/UnsafeNativeMethods.cs

Lines changed: 24 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33

44
using System.Diagnostics;
55
using System.Runtime.InteropServices;
6+
using System.Runtime.InteropServices.Marshalling;
67
using System.Security;
78

89
#pragma warning disable 0618 // ComInterfaceType.InterfaceIsDual is obsolete
@@ -507,10 +508,18 @@ System.Data.OleDb.OleDbHResult GetSchemas(
507508
[Out] out IntPtr prgRestrictionSupport);
508509
}
509510

510-
[Guid("1CF2B120-547D-101B-8E65-08002B2BD119"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), ComImport, SuppressUnmanagedCodeSecurity]
511-
internal interface IErrorInfo
511+
[Guid("0C733A74-2A1C-11CE-ADE5-00AA0044773D"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), GeneratedComInterface, SuppressUnmanagedCodeSecurity]
512+
internal partial interface ISQLErrorInfo
512513
{
513-
[Obsolete("not used", true)] void GetGUID(/*deleted parameter signature*/);
514+
[return: MarshalAs(UnmanagedType.I4)]
515+
int GetSQLInfo(
516+
[MarshalAs(UnmanagedType.BStr)] out string pbstrSQLState);
517+
}
518+
519+
[Guid("1CF2B120-547D-101B-8E65-08002B2BD119"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), GeneratedComInterface, SuppressUnmanagedCodeSecurity]
520+
internal partial interface IErrorInfo
521+
{
522+
[Obsolete("not used")] void GetGUID(/*deleted parameter signature*/);
514523

515524
[PreserveSig]
516525
System.Data.OleDb.OleDbHResult GetSource(
@@ -539,25 +548,26 @@ virtual HRESULT STDMETHODCALLTYPE GetHelpContext(
539548
/* [out] */ DWORD *pdwHelpContext) = 0;
540549
#endif
541550

542-
[Guid("0C733A67-2A1C-11CE-ADE5-00AA0044773D"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), ComImport, SuppressUnmanagedCodeSecurity]
543-
internal interface IErrorRecords
551+
[Guid("0C733A67-2A1C-11CE-ADE5-00AA0044773D"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), GeneratedComInterface, SuppressUnmanagedCodeSecurity]
552+
internal partial interface IErrorRecords
544553
{
545-
[Obsolete("not used", true)] void AddErrorRecord(/*deleted parameter signature*/);
554+
[Obsolete("not used")] void AddErrorRecord(/*deleted parameter signature*/);
546555

547-
[Obsolete("not used", true)] void GetBasicErrorInfo(/*deleted parameter signature*/);
556+
[Obsolete("not used")] void GetBasicErrorInfo(/*deleted parameter signature*/);
548557

549558
[PreserveSig]
550559
System.Data.OleDb.OleDbHResult GetCustomErrorObject( // may return E_NOINTERFACE when asking for IID_ISQLErrorInfo
551-
[In] int ulRecordNum,
552-
[In] in Guid riid,
553-
[Out, MarshalAs(UnmanagedType.Interface)] out ISQLErrorInfo ppObject);
560+
int ulRecordNum,
561+
in Guid riid,
562+
[MarshalUsing(typeof(UniqueComInterfaceMarshaller<ISQLErrorInfo>))]
563+
out ISQLErrorInfo ppObject);
554564

555-
[return: MarshalAs(UnmanagedType.Interface)]
565+
[return: MarshalUsing(typeof(UniqueComInterfaceMarshaller<IErrorInfo>))]
556566
IErrorInfo GetErrorInfo(
557-
[In] int ulRecordNum,
558-
[In] int lcid);
567+
int ulRecordNum,
568+
int lcid);
559569

560-
[Obsolete("not used", true)] void GetErrorParameters(/*deleted parameter signature*/);
570+
[Obsolete("not used")] void GetErrorParameters(/*deleted parameter signature*/);
561571

562572
int GetRecordCount();
563573
}
@@ -725,14 +735,6 @@ System.Data.OleDb.OleDbHResult GetReferencedRowset(
725735
//int GetSpecification(/*deleted parameter signature*/);
726736
}
727737

728-
[Guid("0C733A74-2A1C-11CE-ADE5-00AA0044773D"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), ComImport, SuppressUnmanagedCodeSecurity]
729-
internal interface ISQLErrorInfo
730-
{
731-
[return: MarshalAs(UnmanagedType.I4)]
732-
int GetSQLInfo(
733-
[Out, MarshalAs(UnmanagedType.BStr)] out string pbstrSQLState);
734-
}
735-
736738
[Guid("0C733A5F-2A1C-11CE-ADE5-00AA0044773D"), InterfaceType(ComInterfaceType.InterfaceIsIUnknown), ComImport, SuppressUnmanagedCodeSecurity]
737739
internal interface ITransactionLocal
738740
{

0 commit comments

Comments
 (0)