tags:

views:

1252

answers:

3

I'd like to dynamically load and use a .Net assembly created in C# from a Delphi Win32 application. My classes and interfaces are marked as ComVisible, but I would like to avoid registering the assembly. Is this possible?

P.S. I found here link text another good discussion on the topic, but it is more around hosting the CLR. Which begs a question - why would you host CLR versus using ClrCreateManagedInstance?

A: 

Unfortunately this can't be done (to my knowledge) without exposing a COM object, as .NET dll's are not TRULY compiled to a library that Delphi (or anything else) can load, since that is all done by the JIT compiler at runtime.

Adam Robinson
But you don't necessarily need to register COM classes.
Jonathan Allen
+7  A: 

Strangely enough, I couldn't find an answer on StackOverflow, and there is not much on the Net, especially for Delphi. I found the solution from examples posted here. Here's what I got at the end:

function ClrCreateManagedInstance(pTypeName: PWideChar; const riid: TIID;
out ppObject): HRESULT; stdcall; external 'mscoree.dll';

procedure TMyDotNetInterop.InitDotNetAssemblyLibrary;
var
  MyIntf: IMyIntf;
hr: HRESULT;
NetClassName: WideString;
begin
//Partial assembly name works but full assembly name is preffered.
    NetClassName := 'MyCompany.MyDLLName.MyClassThatImplementsIMyIntf,
          MyCompany.MyDLLName';
    hr := ClrCreateManagedInstance(PWideChar(NetClassName), IMyIntf, MyIntf);
    //Check for error. Possible exception is EOleException with ErrorCode
    //FUSION_E_INVALID_NAME = $80131047 2148732999 : The given assembly name 
    //or codebase was invalid.
    //COR_E_TYPELOAD = $80131522 - "Could not find or load a specific type 
    //(class, enum, etc)"
    //E_NOINTERFACE = $80004002 - "Interface not supported".
    OleCheck(hr);
end;

BTW, depending on the situation, you might want to load mscoree.dll dynamically, because it might be not present on the system (XP with no .Net Framework)

Sergey Aldoukhov
Note that unless you've already loaded the CLR into your process, ClrCreateManagedInstance will try to load the runtime v1.0.3705 before trying to load the latest version... which may cause some interesting behavior.
Neil Williams
+1  A: 

Maybe using RegFreeCOM and a COm-Callable Wrapper.

http://msdn.microsoft.com/en-us/magazine/cc188708.aspx

Jonathan Allen
As far as I understand, RegFreeCOM is for accessing COM from .NET. My question was about accessing COM enabled .Net from native code.
Sergey Aldoukhov