Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Getting IDL (for TLB) from a COM+ dll when it is not provided

I have a .dll that contains some directshow filters (COM) with specific/custom interfaces to query.

Most 3rd party directshow components contain embedded .tlb files that can be used for cross-enviroment communication (C# typelib import).

I would hate to have to attempt to manually create the interfaces needed for c# because no idl/tlb files were provided.

Is it possible to generate a tlb (or at least, an idl, which I can MIDL compile) from a COM .dll?

like image 341
Paul Knopf Avatar asked Aug 22 '13 16:08

Paul Knopf


1 Answers

Yes, it is possible to reverse engineer/disassemble IDL (or something very close to it). What you need to do is give yourself a new C++ Console Project which gives the default code of

#include "stdafx.h"

int _tmain(int argc, _TCHAR* argv[])
{
    return 0;
}

and then you insert an #import statement underneath the #include statement. So I have been playing with C# assembly marked up to function as a COM Interop DLL and I have called it ComExample2 and it lives in the same solution as the C++ console project that I added which means I can use a nice relative pathname. So my #import statement looks like

#import "..\ComExample2\bin\Debug\ComExample2.tlb" no_namespace named_guids

Then you build your console application. If you delve into the files generated during the build you will find a file that ends with .TLH which stands for type library header. So my path is

..\ComExample2\ConsoleApplication1\Debug\comexample2.tlh

Inside my file is something which looks very much like idl. Here is an edited snippet to give you a flavour....

struct __declspec(uuid("515b1b18-1602-4d42-b743-f1b3c458a0d0"))
/* LIBID */ __ComExample2;
struct /* coclass */ ComExampleClass2;

//
// Type library items
//

struct __declspec(uuid("713007fe-e74c-4fec-b91a-5ef8df279929"))
IFoo : IDispatch
{
    //
    // Wrapper methods for error-handling
    //

    _bstr_t Greeting ( );
    long Sim (
        long a,
        long b );

    //
    // Raw methods provided by interface
    //

      virtual HRESULT __stdcall raw_Greeting (
        /*[out,retval]*/ BSTR * pRetVal ) = 0;
      virtual HRESULT __stdcall raw_Sim (
        /*[in]*/ long a,
        /*[in]*/ long b,
        /*[out,retval]*/ long * pRetVal ) = 0;
};

struct __declspec(uuid("efe233b5-8ab3-4414-855e-1f027e0a72d5"))
ComExampleClass2;
    // interface _Object
    // [ default ] interface IFoo

All of this is generated code so that you can script C++ code against a COM library easily. You'll have to pick through what you need but hopefully that should be enough.

Kind regards,

Lord BattenBerg

like image 189
Lord Battenberg Avatar answered Sep 28 '22 15:09

Lord Battenberg