views:

229

answers:

2

Hello,

I need to call the co-class function by reading its address from vtable of COM exposed interface methods. I need some generic way to read addresses.

Now I need to call the function, which would have specific address(NOT KNOWN) arguments(parameters) which I have collected from TLB, and name as well. How that address corresponds to that function name to which I am going to call.

For this I need to traverse vtable which is holding functional addresses, LASTLY need to correspond function address with NAME of that function. This is I dont know. How? More over one function with the same name may appear in vtable(Overloading case). In that case we need to distinguish function names w.r.t their addresses. How to tackle ? Regards Usman

A: 

Call ITypeInfo::GetFuncDesc for each function and the FUNCDESC structure you get back contains the vtable index in the oVft member. Cast an interfaces vtable to void** and just use it as an index.

Of course quite why you need to do this I do not know :)

tyranid
I wonder we cannot use "lpVtable" member. It's hidden. Whenever we refer this member e.g say pTypeInfo->lpVtble .it gives error and say its not the member.
Usman
I think you don't understand how COM objects work. To do unit testing of an object you need an instance. So you do `IInterfaceToTest* pTest; CoCreateInstance(..., IID_IInterfaceToTest, ` (assuming you are writing in C/C++). To get the vtable you do `void** pVTable = *((void***)pTest);` and you finally do `void* pFunction = pVTable[funcDesc.oVft];` See simple. If you are doing it in another language with no access to the binary representation (say VB) then life is hard. If you are using .NET you can convert the type library into native interfaces and invoke the methods.
tyranid
OK.! I got vtable address by other means..typedef void (*FN)(void);int* dwPtr= (int*)pIUknown;pFn=(FN)*((int*)*(BTW how u notice that typecasting pTest with *(void***) you'll get vTable array..?
Usman
You _really_ shouldn't use int* to get pointers as if you ever move to 64bit it will go bad :)
tyranid
Respectfully SiroVft does'nt provide you the proper index.If my method is placed at 7th index(which I checked by hardoding) oVft showes this as 28. Like It shows QuesryInterface at 0, AddRef at 4th index, Release at at 8 and so on.....
Usman
Actually I take it back oVft is the byte offset, so divide the number by sizeof(void*), my mind must be rotting :)
tyranid
thnx Sir now everry thing is working..:-)How you noticed that typecasting pTest with *(void***)pIsomeInterface you will get vtable array?
Usman
That is just how COM works :) For example http://blogs.msdn.com/oldnewthing/archive/2004/02/05/68017.aspx gives a nice overview.
tyranid
Thnx for providing me sensare help:-)
Usman
If you are so thankful accept the answer :)
tyranid
A: 

Respectfully Sir.!!

I am designing a Unit Testing framework for which I need to pull out all function signatures of certain COM Exe or COM DLL to show in the grid or whatever interface to user, so that later by selecting certain function signature from that list, He/She can execute that function after providing the arguments(data as parameters) to that function. All this would be done dynamically at runtime, on runtime function will be called whatever user wants.

This can be achieved from various ways.

By providing TLB(Type libraries) we can pull every function signature and can show every signature to Grid control or on Tree control. Second step is to call these functions at runtime by providing data. Calling require data and address of functions(or Names). I would have some GUI panel or control which will take the data from user and that data would then become as arguments.

Now real problem comes for which I posted earlier. Call to functions/methods of that interface exposed by COM component implemented by co-class. This requires to trail down vtable of interface exposed by component , finding the address of that function and then need to know IS IT REALLY THAT ADDRESS TO WHICH I AM GOING TO CALL AS FUNCTION? So this requires to translate that address to function name and then comparison some string comparison would decide that whether it was really that function name which USER CLICKED from Tree Control showing signatures.

Suggestions or reccommendations?

Usman