Microsoft KB Archive/241810

= IDispEventImpl event handlers may give strange values for parameters in Visual C++ =

Article ID: 241810

Article Last Modified on 6/6/2005

-

APPLIES TO

 Microsoft ActiveX Template Library 3.0, when used with:  Microsoft Visual C++ 6.0 Enterprise Edition

 Microsoft Visual C++ 6.0 Professional Edition

 Microsoft Visual C++ 6.0 Standard Edition 

-

<div class="notice_section">

This article was previously published under Q241810

<div class="symptoms_section">

SYMPTOMS
When using IDispEventImpl in a client that is sinking events with parameters that have different data types with different sizes, the handlers of the events will get incorrect values for the event parameters. The following sample IDL code will cause problems when sinking the event in an ATL client.

[//attributes omitted for brevity. ] dispinterface _ISomeEvents { properties: methods: [id(1), helpstring("method Event1")] HRESULT Event1([in] short s, [in] double d); };

<div class="cause_section">

CAUSE
The cause is errors in the GetFuncInfoFromId function in the IDispEventImpl class, which is located in Atlcom.h.

The following code (in Atlcom.h, line 3918) is in error: for (int i=0; i<pFuncDesc->cParams; i++) { info.pVarTypes[i] = pFuncDesc->lprgelemdescParam[pFuncDesc->cParams - i - 1].tdesc.vt; if (info.pVarTypes[i] == VT_PTR) info.pVarTypes[i] = pFuncDesc->lprgelemdescParam[pFuncDesc->cParams - i - 1].tdesc.lptdesc->vt | VT_BYREF; if (info.pVarTypes[i] == VT_USERDEFINED) info.pVarTypes[i] = GetUserDefinedType(spTypeInfo,pFuncDesc->lprgelemdescParam[pFuncDesc->cParams-i-1].tdesc.hreftype); }

The code should instead be:

for (int i=0; i<pFuncDesc->cParams; i++) { info.pVarTypes[i] = pFuncDesc->lprgelemdescParam[i].tdesc.vt; if (info.pVarTypes[i] == VT_PTR) info.pVarTypes[i] = pFuncDesc->lprgelemdescParam[i].tdesc.lptdesc->vt | VT_BYREF; if (info.pVarTypes[i] == VT_USERDEFINED) info.pVarTypes[i] = GetUserDefinedType(spTypeInfo,pFuncDesc->lprgelemdescParam[i].tdesc.hreftype); }

<div class="resolution_section">

Workarounds
There are three workarounds for this problem:  Provide the type information for the sink method by using the SINK_ENTRY_INFO macro instead of SINK_ENTRY or SINK_ENTRY_EX. For additional information on how to use this macro, click the article number below to view the article in the Microsoft Knowledge Base:

194179 SAMPLE: AtlEvnt.exe Creates ATL Sinks Using IDispEventImpl

</li> Override the virtual function GetFuncInfoFromId in your IDispEventImpl-derived class. The new function should be identical to the original except for the five altered lines in the code shown in the Cause section of this article.</li> Change the incorrect code in Atlcom.h for the IDispEventImpl::GetFuncInfoFromId function:

<ol> Copy the file Atlcom.h in your project directory and name it Atlcom-fix.h .</li> Change the reference to Atlcom.h in StdAfx.h to Atlcom-fix.h.</li> In Atlcom-fix.h, change the code for the IDispEventImpl::GetFuncInfoFromId function as described in the Cause section of this article.</li> Save Atlcom-fix.h.</li> From the Build menu, select, Rebuild All. Do this on a Debug or ReleaseMinDependency build so that the modified code described previously will be linked into your code.</li></ol> </li></ul>

<div class="status_section">

STATUS
Microsoft has confirmed that this is a bug in the Microsoft products that are listed at the beginning of this article.

Additional query words: bad parms parameters stack order backwards sink event SINK_ENTRY_INFO SINK_ENTRY_EX SINK_ENTRY

Keywords: kbtshoot kbbug kbconnpts kbpending kbactivexevents KB241810

-

[mailto:TECHNET@MICROSOFT.COM Send feedback to Microsoft]

© Microsoft Corporation. All rights reserved.