Adapt MFC dll for using in a C++/CLI wrapper - dll

I have found out that it is essential to derive my base MFC class from CWinApp and use AFX_MANAGE_STATE(AfxGetStaticModuleState()) for every exported method! (if MFC is dyn. linked)
I would like also using an pointer to external native C++ object in MFC dll constr (I should use extension dll - but how work this with CLI???)
Have someone a good example for doing this kind of wrapping ?!
Thanks and greets,
leon22

I'm not sure what your question or your problem is. You don't always need to use the AFX_MANAGE_STATE macro, it depends on the circumstances. What's a 'MFC dll constr' ? What does 'I should use extension dll' mean? (I know what an extension dll is, but what do you mean by 'should' in this context?) What does 'this kind of wrapping' mean?

Related

Get library interface from dll

i have a compiled dll library but i have no documentation about it. There is a way to get the public interface of a dll (at least function names, params numbers and type).
Thanks
You would have to decompile it and analyze each function, its calling convention, parametrs count, parameters meaning (unless it comes with some PDB, but I doubt it), I've done something like this before, it's complicated work, but it can be done.
In order to retrieve the public symbols (functions and variables) exported by a Dynamic-Link Library, one can use the well-known dependency walker. Parameters and Types are only available when the associated PDB file is available (which does not seems to be your case).
You could use the OLEViewer that comes with Visual Studio to view the TypeLib of the DLL if it is a COM library. This would give you the information you need.

c++/cli wrapper question

Is there a recommended way to wrap a native c++ library by c++ cli?
Not sure if one size fits all, but yeah, it is largely a mechanical process. Your ref class wrapper should declare a private member that's a pointer to your native C++ class. Create the instance in the constructor. You'll need a destructor and a finalizer to delete that instance again.
Then for each function in the native C++ class you write a managed version of it. That's almost always a one-to-one call, you simply call the corresponding native method and let C++ Interop convert the arguments. Sometimes you have to write a bit of glue code to convert a managed argument to the native version of it, particularly if your native method uses 8-bit char* or structure arguments.
You'll find that standard pattern in code in my answer here. I also should mention SWIG, a tool that can automate it. Not sure how good it is, never used it myself.

Is it OK to use boost::shared ptr in DLL interface?

Is it valid to develop a DLL in C++ that returns boost shared pointers and uses them as parameters?
So, is it ok to export functions like this?
1.) boost::shared_ptr<Connection> startConnection();
2.) void sendToConnection(boost::shared_ptr<Connection> conn, byte* data, int len);
In special: Does the reference count work across DLL boundaries or would the requirement be that exe and dll use the same runtime?
The intention is to overcome the problems with object ownership. So the object gets deleted when both dll and exe don't reference it any more.
According to Scott Meyers in Effective C++ (3rd Edition), shared_ptrs are safe across dll boundaries. The shared_ptr object keeps a pointer to the destructor from the dll that created it.
In his book in Item 18 he states, "An especially nice feature of
tr1::shared_ptr is that it automatically uses its per-pointer deleter
to eliminate another potential client error, the "cross-DLL problem."
This problem crops up when an object is created using new in one
dynamically linked library (DLL) but is deleted in a different DLL. On
many platforms, such cross-DLL new/delete pairs lead to runtime
errors. tr1::shared_ptr avoid the problem, because its default deleter
uses delete from the same DLL where the tr1::shared_ptr is created."
Tim Lesher has an interesting gotcha to watch for, though, that he mentions here. You need to make sure that the DLL that created the shared_ptr isn't unloaded before the shared_ptr finally goes out of scope. I would say that in most cases this isn't something you have to watch for, but if you're creating dlls that will be loosely coupled then I would recommend against using a shared_ptr.
Another potential downside is making sure both sides are created with compatible versions of the boost library. Boost's shared_ptr has been stable for a long while. At least since 1.34 it's been tr1 compatible.
In my opinion, if it's not in the standard and it's not an object/mechanism provided by your library, then it shouldn't be part of the interface to the library. You can create your own object to do the reference counting, and perhaps use boost underneath, but it shouldn't be explicitly exposed in the interface.
DLLs do not normally own resources - the resources are owned by the processes that use the DLL. You are probably better off returning a plain pointer, which you then store in a shared pointer on the calling side. But without more info it's hard to be 100% certain about this.
Something to lookout for if you expose raw pointers from a dll interface. It forces you to use the shared dll CRT, memory allocated in one CRT cannot be deallocated in a different CRT. If you use the shared dll CRT in all your modules ( dll's & exe's ) then you are fine, they all share the same heap, if you dont you will be crossing CRT's and the world will meltdown.
Aside from that issue, I agree with the accepted answer. The creation factory probably shouldn't define ownership & lifecycle management for the client code.
No it is not.
The layout of boost::shared_ptr<T> might not be the same on both sides of the DLL boundary. (Layout is influenced by compiler version, packing pragmas, and other compiler options, as well as the actual version of the Boost source code.)
Only "standard layout" (a new concept in C++11, related to the old "POD = plain old data" concept) types can safely be passed between separately-built modules.

Use a .net assembly from a totally unmanaged C++ application?

Is there any way I can reference and use classes and methods from a managed .net assembly from within a totally unmanaged C++ application? (no /clr)
Absolutely, and this gem from CodeProject should prove helpful
You need a CCW (COM callable wrapper).
You can - by hosting the CLR. I found one set of example code here . I have no way of knowing how good the advice there is though, as I've never done it.
You can expose the .NET class thru COM and consume the classes thru COM.

How to get the executable path from a Managed DLL

I have a managed DLL (written in C++/CLI) that contains a class used by a C# executable. In the constructor of the class, I need to get access to the full path of the executable referencing the DLL. In the actual app I know I can use the Application object to do this, but how can I do it from a managed DLL?
Assembly.GetCallingAssembly()
or
Assembly.GetExecutingAssembly()
or
Assembly.GetEntryAssembly()
Depending on your need.
Then use Location or CodeBase property (I never remember which one).
#leppie: Thanks - that was the pointer I needed.
For future reference, in C++/CLI this is the actual syntax that works:
String^ appPathString = Assembly::GetEntryAssembly()->Location;
GetExecutingAssembly() provided the name of the DLL
GetCallingAssembly() returned something like System.Windows.Forms
GetEntryAssembly returned the full path, similar to GetModulePath() under Win32.