📄 dispatch.c
字号:
LPDISPATCH iface,
REFIID riid,
void** ppvObject)
{
StdDispatch *This = (StdDispatch *)iface;
TRACE("(%p)->(%s, %p)\n", iface, debugstr_guid(riid), ppvObject);
if (IsEqualIID(riid, &IID_IDispatch) ||
IsEqualIID(riid, &IID_IUnknown))
{
*ppvObject = (LPVOID)This;
IUnknown_AddRef((LPUNKNOWN)*ppvObject);
return S_OK;
}
return E_NOINTERFACE;
}
/******************************************************************************
* IDispatch_AddRef {OLEAUT32}
*
* See IUnknown_AddRef.
*/
static ULONG WINAPI StdDispatch_AddRef(LPDISPATCH iface)
{
StdDispatch *This = (StdDispatch *)iface;
ULONG refCount = InterlockedIncrement(&This->ref);
TRACE("(%p)->(ref before=%u)\n",This, refCount - 1);
return refCount;
}
/******************************************************************************
* IDispatch_Release {OLEAUT32}
*
* See IUnknown_Release.
*/
static ULONG WINAPI StdDispatch_Release(LPDISPATCH iface)
{
StdDispatch *This = (StdDispatch *)iface;
ULONG refCount = InterlockedDecrement(&This->ref);
TRACE("(%p)->(ref before=%u)\n", This, refCount + 1);
if (!refCount)
{
ITypeInfo_Release(This->pTypeInfo);
CoTaskMemFree(This);
}
return refCount;
}
/******************************************************************************
* IDispatch_GetTypeInfoCount {OLEAUT32}
*
* Get the count of type information in an IDispatch interface.
*
* PARAMS
* iface [I] IDispatch interface
* pctinfo [O] Destination for the count
*
* RETURNS
* Success: S_OK. pctinfo is updated with the count. This is always 1 if
* the object provides type information, and 0 if it does not.
* Failure: E_NOTIMPL. The object does not provide type information.
*
* NOTES
* See IDispatch() and IDispatch_GetTypeInfo().
*/
static HRESULT WINAPI StdDispatch_GetTypeInfoCount(LPDISPATCH iface, UINT * pctinfo)
{
StdDispatch *This = (StdDispatch *)iface;
TRACE("(%p)\n", pctinfo);
*pctinfo = This->pTypeInfo ? 1 : 0;
return S_OK;
}
/******************************************************************************
* IDispatch_GetTypeInfo {OLEAUT32}
*
* Get type information from an IDispatch interface.
*
* PARAMS
* iface [I] IDispatch interface
* iTInfo [I] Index of type information.
* lcid [I] Locale of the type information to get
* ppTInfo [O] Destination for the ITypeInfo object
*
* RETURNS
* Success: S_OK. ppTInfo is updated with the objects type information
* Failure: DISP_E_BADINDEX, if iTInfo is any value other than 0.
*
* NOTES
* See IDispatch.
*/
static HRESULT WINAPI StdDispatch_GetTypeInfo(LPDISPATCH iface, UINT iTInfo, LCID lcid, ITypeInfo** ppTInfo)
{
StdDispatch *This = (StdDispatch *)iface;
TRACE("(%d, %x, %p)\n", iTInfo, lcid, ppTInfo);
*ppTInfo = NULL;
if (iTInfo != 0)
return DISP_E_BADINDEX;
if (This->pTypeInfo)
{
*ppTInfo = This->pTypeInfo;
ITypeInfo_AddRef(*ppTInfo);
}
return S_OK;
}
/******************************************************************************
* IDispatch_GetIDsOfNames {OLEAUT32}
*
* Convert a methods name and an optional set of parameter names into DISPIDs
* for passing to IDispatch_Invoke().
*
* PARAMS
* iface [I] IDispatch interface
* riid [I] Reserved, set to IID_NULL
* rgszNames [I] Name to convert
* cNames [I] Number of names in rgszNames
* lcid [I] Locale of the type information to convert from
* rgDispId [O] Destination for converted DISPIDs.
*
* RETURNS
* Success: S_OK.
* Failure: DISP_E_UNKNOWNNAME, if any of the names is invalid.
* DISP_E_UNKNOWNLCID if lcid is invalid.
* Otherwise, an HRESULT error code.
*
* NOTES
* This call defers to ITypeInfo_GetIDsOfNames(), using the ITypeInfo object
* contained within the IDispatch object.
* The first member of the names list must be a method name. The names following
* the method name are the parameters for that method.
*/
static HRESULT WINAPI StdDispatch_GetIDsOfNames(LPDISPATCH iface, REFIID riid, LPOLESTR * rgszNames, UINT cNames, LCID lcid, DISPID * rgDispId)
{
StdDispatch *This = (StdDispatch *)iface;
TRACE("(%s, %p, %d, 0x%x, %p)\n", debugstr_guid(riid), rgszNames, cNames, lcid, rgDispId);
if (!IsEqualGUID(riid, &IID_NULL))
{
FIXME(" expected riid == IID_NULL\n");
return E_INVALIDARG;
}
return DispGetIDsOfNames(This->pTypeInfo, rgszNames, cNames, rgDispId);
}
/******************************************************************************
* IDispatch_Invoke {OLEAUT32}
*
* Call an object method.
*
* PARAMS
* iface [I] IDispatch interface
* dispIdMember [I] DISPID of the method (from GetIDsOfNames())
* riid [I] Reserved, set to IID_NULL
* lcid [I] Locale of the type information to convert parameters with
* wFlags, [I] Kind of method call (DISPATCH_ flags from "oaidl.h")
* pDispParams [I] Array of method arguments
* pVarResult [O] Destination for the result of the call
* pExcepInfo [O] Destination for exception information
* puArgErr [O] Destination for bad argument
*
* RETURNS
* Success: S_OK.
* Failure: See DispInvoke() for failure cases.
*
* NOTES
* See DispInvoke() and IDispatch().
*/
static HRESULT WINAPI StdDispatch_Invoke(LPDISPATCH iface, DISPID dispIdMember, REFIID riid, LCID lcid,
WORD wFlags, DISPPARAMS * pDispParams, VARIANT * pVarResult,
EXCEPINFO * pExcepInfo, UINT * puArgErr)
{
StdDispatch *This = (StdDispatch *)iface;
TRACE("(%d, %s, 0x%x, 0x%x, %p, %p, %p, %p)\n", dispIdMember, debugstr_guid(riid), lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
if (!IsEqualGUID(riid, &IID_NULL))
{
FIXME(" expected riid == IID_NULL\n");
return E_INVALIDARG;
}
return DispInvoke(This->pvThis, This->pTypeInfo, dispIdMember, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
}
static const IDispatchVtbl StdDispatch_VTable =
{
StdDispatch_QueryInterface,
StdDispatch_AddRef,
StdDispatch_Release,
StdDispatch_GetTypeInfoCount,
StdDispatch_GetTypeInfo,
StdDispatch_GetIDsOfNames,
StdDispatch_Invoke
};
static IDispatch * WINAPI StdDispatch_Construct(
IUnknown * punkOuter,
void * pvThis,
ITypeInfo * pTypeInfo)
{
StdDispatch * pStdDispatch;
pStdDispatch = CoTaskMemAlloc(sizeof(StdDispatch));
if (!pStdDispatch)
return (IDispatch *)pStdDispatch;
pStdDispatch->lpVtbl = &StdDispatch_VTable;
pStdDispatch->pvThis = pvThis;
pStdDispatch->pTypeInfo = pTypeInfo;
pStdDispatch->ref = 1;
/* we keep a reference to the type info so prevent it from
* being destroyed until we are done with it */
ITypeInfo_AddRef(pTypeInfo);
return (IDispatch *)pStdDispatch;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -