Managed C++ class cannot be referenced from C# - c#

The problem I am currently encountering is really weird. I try to use a Managed C++ class from a C# project but the compiler cannot find the type.
Take a look at this screenshot:
The Managed C++ project (NGervill.Gervill.Native) is referenced and according to the Object Browser it contains all required namespaces and types. In my source code I've added the using and used the class but still I get a compile error.
Now the strangest part: The other types within the Managed C++ project can be referenced. In another C# class I access the methods of the PortMixerProviderNative class. That means target platform and .net framework version are correct (.net 4.5 - x86 build).
Is Visual Studio somehow caching an old version of the Managed C++ DLL or what else can cause such a problem?

PortMixerNative is a native C++ class, not a managed class. Native classes can be exposed in the assembly metadata in some cases, usually because they are the type of a private field in a managed class wrapper, but they are not usable in any way from a C# program. Only public ref class declarations in the C++/CLI project are usable.
It isn't clear what wrapper class you are supposed to use. Not PortMixerNative. Check the vendor's manual and/or code samples or contact them if you need more help.

I finally found the solution of this problem: For some reason the cpp file implementing the PortMixerNative class was not included in the project. After adding the PortMixerNative.cpp to the project again I finally could see that there were syntax errors in this file. After fixing the errors and recompiling the .Native project I could successfully reference the class.
The strange thing is that the .Native project successfully compiled even with methods without implementations. If anybody encounters this problem too, check if all methods of the class you try to use have an implementation.

Related

App won't run when interface is added to class definition but dll is missing

I'm new to the forum and not a professional programmer, so apologies if I am not using the correct terminology.
I am using a 3rd party DLL in my c# forms application, and it has an interface which (in their example) I specify when creating the class:
public partial class frmMain : Form, PIEHid32Net.PIEDataHandler, PIEHid32Net.PIEErrorHandler
The problem is that the dll, which is added to my project as a reference, may not exist. If it does not exist, the application doesn't start (and in Visual Studio I get a FileNotFoundException as soon as I step into the code, before I could add a try/catch etc.
I can create the DLL from the installer which works fine, but historically I have also added it to the app as an embedded resource and exported it at runtime if it did not exist - which is nice if someone just copies the exe rather than doing a full install. But I've never had a DLL with an "interface" defined in the above way. I guess because the class is referencing it, the app will never run.
So is there a way around this? A way to add the interface reference as being "optional", or adding it at runtime AFTER I have exported the DLL to which they reference?

Conflicting overloads of global delete

I am attempting to write a a CLI interop layer between an existing c++ codebase and a c# wpf app. My c++ libraries already overload global new and delete in order to implement my own memory tracking and other niceties. So the dependencies look something like this:
(Native library compiled to static lib)->(CLI layer)->(C# WPF application)
However, whenever I include my native libraries and try and build my CLI project, I run into a conflicting symbol for global delete which was already defined in msvcrtd:
Error LNK2005 "void __cdecl operator delete(void *)" (??3#YAXPAX#Z) already defined in msvcrtd.lib(delete_scalar.obj)
I'm not sure how to get my build to take my global delete instead of the one in the default library. I have tried making another pure native project that compiles a DLL, and compiling all of my static libs into that, then having the interop layer load that DLL. This works, but I'd rather not have 2 layers of glue instead of the one.
I'm using visual studio 2015.
The native component uses the CRT as DLL? This is requirement if using mixed assemblies. If you statically linked library uses the static CRT you get into troubles.
Check and link with the /VERBOSE flag to see, where this other delete comes from. Eliminate this other library call.

C# Classes from Module could not be loaded

I'm getting an internal compiler error:
System.Reflection.ReflectionTypeLoadException: The classes in the module cannot be loaded.
What would make them not load? The error offers no help and MSDN tell you about the class throwing when they can't be loaded, not why they wouldn't be able to be loaded.
There is literally no information on what would prevent classes from being loaded that I can find, help me out?
Edit: It doesn't actually tell me at which line the exception is thrown. Not all classes are public, some are internal, but the classes that need to be exposed in order for the system to work are public (no classes other than public are used in the calling code). The DLL was compiled in VS13, and the quick console application I made alongside that in VS for testing works fine - it recognises the namespace from the DLL, and makes use of the public classes available. When I bring the DLL out of a release build and into the program I'm using it with, however, that is when I run into this error.
It looks like a simple mistake: the target platform for using the DLL with is constantly updated, and does not specify a .NET version; one normally assumes this means that it uses 'up-to-date'. Oh no, rolling back through build targets for the DLL finally yielded a working DLL. Will post this to the author of the program as a request; it helps if you know what you're working with!
TL;DR:
Wrong target version of .NET, changing to 3.0 allowed the DLL to work, with no complaining.

Using tlbimp without needing a second assembly?

I am trying to implement a COM interface in my C# dll for others to consume. I have defined an interface in foo.idl.
I've run foo.idl through tlbimp to produce foo.dll, a .Net assembly. Now to implement my interface, I can reference foo.dll in my dll to implement the interface.
This works perfectly as it stands with one exception: I now have to distribute two dlls instead of one. This actually goes against the requirements of the project I'm working on: deliver one DLL.
Is there a way to merge the tlbimp dll into mine, or any other way to do this (implement a COM interface in C# without the second dll)?
A good disassembler gets the job done, like Reflector. You can simply disassemble the interop assembly and copy the generated C# interface declarations into your source code. Of course you should only do this if the interface declarations and IIDs are stable.
And definitely consider upgrading to VS2010. Its "embed interop types" feature allows you to ship your assembly without the interop assembly.
You could probably cheat by using a .tlb instead of the 'glue' dll.
I'd suggest you create a mixed-mode assembly using MSVC++/CLR
http://msdn.microsoft.com/en-us/library/k8d11d4s(v=vs.100).aspx
Interop (How Do I in Visual C++)
This might have the drawback that you can't use C# in the same assembly. Should you want to add C# code to the mix, you might be able to squeeze out of your tough situation using
IlMerge
For other, possibly interesting, thoughts see my earlier answer:
Is it possible to compile a console application into a single .dll file?

Can I use DLL written in C++ in my C# project?

The problem is - I want to write a template class in C++, put it in a DLL, and then call it from my C# project. Is it possible? Can you please provide any references or articles on about how to do it?
EDIT
I want DLL to be written in unmanaged C++
Template class could not be exported. It does not exist until someone instantiate it. You should explicitly instantiate it and then export it as usual class.
I think this question may help you out:
Use C++ CLI template class in C#
By using C++/CLI you can expose your C++ classes as .NET classes where they use compatible features. You won't, however, be able to expose your template definition, but may be able to use a concrete class that specializes that template.
When you build a C++/CLI class you can reference it just like any other .NET assembly.
You create it just as with any other DLLs - the main idea behind DLLs is that it can be created in any programming language, and be used with every other. Just remember that C++ is unmanaged, so it has to be treated carefully. Look for instance here (MSDN forum).
One more link.
In general, use DllImport decorator to import functions from DLL file you've created in C++. Example from MSDN:
using System.Runtime.InteropServices; // DllImport
public class Win32 {
[DllImport("User32.Dll")]
public static extern void SetWindowText(int h, String s);
}
As far as I recall there's a bit of a problem.
It is possible to Have C# use a C++ Dll (managed and unmanaged)
It is possible to have unmanaged C++ use a C# Dll (you need to do this via COM and an interface).
I'll see if I can find more detailed information

Categories