Skip to content
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

First round of converting System.Drawing.Common to COMWrappers #54636

Merged
merged 13 commits into from
Jun 28, 2021
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ private DrawingComWrappers() { }

protected override object CreateObject(IntPtr externalComObject, CreateObjectFlags flags)
{
Debug.Assert(flags == CreateObjectFlags.None);
Debug.Assert(flags == CreateObjectFlags.UniqueInstance);

Guid pictureIID = IPicture.IID;
int hr = Marshal.QueryInterface(externalComObject, ref pictureIID, out IntPtr comObject);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,12 +35,14 @@ public unsafe void Save(Stream outputStream)
IntPtr streamPtr = IntPtr.Zero;
try
{
using DrawingComWrappers.IPicture picture = (DrawingComWrappers.IPicture)DrawingComWrappers.Instance.GetOrCreateObjectForComInstance(lpPicture, CreateObjectFlags.None);
// Use UniqueInstance here because we never want to cache the wrapper. It only gets used once and then disposed.
using DrawingComWrappers.IPicture picture = (DrawingComWrappers.IPicture)DrawingComWrappers.Instance
.GetOrCreateObjectForComInstance(lpPicture, CreateObjectFlags.UniqueInstance);

var gpStream = new GPStream(outputStream, makeSeekable: false);
streamPtr = DrawingComWrappers.Instance.GetOrCreateComInterfaceForObject(gpStream, CreateComInterfaceFlags.None);

Marshal.ThrowExceptionForHR(picture.SaveAsFile(streamPtr, -1, null));
CheckSaveAsFileResult(picture.SaveAsFile(streamPtr, -1, null));
}
finally
{
Expand All @@ -52,13 +54,25 @@ public unsafe void Save(Stream outputStream)

if (lpPicture != IntPtr.Zero)
{
// don't assert the count went to 0 here because some other thread could be using the same lpPicture
Marshal.Release(lpPicture);
int count = Marshal.Release(lpPicture);
Debug.Assert(count == 0);
}

}
}
}

private static void CheckSaveAsFileResult(int errorCode)
{
// Pass -1 for errorInfo to indicate that Windows' GetErrorInfo shouldn't be called, and only
// return the Exception corresponding to the specified errorCode.
Exception? ex = Marshal.GetExceptionForHR(errorCode, errorInfo: new IntPtr(-1));
if (ex != null)
{
throw ex;
}
eerhardt marked this conversation as resolved.
Show resolved Hide resolved
}

[DllImport(Interop.Libraries.Oleaut32)]
private static unsafe extern int OleCreatePictureIndirect(PICTDESC* pictdesc, Guid* refiid, int fOwn, IntPtr* lplpvObj);

Expand Down