C # / C ++ pInvoke Tips

What is the best way to change a C ++ program to be used with pInvoke from C # .NET CF?

I have a large C ++ code base that makes extensive use of STL. Namely, iterators, container classes, and standard strings.

In addition to this, many light classes are passed by value.

I want to build C # gui ontop of this codebase for mobile devices for Windows mobile devices.

Is it worth it?

I managed to get some examples working using pInvoke to call C ++ code from C # .NET, but writing wrappers for each access point and for all return types of STL seems very complicated and ugly. Is there any other way, or am I a bit full?

BTW. Managed C ++ is not an option because it is not supported in any form of .NET CF.

- edit: I have one specific question regarding pinvoke.

Suppose you had a function returning a C ++ string by value

std::string foo () { return std::string ("Hi"); } 

I understand that it cannot be called from C # using pinvoke, because there is no way to output the STL string, but my problem is that I can’t even write a shell without allocating a new array, because std :: string is not returned in heap.

 char* foo2 () { return foo().c_str(); //Very bad //the returned pointer is released when the std::string falls out of scope. //and will be invalid before the caller is able to do anything with it. } 

So my problem is how to wrap foo in a suitable pInvoke format without having to redistribute the whole line.

 char* foo2 () { std::string f = foo(); char* waste = new char[f.length()+1]; strcpy (waste, f.c_str()); return f; } 

The thought of doing above for each point at which I need to return std :: string is enough to make me give up trying to use C #.

+3
c ++ c # windows-mobile
source share
4 answers

I would say that it is worth it, but I agree with another message that this is not easy.

Possible approaches could be:

  • C in C ++ and appears as a DLL.
  • COM objects (altho WM does not support COM servers, so you are forced to use in-process servers, mainly an implementation of COM DLLs). This will give you more OO interface.
  • Background process displaying some kind of API. You can go modulo "CE Services" or come up with your own API.

Everything is possible, and there are pros and cons. No matter what you do, you cannot use STL types in an interface. You came down to simple basic types that are easy to marshal between processes. Since you're talking about C #, then COM can go, as you can open the OO interface.

I would recommend trying the simplest possible interface between them.

+3
source share

What you want to do is not easy. If you really wanted to do this, it’s best to create some clean C interfaces that wrap all C ++ and STL elements and pass structures that can easily go from .net to C. Depending on how big your code base is, this can be very challenging.

Unfortunately.

+1
source share

maybe you should write a lumpy shell and then use the .net tool that will automatically create a C # assembly for you?

0
source share

Doesn't SWIG create a C-style wrapper for C ++? How to convey all the non-basics of complex C ++? Correct me if I am wrong, because I'm in a similar situation, I want to wrap a very large and complex C ++ api open in dll. I need to avoid manipulation and non-basic data types by writing a C-style wrapper to expose all the data before outputting it, and this is impossible without automatic tools, given the size of the api and the complexity of types and prototypes.

0
source share

All Articles