Zebediah Figura : rpcrt4: Retrieve the underlying interface for dual interfaces.
Alexandre Julliard
julliard at winehq.org
Mon Nov 12 16:26:55 CST 2018
Module: wine
Branch: master
Commit: f6b1341aa2b505f1a1c516ec675f6667381db7c2
URL: https://source.winehq.org/git/wine.git/?a=commit;h=f6b1341aa2b505f1a1c516ec675f6667381db7c2
Author: Zebediah Figura <z.figura12 at gmail.com>
Date: Fri Nov 9 18:01:57 2018 -0600
rpcrt4: Retrieve the underlying interface for dual interfaces.
Signed-off-by: Zebediah Figura <z.figura12 at gmail.com>
Signed-off-by: Huw Davies <huw at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/rpcrt4/ndr_typelib.c | 37 +++++++++++++++++++++++++++++++------
1 file changed, 31 insertions(+), 6 deletions(-)
diff --git a/dlls/rpcrt4/ndr_typelib.c b/dlls/rpcrt4/ndr_typelib.c
index f819026..31d9d40 100644
--- a/dlls/rpcrt4/ndr_typelib.c
+++ b/dlls/rpcrt4/ndr_typelib.c
@@ -792,15 +792,40 @@ err:
}
/* Common helper for Create{Proxy,Stub}FromTypeInfo(). */
-static HRESULT get_iface_info(ITypeInfo *typeinfo, WORD *funcs, WORD *parentfuncs)
+static HRESULT get_iface_info(ITypeInfo **typeinfo, WORD *funcs, WORD *parentfuncs)
{
+ ITypeInfo *real_typeinfo;
TYPEATTR *typeattr;
ITypeLib *typelib;
TLIBATTR *libattr;
+ TYPEKIND typekind;
+ HREFTYPE reftype;
SYSKIND syskind;
HRESULT hr;
- hr = ITypeInfo_GetContainingTypeLib(typeinfo, &typelib, NULL);
+ /* Dual interfaces report their size to be sizeof(IDispatchVtbl) and their
+ * implemented type to be IDispatch. We need to retrieve the underlying
+ * interface to get that information. */
+ hr = ITypeInfo_GetTypeAttr(*typeinfo, &typeattr);
+ if (FAILED(hr))
+ return hr;
+ typekind = typeattr->typekind;
+ ITypeInfo_ReleaseTypeAttr(*typeinfo, typeattr);
+ if (typekind == TKIND_DISPATCH)
+ {
+ hr = ITypeInfo_GetRefTypeOfImplType(*typeinfo, -1, &reftype);
+ if (FAILED(hr))
+ return hr;
+
+ hr = ITypeInfo_GetRefTypeInfo(*typeinfo, reftype, &real_typeinfo);
+ if (FAILED(hr))
+ return hr;
+
+ ITypeInfo_Release(*typeinfo);
+ *typeinfo = real_typeinfo;
+ }
+
+ hr = ITypeInfo_GetContainingTypeLib(*typeinfo, &typelib, NULL);
if (FAILED(hr))
return hr;
@@ -814,12 +839,12 @@ static HRESULT get_iface_info(ITypeInfo *typeinfo, WORD *funcs, WORD *parentfunc
ITypeLib_ReleaseTLibAttr(typelib, libattr);
ITypeLib_Release(typelib);
- hr = ITypeInfo_GetTypeAttr(typeinfo, &typeattr);
+ hr = ITypeInfo_GetTypeAttr(*typeinfo, &typeattr);
if (FAILED(hr))
return hr;
*funcs = typeattr->cFuncs;
*parentfuncs = typeattr->cbSizeVft / (syskind == SYS_WIN64 ? 8 : 4) - *funcs;
- ITypeInfo_ReleaseTypeAttr(typeinfo, typeattr);
+ ITypeInfo_ReleaseTypeAttr(*typeinfo, typeattr);
return S_OK;
}
@@ -903,7 +928,7 @@ HRESULT WINAPI CreateProxyFromTypeInfo(ITypeInfo *typeinfo, IUnknown *outer,
TRACE("typeinfo %p, outer %p, iid %s, proxy_buffer %p, out %p.\n",
typeinfo, outer, debugstr_guid(iid), proxy_buffer, out);
- hr = get_iface_info(typeinfo, &funcs, &parentfuncs);
+ hr = get_iface_info(&typeinfo, &funcs, &parentfuncs);
if (FAILED(hr))
return hr;
@@ -1016,7 +1041,7 @@ HRESULT WINAPI CreateStubFromTypeInfo(ITypeInfo *typeinfo, REFIID iid,
TRACE("typeinfo %p, iid %s, server %p, stub_buffer %p.\n",
typeinfo, debugstr_guid(iid), server, stub_buffer);
- hr = get_iface_info(typeinfo, &funcs, &parentfuncs);
+ hr = get_iface_info(&typeinfo, &funcs, &parentfuncs);
if (FAILED(hr))
return hr;
More information about the wine-cvs
mailing list