📄 typelib2.c
字号:
foo.next_hash = -1;
guidoffset = ctl2_alloc_guid(This->typelib, &foo);
if (guidoffset == -1) return E_OUTOFMEMORY;
fileoffset = ctl2_alloc_importfile(This->typelib, guidoffset, 2, 0, stdole2tlb);
if (fileoffset == -1) return E_OUTOFMEMORY;
foo.guid = IID_IDispatch;
foo.hreftype = 1;
foo.next_hash = -1;
guidoffset = ctl2_alloc_guid(This->typelib, &foo);
if (guidoffset == -1) return E_OUTOFMEMORY;
impinfo.flags = TKIND_INTERFACE << 24 | MSFT_IMPINFO_OFFSET_IS_GUID;
impinfo.oImpFile = fileoffset;
impinfo.oGuid = guidoffset;
ctl2_alloc_importinfo(This->typelib, &impinfo);
This->typelib->typelib_header.dispatchpos = 1;
This->typeinfo->typekind |= 0x10;
This->typeinfo->typekind &= ~0x0f;
This->typeinfo->typekind |= TKIND_DISPATCH;
}
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_SetDocString {OLEAUT32}
*
* See ICreateTypeInfo_SetDocString.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnSetDocString(
ICreateTypeInfo2* iface,
LPOLESTR pStrDoc)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
int offset;
TRACE("(%p,%s)\n", iface, debugstr_w(pStrDoc));
offset = ctl2_alloc_string(This->typelib, pStrDoc);
if (offset == -1) return E_OUTOFMEMORY;
This->typeinfo->docstringoffs = offset;
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_SetHelpContext {OLEAUT32}
*
* See ICreateTypeInfo_SetHelpContext.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnSetHelpContext(
ICreateTypeInfo2* iface,
DWORD dwHelpContext)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
TRACE("(%p,%d)\n", iface, dwHelpContext);
This->typeinfo->helpcontext = dwHelpContext;
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_SetVersion {OLEAUT32}
*
* See ICreateTypeInfo_SetVersion.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnSetVersion(
ICreateTypeInfo2* iface,
WORD wMajorVerNum,
WORD wMinorVerNum)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
TRACE("(%p,%d,%d)\n", iface, wMajorVerNum, wMinorVerNum);
This->typeinfo->version = wMajorVerNum | (wMinorVerNum << 16);
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_AddRefTypeInfo {OLEAUT32}
*
* See ICreateTypeInfo_AddRefTypeInfo.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnAddRefTypeInfo(
ICreateTypeInfo2* iface,
ITypeInfo* pTInfo,
HREFTYPE* phRefType)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
ITypeLib *container;
UINT index;
HRESULT res;
TRACE("(%p,%p,%p)\n", iface, pTInfo, phRefType);
/*
* If this is one of ours, we set *phRefType to the TYPEINFO offset of
* the referred TypeInfo. Otherwise, we presumably have more magic to do.
*
* Unfortunately, we can't rely on the passed-in TypeInfo even having the
* same internal structure as one of ours. It could be from another
* implementation of ITypeInfo. So we need to do the following...
*/
res = ITypeInfo_GetContainingTypeLib(pTInfo, &container, &index);
if (!SUCCEEDED(res)) {
TRACE("failed to find containing typelib.\n");
return res;
}
if (container == (ITypeLib *)&This->typelib->lpVtblTypeLib2) {
*phRefType = This->typelib->typelib_typeinfo_offsets[index];
} else {
FIXME("(%p,%p,%p), pTInfo from different typelib.\n", iface, pTInfo, phRefType);
}
ITypeLib_Release(container);
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_AddFuncDesc {OLEAUT32}
*
* See ICreateTypeInfo_AddFuncDesc.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnAddFuncDesc(
ICreateTypeInfo2* iface,
UINT index,
FUNCDESC* pFuncDesc)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
int offset;
int *typedata;
int i;
int decoded_size;
FIXME("(%p,%d,%p), stub!\n", iface, index, pFuncDesc);
FIXME("{%d,%p,%p,%d,%d,%d,%d,%d,%d,%d,{%d},%d}\n", pFuncDesc->memid, pFuncDesc->lprgscode, pFuncDesc->lprgelemdescParam, pFuncDesc->funckind, pFuncDesc->invkind, pFuncDesc->callconv, pFuncDesc->cParams, pFuncDesc->cParamsOpt, pFuncDesc->oVft, pFuncDesc->cScodes, pFuncDesc->elemdescFunc.tdesc.vt, pFuncDesc->wFuncFlags);
/* FIXME("{%d, %d}\n", pFuncDesc->lprgelemdescParam[0].tdesc.vt, pFuncDesc->lprgelemdescParam[1].tdesc.vt); */
/* return E_OUTOFMEMORY; */
if (!This->typedata) {
This->typedata = HeapAlloc(GetProcessHeap(), 0, 0x2000);
This->typedata[0] = 0;
}
/* allocate type data space for us */
offset = This->typedata[0];
This->typedata[0] += 0x18 + (pFuncDesc->cParams * 12);
typedata = This->typedata + (offset >> 2) + 1;
/* fill out the basic type information */
typedata[0] = (0x18 + (pFuncDesc->cParams * 12)) | (index << 16);
ctl2_encode_typedesc(This->typelib, &pFuncDesc->elemdescFunc.tdesc, &typedata[1], NULL, NULL, &decoded_size);
typedata[2] = pFuncDesc->wFuncFlags;
typedata[3] = ((sizeof(FUNCDESC) + decoded_size) << 16) | This->typeinfo->cbSizeVft;
typedata[4] = (index << 16) | (pFuncDesc->callconv << 8) | 9;
typedata[5] = pFuncDesc->cParams;
/* NOTE: High word of typedata[3] is total size of FUNCDESC + size of all ELEMDESCs for params + TYPEDESCs for pointer params and return types. */
/* That is, total memory allocation required to reconstitute the FUNCDESC in its entirety. */
typedata[3] += (sizeof(ELEMDESC) * pFuncDesc->cParams) << 16;
for (i = 0; i < pFuncDesc->cParams; i++) {
ctl2_encode_typedesc(This->typelib, &pFuncDesc->lprgelemdescParam[i].tdesc, &typedata[6+(i*3)], NULL, NULL, &decoded_size);
typedata[7+(i*3)] = -1;
typedata[8+(i*3)] = pFuncDesc->lprgelemdescParam[i].u.paramdesc.wParamFlags;
typedata[3] += decoded_size << 16;
#if 0
/* FIXME: Doesn't work. Doesn't even come up with usable VTs for varDefaultValue. */
if (pFuncDesc->lprgelemdescParam[i].u.paramdesc.wParamFlags & PARAMFLAG_FHASDEFAULT) {
ctl2_alloc_custdata(This->typelib, &pFuncDesc->lprgelemdescParam[i].u.paramdesc.pparamdescex->varDefaultValue);
}
#endif
}
/* update the index data */
This->indices[index] = ((0x6000 | This->typeinfo->cImplTypes) << 16) | index;
This->names[index] = -1;
This->offsets[index] = offset;
/* ??? */
if (!This->typeinfo->res2) This->typeinfo->res2 = 0x20;
This->typeinfo->res2 <<= 1;
/* ??? */
if (This->typeinfo->res3 == -1) This->typeinfo->res3 = 0;
This->typeinfo->res3 += 0x38;
/* ??? */
if (index < 2) This->typeinfo->res2 += pFuncDesc->cParams << 4;
This->typeinfo->res3 += pFuncDesc->cParams << 4;
/* adjust size of VTBL */
This->typeinfo->cbSizeVft += 4;
/* Increment the number of function elements */
This->typeinfo->cElement += 1;
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_AddImplType {OLEAUT32}
*
* See ICreateTypeInfo_AddImplType.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnAddImplType(
ICreateTypeInfo2* iface,
UINT index,
HREFTYPE hRefType)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
TRACE("(%p,%d,%d)\n", iface, index, hRefType);
if ((This->typeinfo->typekind & 15) == TKIND_COCLASS) {
int offset;
MSFT_RefRecord *ref;
if (index == 0) {
if (This->typeinfo->datatype1 != -1) return TYPE_E_ELEMENTNOTFOUND;
offset = ctl2_alloc_segment(This->typelib, MSFT_SEG_REFERENCES, sizeof(MSFT_RefRecord), 0);
if (offset == -1) return E_OUTOFMEMORY;
This->typeinfo->datatype1 = offset;
} else {
int lastoffset;
lastoffset = ctl2_find_nth_reference(This->typelib, This->typeinfo->datatype1, index - 1);
if (lastoffset == -1) return TYPE_E_ELEMENTNOTFOUND;
ref = (MSFT_RefRecord *)&This->typelib->typelib_segment_data[MSFT_SEG_REFERENCES][lastoffset];
if (ref->onext != -1) return TYPE_E_ELEMENTNOTFOUND;
offset = ctl2_alloc_segment(This->typelib, MSFT_SEG_REFERENCES, sizeof(MSFT_RefRecord), 0);
if (offset == -1) return E_OUTOFMEMORY;
ref->onext = offset;
}
ref = (MSFT_RefRecord *)&This->typelib->typelib_segment_data[MSFT_SEG_REFERENCES][offset];
ref->reftype = hRefType;
ref->flags = 0;
ref->oCustData = -1;
ref->onext = -1;
} else if ((This->typeinfo->typekind & 15) == TKIND_DISPATCH) {
FIXME("dispatch case unhandled.\n");
} else if ((This->typeinfo->typekind & 15) == TKIND_INTERFACE) {
if (This->typeinfo->cImplTypes) {
return (index == 1)? TYPE_E_BADMODULEKIND: TYPE_E_ELEMENTNOTFOUND;
}
if (index != 0) return TYPE_E_ELEMENTNOTFOUND;
This->typeinfo->cImplTypes++;
/* hacked values for IDispatch only, and maybe only for stdole. */
This->typeinfo->cbSizeVft += 0x0c; /* hack */
This->typeinfo->datatype1 = hRefType;
This->typeinfo->datatype2 = (3 << 16) | 1; /* ? */
} else {
FIXME("AddImplType unsupported on typekind %d\n", This->typeinfo->typekind & 15);
return E_OUTOFMEMORY;
}
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_SetImplTypeFlags {OLEAUT32}
*
* See ICreateTypeInfo_SetImplTypeFlags.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnSetImplTypeFlags(
ICreateTypeInfo2* iface,
UINT index,
INT implTypeFlags)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
int offset;
MSFT_RefRecord *ref;
TRACE("(%p,%d,0x%x)\n", iface, index, implTypeFlags);
if ((This->typeinfo->typekind & 15) != TKIND_COCLASS) {
return TYPE_E_BADMODULEKIND;
}
offset = ctl2_find_nth_reference(This->typelib, This->typeinfo->datatype1, index);
if (offset == -1) return TYPE_E_ELEMENTNOTFOUND;
ref = (MSFT_RefRecord *)&This->typelib->typelib_segment_data[MSFT_SEG_REFERENCES][offset];
ref->flags = implTypeFlags;
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_SetAlignment {OLEAUT32}
*
* See ICreateTypeInfo_SetAlignment.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnSetAlignment(
ICreateTypeInfo2* iface,
WORD cbAlignment)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
TRACE("(%p,%d)\n", iface, cbAlignment);
if (!cbAlignment) return E_INVALIDARG;
if (cbAlignment > 16) return E_INVALIDARG;
This->typeinfo->typekind &= ~0xffc0;
This->typeinfo->typekind |= cbAlignment << 6;
/* FIXME: There's probably some way to simplify this. */
switch (This->typeinfo->typekind & 15) {
case TKIND_ALIAS:
default:
break;
case TKIND_ENUM:
case TKIND_INTERFACE:
case TKIND_DISPATCH:
case TKIND_COCLASS:
if (cbAlignment > 4) cbAlignment = 4;
break;
case TKIND_RECORD:
case TKIND_MODULE:
case TKIND_UNION:
cbAlignment = 1;
break;
}
This->typeinfo->typekind |= cbAlignment << 11;
return S_OK;
}
/******************************************************************************
* ICreateTypeInfo2_SetSchema {OLEAUT32}
*
* See ICreateTypeInfo_SetSchema.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnSetSchema(
ICreateTypeInfo2* iface,
LPOLESTR pStrSchema)
{
FIXME("(%p,%s), stub!\n", iface, debugstr_w(pStrSchema));
return E_OUTOFMEMORY;
}
/******************************************************************************
* ICreateTypeInfo2_AddVarDesc {OLEAUT32}
*
* See ICreateTypeInfo_AddVarDesc.
*/
static HRESULT WINAPI ICreateTypeInfo2_fnAddVarDesc(
ICreateTypeInfo2* iface,
UINT index,
VARDESC* pVarDesc)
{
ICreateTypeInfo2Impl *This = (ICreateTypeInfo2Impl *)iface;
int offset;
INT *typedata;
int var_datawidth;
int var_alignment;
int var_type_size;
int alignment;
TRACE("(%p,%d,%p), stub!\n", iface, index, pVarDesc);
TRACE("%d, %p, %d, {{%x, %d}, {%p, %x}}, 0x%x, %d\n", pVarDesc->memid, pVarDesc->lpstrSchema, pVarDesc->u.oInst,
pVarDesc->elemdescVar.tdesc.u.hreftype, pVarDesc->elemdescVar.tdesc.vt,
pVarDesc->elemdescVar.u.paramdesc.pparamdescex, pVarDesc->elemdescVar.u.paramdesc.wParamFlags,
pVarDesc->wVarFlags, pVarDesc->varkind);
if ((This->typeinfo->cElement >> 16) != index) {
TRACE("Out-of-order element.\n");
return TYPE_E_ELEMENTNOTFOUND;
}
if (!This->typedata) {
This->typedata = HeapAlloc(GetProcessHeap(), 0, 0x2000);
This->typedata[0] = 0;
}
/* allocate type data space for us */
offset = This->typedata[0];
This->typedata[0] += 0x14;
typedata = This->typedata + (offset >> 2) + 1;
/* fill out the basic type information */
typedata[0] = 0x14 | (index << 16);
typedata[2] = pVarDesc->wVarFlags;
typedata[3] = (sizeof(VARDESC) << 16) | 0;
/* update the index data */
This->indices[index] = 0x40000000 + index;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -