I have an application that's suppose to be realized in plugin pattern.
Plugins are located in dll files and I'm loading them on the fly, depending on the parameter given from a user via command line. That is, if user wants to use plugin1 he types that name as a parameter in command line when running the app and I am supposed to load it on the fly.
Since I'm using plugin pattern I have an interface (since working in c++ it's an abstract class), that all of the plugins classes implement.
My dilemma is where to put the interface class? In order to have dlls built I will have to have a declaration of interface in every dll.
I want to avoid the need for changing the interface in all of dlls when there is a need for change in interface.
On the other hand if I declare interface class in main app my dlls wont be compiled and built?
Do you have a suggestion on how to extract the interface class from dlls and put it in the main app, so when I want to change it's code, wouldn't need to change it in a dozen of places (that is, in every dll).
Thanks in advance,
Cheers
You will have to store the interface definition in a common location (separate .h file in say \inc subdirectory) and you will have to recompile all the libraries once you change the interface. There's no way around that in C++. If you need the ability to uniquely indentify interfaces you can use something like COM and change interface id each time you break the interface (again you will have to recompile the implementations, but with COM the client will not run into undefined behavior because of DLL hell).
If by "interface" you are talking about the header file that describes your base-abstract class, I see no real issue.
You can share and use a file (here, a "header file") among several projects (a "project" is either your main application or one of your plugins). In your case, it actually makes perfect sense.
Every DLL needs to have the same exported function that returns a pointer to your interface. Each DLL should be responsible for instantiating the 'interface' (Really subclass actually).
So the main app will come along, call LoadLibrary on the DLL, and then using GetProcAddress, will call the exported function on the DLL. The exported function should then instantiate the concrete interface and return a pointer to it.
Question:
"Where to put the interface"
Answer:
In your 'public' API folder.
I once did this in C#, but maybe it can help you. I created an interface and abstract class in a separate project, which the main app and the plugins reference to. That way there is only one place for edits if necessary.
Main App.exe <-> PluginInterface.dll <-> APlugin.dll
Not sure how you would accomplish this in C++, I guess you could create a separate dll for the plugin interface and load it from your exe and your plugin dll's.
Hope that helps.
Related
See the image below. The plugins implement an interace from the core library. (QtPlugin) The concrete plugin class is exported. The plugins should be able to retrieve the concrete plugin class instance from the core and call its methods. If I want to implement this kind of interacting plugins, do I have to link the plugins against each other?
I dont know what happens exactly when symbols get resolved. As far as I can imagine the process stores the resolved symbols. So as soon as the core library resolved the symbols the plugins can receive objects of other plugin classes and call methods on it, if they have the headers. Is this true (for all platforms)?
Some generic information on where symbols get stored and who can access it would be nice too.
generally you link against something, so plugin A links against Core library since it needs to know about the core implementation to function, the implicit link does not exist, there is not knowledge of plugin A inside Core (and there shouldnt be) so therefore core does not know about plugin A or B, and that means plugin B and A wont know about each other either without linking against each other.
in this kind of model you want to keep it agnostic between the plugins and use interfaces or abstract classes to communicate. (for example if a plugin inherits from Core with some pure virtual functions, another plugin can hold a pointer to it, and call functions on it without knowing the full implementation)
generally you link against something, so plugin A links against Core library since it needs to know about the core implementation to function, the implicit link does not exist, there is not knowledge of plugin A inside Core (and there shouldnt be) so therefore core does not know about plugin A or B, and that means plugin B and A wont know about each other either without linking against each other.
Edit for comment:
In that case you could use interfaces, which plugins inherit from. so in the core library you make a class that is called ITerminal, which has a set of virtual functions (Update, Init, Connect, Open, whatever you need) without an implementation, and then pluginA can inherit from it and give the functions implementations. that way other plugins can hold a handle to ITerminal and call functions on it without knowing about the details of pluginA. to create it you need a factory for example Core::CreateTerminal, which will return an ITerminal (ITerminal* object = new PluginA();) now pluginB can call Core::CreateTerminal, which gives them a handle to ITerminal which has an implementation that Core chose in this case. to expand on it you can have plugins register themselves to core so core just calls a create function in the plugin, for example pluginA could register itself as a ITerminal class to core, then when CreateTerminal is called it will call the plugin to create a specific object. that way you can swap plugins in and out (have different terminals without changing Core or other plugins)
I'm updating a DLL for a customer and, due to corporate politics - among other things - my company has decided to no longer share source code with the customer.
Previously. I assume they had all the source and imported it as a VC++6 project. Now they will have to link to the pre-compiled DLL. I would imagine, at minimum, that I'll need to distribute the *.lib file with the DLL so that DLL entry-points can be defined. However, do I also need to distribute the header file?
If I can get away with not distributing it, how would the customer go about importing the DLL into their code?
Yes, you will need to distribute the header along with your .lib and .dll
Why ?
At least two reasons:
because C++ needs to know the return type and arguments of the functions in the library (roughly said, most compilers use name mangling, to map the C++ function signature to the library entry point).
because if your library uses classes, the C++ compiler needs to know their layout to generate code in you the library client (e.g. how many bytes to put on the stack for parameter passing).
Additional note: If you're asking this question because you want to hide implementation details from the headers, you could consider the pimpl idiom. But this would require some refactoring of your code and could also have some consequences in terms of performance, so consider it carefully
However, do I also need to distribute the header file?
Yes. Otherwise, your customers will have to manually declare the functions themselves before they can use it. As you can imagine, that will be very error prone and a debugging nightmare.
In addition to what others explained about header/LIB file, here is different perspective.
The customer will anyway be able to reverse-engineer the DLL, with basic tools such as Dependency Walker to find out what system DLLs your DLL is using, what functions being used by your DLL (for example some function from AdvApi32.DLL).
If you want your DLL to be obscured, your DLL must:
Load all custom DLLs dynamically (and if not possible, do the next thing anyhow)
Call GetProcAddress on all functions you want to call (GetProcessToken from ADVAPI32.DLL for example
This way, at least dependency walker (without tracing) won't be able to find what functions (or DLLs) are being used. You can load the functions of system DLL by ordinal, and not by name so it becomes more difficult to reverse-engineer by text search in DLL.
Debuggers will still be able to debug your DLL (among other tools) and reverse engineer it. You need to find techniques to prevent debugging the DLL. For example, the very basic API is IsDebuggerPresent. Other advanced approaches are available.
Why did I say all this? Well, if you intend to not to deliver header/DLL, the customer will still be able to find exported functions and would use it. You, as a DLL provider, must also provide programming elements with it. If you must hide, then hide it totally.
One alternative you could use is to pass only the DLL and make the customer to load it dynamically using LoadLibrary() + GetProcAddress(). Although you still need to let your customer know the signature of the functions in the DLL.
More detailed sample here:
Dynamically load a function from a DLL
I have a C++ DLL which was written in 1998, and I want to view the members (properties, fields, methods, constructors etc). I am of the understanding that the company who wrote the DLL is no longer about, but it is still used.
If I have only the DLL, is this possible? Or do you have to just know what is inside the DLL to work with it. If it is possible how would I go about this?
I am looking to work with the DLL from .Net via P/Invoke.
Get this: http://www.dependencywalker.com/ , use depends.exe to open the DLL, then activate "Undecorate C++ Functions" in the "View" menu. I mainly use it to find dependencies, but it also exposes entry points of DLLs.
This is not fool proof, because a DLL that exposes a class doesn't have to export its methods. For example, pure virtual method layout is sufficiently uniform that you can expose your instances as interface pointers with maybe a factory function. But it might solve your problem.
And regardless, you need a copy of dependency walker. :)
You can use a tool like IDA to dissasemble the binary and try to make out function names, but this can be hard. Why do you only have the DLL? It would be much easier to get the info from the export table of the associated lib or, even better, header files.
you can use VS Command prompt
a simple command is:
dumpbin /exports <nameofdll>
NirSoft offers 'DLL Export Viewer'
https://www.nirsoft.net/utils/dllexp.zip
Convinient UI application which can display dll members.
I have a application and two Dlls. Both libraries are loaded by the application. I don't have the source of the application, but the source of the libs. I want to instantiate a class in lib A and want to use this instance also in lib B.
How do I do this? I'm not sure, but I think that both libs are used in different threads of the application.
I have no idea where I have to search for a solution.
No. Think about DLL as just normal library. Both can be used in a single thread.
If you want to use a class A in library X, you must pass a pointer/reference to it. The same applies to library Y. This way both libraries can work with same class/data.
Two dll's loaded into the same process is a fairly simple setup.
You just need to be careful with module scope, which will be the same as dll scope.
e.g. each dll will have its own set of static instances for any static objects.
Next you need to understand how to reference functions/classes across the boundary and what sort of types are safe to use as arguments.
Have a look on any documentation for dllexport and dllimport - there are several useful questions on this site if you search with those terms.
You have to realize that even though your DLLs are used by the host application nothing prevents you (that is your DLLs) from using your DLLs as well. So in your DLL A you could load and use your DLL B and call functions and stuff. When DLL A is unloaded, free DLL B as well. DLLs are reference counted, so your DLL A will have a reference of 1 (the host application) and your DLL B 2 (the host application and DLL A). You will not have two instances of DLL B loaded in the same process.
Named pipes might be the solution to your problems.
If you're targetting windows, you can check this reference
[EDIT] Didnt see you wanted to work on the same instance. In that case you need shared memory spaces, however, you really have to know what you're doing as it's quite dangerous :)
A better solution could be to apply OO Networking principles to your libs and communicate with, say CORBA, using interprocess middleware or the 127.0.0.1 loopback interface (firewalls will need to allow this).
Seems the simple solution would be to include in some initialization function of library A (or in DllMain if needed) a simple call to a function in library B passing a pointer to the common object. The only caveat is that you must ensure the object is deleted by the same DLL that newed it to avoid problems with the heap manager.
If these DLL's are in fact used in different threads you may have to protect access to said data structure using some kind of mutex.
Consider me a novice to windows environment and COM programming.
I have to automate an application (CANoe) access. CANoe exposes itself as a COM server and provides CANoe.h , CANoe_i.c and CANoe.tlb files.
Can anyone specify how to write a C++ client, for accessing the object, functions of the application.
Also, please specify how to access the code present in tlb file from C++.
Visual studio has a lot of built in support for importing type libraries into your C++ project and using the objects thus defined. For example, you can use the #import directive:
#import "CANoe.tlb"
This will import the type library, and convert it to header files and implementation files - also it will cause the implementation files to be built with your project and the header files to be included, so this is lots of magic stuff right there.
Then, you get a whole lot of typedefs for smart pointer wrappers for the types and objects defined in the type library. For example, if there was a CoClass called Application which implemented the interface IApplication, you could do this:
ApplicationPtr app(__uuidof(Application));
This would cause at run time, the coclass application to be created and bound to the variable app, and you can call on it like so:
app->DoSomeCoolStuff();
Error handling is done by checking the result of COM calls, and throwing the appropriate _com_error exception as necessary so this implies you need to write exception safely.
Use import directive to import the .tlb file - this will give you a C++ equivalent of the interfaces exposed by the COM component.
You will also need to register the COM component to the registry (run regsvr32 on the .dll file of the component). After that you can call CoCreateInstance() (or _com_ptr_t::CreateInstance() as it is usually more convenient) to create an instance of the class that implements the interface. You can then call methods of the interface - it will work almost the same way as if it was a plain C++ interface and class.
The easier way is to include both .h and _i.c project in your .cpp file using #include statements.
Since you haven't been given the dll and only tlb is provided, you can register the tlb using regtlibv12.exe which is a part of visual studio (this is the VS2005 version). By registering tlb, appropriate entries will be made in the registry and then you can use the COM library functionality as you need.
EDIT: BTW, you need DLL anyway to instantiate the COM Component successfully.
To create an interface pointer, one of the safer ways is to use CComPTR like:
CComPtr myPtr;
myPtr.CoCreateInstance(__uuidof("ClassNamehere"));
myPtr->Method(....);