MSDN Magazine - January 2009 - (Page 24) Figure 7 Reflecting on Function Members For iFunc = 0 To typeAttr.cFuncs - 1 ' retrieve FUNCDESC: Dim pFuncDesc As IntPtr : typeInfo.GetFuncDesc(iFunc, pFuncDesc) Dim funcDesc = CType(Marshal.PtrToStructure(pFuncDesc, _ GetType(ComTypes.FUNCDESC)), ComTypes.FUNCDESC) Dim names As String() = {""} typeInfo.GetNames(funcDesc.memid, names, 1, 0) Dim funcName = names(0) ' Function formal parameters: Dim cParams = funcDesc.cParams Dim s = "" For iParam = 0 To cParams - 1 Dim elemDesc = CType(Marshal.PtrToStructure( _ New IntPtr(funcDesc.lprgelemdescParam.ToInt64 + _ Marshal.SizeOf(GetType(ComTypes.ELEMDESC)) * iParam), _ GetType(ComTypes.ELEMDESC)), ComTypes.ELEMDESC) If s.Length > 0 Then s &= ", " If (elemDesc.desc.paramdesc.wParamFlags And _ Runtime.InteropServices.ComTypes.PARAMFLAG.PARAMFLAG_FOUT) _ 0 Then s &= "out " s &= DumpTypeDesc(elemDesc.tdesc, typeInfo) Next ' And print out the rest of the function's information: Dim props = "" If (funcDesc.invkind And ComTypes.INVOKEKIND.INVOKE_PROPERTYGET) _ 0 Then props &= "Get " If (funcDesc.invkind And ComTypes.INVOKEKIND.INVOKE_PROPERTYPUT) _ 0 Then props &= "Set " If (funcDesc.invkind And ComTypes.INVOKEKIND.INVOKE_PROPERTYPUTREF) _ 0 Then props &= "Set " Dim isSub = (FUNCDESC.elemdescFunc.tdesc.vt = VarEnum.VT_VOID) s = props & If(isSub, "Sub ", "Function ") & funcName & "(" & s & ")" s &= If(isSub, "", " as " & _ DumpTypeDesc(funcDesc.elemdescFunc.tdesc, typeInfo)) Console.WriteLine(" " & s) typeInfo.ReleaseFuncDesc(pFuncDesc) Next Chasing Down Type References The first task that must be completed is to get a list of imple mented/inherited interfaces. (In COM, one never inherits from another class). Here’s the code: ' Inheritance: For iImplType = 0 To typeAttr.cImplTypes - 1 Dim href As Integer typeInfo.GetRefTypeOfImplType(iImplType, href) ' "href" is an index into the list of type descriptions within the ' type library. Dim implTypeInfo As ComTypes.ITypeInfo typeInfo.GetRefTypeInfo(href, implTypeInfo) ' And GetRefTypeInfo looks up the index to get an ITypeInfo for it. Dim implTypeName = "" implTypeInfo.GetDocumentation(-1, implTypeName, "", 0, "") Console.WriteLine(" Implements {0}", implTypeName) Next There’s a layer of indirection here. GetRefTypeOfImplType doesn’t give you the ITypeInfo of the implemented types directly: instead, it gives you a handle to an ITypeInfo. The function GetRefTy peInfo is what looks up that handle. Then you can use the familiar GetDocumentation(1) to get the name of that implemented type. I’ll discuss handles to ITypeInfo again later. Getting the Members For reflecting on field members, each field has a VARDESC to describe it. Once again, the typeInfo object allocates an unman aged memory block pVarDesc, and you marshal it into a managed block varDesc and release the unmanaged block: ' Field members: For iVar = 0 To typeAttr.cVars - 1 Dim pVarDesc As IntPtr : typeInfo.GetVarDesc(iVar, pVarDesc) Dim varDesc = CType(Marshal.PtrToStructure(pVarDesc, _ GetType(ComTypes.VARDESC)), ComTypes.VARDESC) typeInfo.ReleaseVarDesc(pVarDesc) Dim names As String() = {""} typeInfo.GetNames(varDesc.memid, names, 1, 0) Dim varName = names(0) Console.WriteLine(" Dim {0} As {1}", varName, _ DumpTypeDesc(varDesc.elemdescVar.tdesc, typeInfo)) Next Figure 8 Looking at TYPEDESC Function DumpTypeDesc(ByVal tdesc As ComTypes.TYPEDESC, _ ByVal context As ComTypes.ITypeInfo) As String Dim vt = CType(tdesc.vt, VarEnum) Select Case vt Case VarEnum.VT_PTR Dim tdesc2 = CType(Marshal.PtrToStructure(tdesc.lpValue, _ GetType(ComTypes.TYPEDESC)), ComTypes.TYPEDESC) Return "Ref " & DumpTypeDesc(tdesc2, context) Case VarEnum.VT_USERDEFINED Dim href = CType(tdesc.lpValue.ToInt64 And Integer.MaxValue, Integer) Dim refTypeInfo As ComTypes.ITypeInfo = Nothing context.GetRefTypeInfo(href, refTypeInfo) Dim refTypeName = "" refTypeInfo.GetDocumentation(-1, refTypeName, "", 0, "") Return refTypeName Case VarEnum.VT_CARRAY Dim tdesc2 = CType(Marshal.PtrToStructure(tdesc.lpValue, _ GetType(ComTypes.TYPEDESC)), ComTypes.TYPEDESC) Return "Array of " & DumpTypeDesc(tdesc2, context) ' lpValue is actually an ARRAYDESC structure, which also has ' information on the array dimensions, but alas .NET doesn't ' predefine ARRAYDESC. Case Else ' There are many other VT_s that I haven't special-cased, ' e.g. VT_INTEGER. Return vt.ToString() End Select End Function The function “GetNames” is curious. Conceivably each member might have several names. It’s enough just to get the first. The code for reflecting on function members is generally similar (see Figure 7). The return type is funcDesc.elemdescFunc.tdesc. The count of formal parameters is given by funcDesc.cParams, and formal parameters are stored in the array funcDesc.lprgelemdesc Param. (It’s not pleasant accessing an unmanaged array like this from managed code because you have to do pointer arithmetic.) There are other flags as well as PARAMFLAG_FOUT—flags for in, retval, optional, and so on. Type information for both fields and members was stored in a TYPEDESC structure, and I invoked a function DumpTypeDesc to print it out. It might seem surprising that TYPEDESC is used instead of ITypeInfo. I’ll elaborate next. Primitive and Synthetic Types COM uses TYPEDESC to describe some types and ITypeInfo to describe others. What’s the difference? COM uses ITypeInfo only for classes and interfaces defined in type libraries. And it uses TYPEDESC for primitive types such as Integer or String, and also for compound types such as Array of SpVoice or IUnknown Reference. This is different from .NET: first, in .NET even the primitive types Basic instincts 24 msdn magazine
Table of Contents Feed for the Digital Edition of MSDN Magazine - January 2009 Toolbox CLR Inside Out Basic Instincts Cutting Edge Test Run First Look Geneva Framework Silverlight Windows Mobile Service Station Security Briefs Extreme ASP.NET Foundations .NET Matters { End Bracket } MSDN Magazine - January 2009 MSDN Magazine - January 2009 - (Page Intro) MSDN Magazine - January 2009 - (Page Cover1) MSDN Magazine - January 2009 - (Page Cover2) MSDN Magazine - January 2009 - (Page 1) MSDN Magazine - January 2009 - (Page 2) MSDN Magazine - January 2009 - (Page 3) MSDN Magazine - January 2009 - (Page 4) MSDN Magazine - January 2009 - (Page 5) MSDN Magazine - January 2009 - (Page 6) MSDN Magazine - January 2009 - (Page 7) MSDN Magazine - January 2009 - (Page 8) MSDN Magazine - January 2009 - Toolbox (Page 9) MSDN Magazine - January 2009 - Toolbox (Page 10) MSDN Magazine - January 2009 - Toolbox (Page 11) MSDN Magazine - January 2009 - Toolbox (Page 12) MSDN Magazine - January 2009 - Toolbox (Page 13) MSDN Magazine - January 2009 - Toolbox (Page 14) MSDN Magazine - January 2009 - CLR Inside Out (Page 15) MSDN Magazine - January 2009 - CLR Inside Out (Page 16) MSDN Magazine - January 2009 - CLR Inside Out (Page 17) MSDN Magazine - January 2009 - CLR Inside Out (Page 18) MSDN Magazine - January 2009 - CLR Inside Out (Page 19) MSDN Magazine - January 2009 - CLR Inside Out (Page 20) MSDN Magazine - January 2009 - Basic Instincts (Page 21) MSDN Magazine - January 2009 - Basic Instincts (Page 22) MSDN Magazine - January 2009 - Basic Instincts (Page 23) MSDN Magazine - January 2009 - Basic Instincts (Page 24) MSDN Magazine - January 2009 - Basic Instincts (Page 25) MSDN Magazine - January 2009 - Basic Instincts (Page 26) MSDN Magazine - January 2009 - Basic Instincts (Page 27) MSDN Magazine - January 2009 - Basic Instincts (Page 28) MSDN Magazine - January 2009 - Basic Instincts (Page 29) MSDN Magazine - January 2009 - Basic Instincts (Page 30) MSDN Magazine - January 2009 - Cutting Edge (Page 31) MSDN Magazine - January 2009 - Cutting Edge (Page 32) MSDN Magazine - January 2009 - Cutting Edge (Page 33) MSDN Magazine - January 2009 - Cutting Edge (Page 34) MSDN Magazine - January 2009 - Cutting Edge (Page 35) MSDN Magazine - January 2009 - Cutting Edge (Page 36) MSDN Magazine - January 2009 - Cutting Edge (Page 37) MSDN Magazine - January 2009 - Cutting Edge (Page 38) MSDN Magazine - January 2009 - Test Run (Page 39) MSDN Magazine - January 2009 - Test Run (Page 40) MSDN Magazine - January 2009 - Test Run (Page 41) MSDN Magazine - January 2009 - Test Run (Page 42) MSDN Magazine - January 2009 - Test Run (Page 43) MSDN Magazine - January 2009 - Test Run (Page 44) MSDN Magazine - January 2009 - Test Run (Page 45) MSDN Magazine - January 2009 - Test Run (Page 46) MSDN Magazine - January 2009 - Test Run (Page 47) MSDN Magazine - January 2009 - Test Run (Page 48) MSDN Magazine - January 2009 - Test Run (Page 49) MSDN Magazine - January 2009 - First Look (Page 50) MSDN Magazine - January 2009 - First Look (Page 51) MSDN Magazine - January 2009 - First Look (Page 52) MSDN Magazine - January 2009 - First Look (Page 53) MSDN Magazine - January 2009 - First Look (Page 54) MSDN Magazine - January 2009 - First Look (Page 55) MSDN Magazine - January 2009 - First Look (Page 56) MSDN Magazine - January 2009 - First Look (Page 57) MSDN Magazine - January 2009 - First Look (Page 58) MSDN Magazine - January 2009 - First Look (Page 59) MSDN Magazine - January 2009 - First Look (Page 60) MSDN Magazine - January 2009 - First Look (Page 61) MSDN Magazine - January 2009 - First Look (Page 62) MSDN Magazine - January 2009 - First Look (Page 63) MSDN Magazine - January 2009 - Geneva Framework (Page 64) MSDN Magazine - January 2009 - Geneva Framework (Page 65) MSDN Magazine - January 2009 - Geneva Framework (Page 66) MSDN Magazine - January 2009 - Geneva Framework (Page 67) MSDN Magazine - January 2009 - Geneva Framework (Page 68) MSDN Magazine - January 2009 - Geneva Framework (Page 69) MSDN Magazine - January 2009 - Geneva Framework (Page 70) MSDN Magazine - January 2009 - Geneva Framework (Page 71) MSDN Magazine - January 2009 - Geneva Framework (Page 72) MSDN Magazine - January 2009 - Geneva Framework (Page 73) MSDN Magazine - January 2009 - Geneva Framework (Page 74) MSDN Magazine - January 2009 - Silverlight (Page 75) MSDN Magazine - January 2009 - Silverlight (Page 76) MSDN Magazine - January 2009 - Silverlight (Page 77) MSDN Magazine - January 2009 - Silverlight (Page 78) MSDN Magazine - January 2009 - Silverlight (Page 79) MSDN Magazine - January 2009 - Silverlight (Page 80) MSDN Magazine - January 2009 - Silverlight (Page 81) MSDN Magazine - January 2009 - Silverlight (Page 82) MSDN Magazine - January 2009 - Silverlight (Page 83) MSDN Magazine - January 2009 - Silverlight (Page 84) MSDN Magazine - January 2009 - Silverlight (Page 85) MSDN Magazine - January 2009 - Silverlight (Page 86) MSDN Magazine - January 2009 - Silverlight (Page 87) MSDN Magazine - January 2009 - Windows Mobile (Page 88) MSDN Magazine - January 2009 - Windows Mobile (Page 89) MSDN Magazine - January 2009 - Windows Mobile (Page 90) MSDN Magazine - January 2009 - Windows Mobile (Page 91) MSDN Magazine - January 2009 - Windows Mobile (Page 92) MSDN Magazine - January 2009 - Service Station (Page 93) MSDN Magazine - January 2009 - Service Station (Page 94) MSDN Magazine - January 2009 - Service Station (Page 95) MSDN Magazine - January 2009 - Service Station (Page 96) MSDN Magazine - January 2009 - Service Station (Page 97) MSDN Magazine - January 2009 - Service Station (Page 98) MSDN Magazine - January 2009 - Security Briefs (Page 99) MSDN Magazine - January 2009 - Security Briefs (Page 100) MSDN Magazine - January 2009 - Security Briefs (Page 101) MSDN Magazine - January 2009 - Security Briefs (Page 102) MSDN Magazine - January 2009 - Extreme ASP.NET (Page 103) MSDN Magazine - January 2009 - Extreme ASP.NET (Page 104) MSDN Magazine - January 2009 - Extreme ASP.NET (Page 105) MSDN Magazine - January 2009 - Extreme ASP.NET (Page 106) MSDN Magazine - January 2009 - Extreme ASP.NET (Page 107) MSDN Magazine - January 2009 - Extreme ASP.NET (Page 108) MSDN Magazine - January 2009 - Foundations (Page 109) MSDN Magazine - January 2009 - Foundations (Page 110) MSDN Magazine - January 2009 - Foundations (Page 111) MSDN Magazine - January 2009 - Foundations (Page 112) MSDN Magazine - January 2009 - Foundations (Page 113) MSDN Magazine - January 2009 - Foundations (Page 114) MSDN Magazine - January 2009 - Foundations (Page 115) MSDN Magazine - January 2009 - .NET Matters (Page 116) MSDN Magazine - January 2009 - .NET Matters (Page 117) MSDN Magazine - January 2009 - .NET Matters (Page 118) MSDN Magazine - January 2009 - .NET Matters (Page 119) MSDN Magazine - January 2009 - { End Bracket } (Page 120) MSDN Magazine - January 2009 - { End Bracket } (Page Cover3) MSDN Magazine - January 2009 - { End Bracket } (Page Cover4)
For optimal viewing of this digital publication, please enable JavaScript and then refresh the page. If you would like to try to load the digital publication without using Flash Player detection, please click here.