I made use of the Component Object Model (COM) in the .NET Framework before in order to use my C# class library in Delphi as shown in this YouTube tutorial, which worked surprisingly well. However, I now want to use .NET Core 6 instead.
Following the official tutorial from Microsoft "Expose .NET Core components to COM", I created this interface
using System.Runtime.InteropServices;
[ComVisible(true)]
[Guid(6775d93d-cf14-42b9-83db-425bac0acf4d)]
[InterfaceType(ComInterfaceType.InterfaceIsIUnknown)]
public interface IServer
{
public string getHelloWorld();
}
and this class.
using System.Runtime.InteropServices;
[ComVisible(true)]
[Guid(d62bf794-d29e-4fcd-8637-994490264a93)]
public class Server : IServer
{
public string getHelloWorld()
{
return "Hello World";
}
}
After building the project, I executed this command to register all of my exposed .NET objects with COM.
regsvr32 MyProjectName.comhost.dll
The command executed successfully. I now tried to import the created .dll file in Delphi, like I did before with the class libraries written in .NET Framework (See timestamp of YouTube tutorial). However, Delphi runs into an error because it can't load the type library.
According to the official documentation...
Unlike in .NET Framework, there is no support in .NET Core or .NET 5+ for generating a COM Type Library (TLB) from a .NET assembly. The guidance is to either manually write an IDL file or a C/C++ header for the native declarations of the COM interfaces. If you decide to write an IDL file, you can compile it with the Visual C++ SDK's MIDL compiler to produce a TLB.
... there is no support in .NET Core for generating a typelib.
However, there is still a way to manually produce a TBL file by using the MIDL compiler. As you can read up in the official documentation, the MIDL compiler processes an IDL file to generate a type library. With that beeing said, I created this IDL file by using this guide.
[
uuid(a93d03e0-9adf-4a2d-93e3-0ccfc2d8e1a6),
lcid(0x0409),
version(1.0),
]
library MyProjectName
{
importlib("stdole.tlb");
[
uuid(16292ce5-ccd1-405d-9a70-ace42152bb15),
oleautomation,
dual
]
interface IServer: IUnknown {
HRESULT getHelloWorld([out, string] IServer** string);
};
};
However, I get an error when I execute the following command to generate the .tlb file.
midl myProjectName.idl /tlb myProjectName.tlb
> midl : command line error MIDL1005 : cannot find C preprocessor cl.exe
Issue: I searched for cl.exe on my Computer but couldn't find anything.
Q.: Does anybody have an idea on how I could solve my problem? I highly appreciate any kind of help, cheers!
If you do not mind switching to a different approach, you can compile a native library from .Net using NativeAOT. You can find an example here
It seems to be planned to be available in .Net 7 but you can already start using it with .Net 6.
Wouldn't it be easier to create an API using MVC and call that from the Delphi appication. That way you can avoid all the problems with DLL's.
Maybe this tool will help you:
https://github.com/dspace-group/dscom
C:\> dotnet tool install dscom -g
C:\> dscom tlbexport myassembly.dll