Unsolved Are there any special rules with plugins?
-
I thought I had the solution, but unfortunately I was wrong.
I had assumed that the access class for the singleton would be the problem and therefore "retrofitted" copy constructor and assignment operator - unfortunately I found that I can't set the static pointer in the plugin's address space, which still causes crashes.
I would be very happy about some help.
-
Rather than using a singleton, why not have a controller that you pass to your plugin ?
That said, again, plugins using a singleton to modify the internal state of the main application looks a bit off.
-
@SGaist said in Are there any special rules with plugins?:
Any chances that your singleton is a QObject ?
I completely overlooked the question.
You are right, of course - my singleton is a QObject. This is because I use a variety of signals to communicate with another thread.
My application is a bit different from usual GUI applications, because the (foreign) backend controls many functions, including the state of many UI elements.
To minimize the internal dependencies I decided to use the "singleton".
In the context of the plugins, I started another test. I passed the singleton pointer as a parameter to the plugins and put it back in the right place there.
In addition, I output the contents of the pointer from the application area and from the plugin area. Both were identical.
The first time I called a function that was supposed to use the pointer, the pointer was then suddenly null again, which of course led to a crash.From there I would need still some further support. When is the copied address range used and when not?
Apparently there is a difference if the plugin executes functions while it is created by the factory or if the call is made within the QT event cycle.I had the (crazy?) idea to make every page of the application a plugin. The only thing is that each interactive UI element has to communicate with the backend (different thread), which works via the signals from the singleton.
That's why I'm a bit stuck. Is my idea even feasible, or am I completely barking up the wrong tree?
-
Ok, injecting the memory address did the trick.
But stil got lots of crashes.Don't really understand why, but obtaining the real class from plugin interface does not work with
qobject_cast
. Had to replace it byreinterpret_cast
and now it works.Well, 9 out of 13 plugins work. On two I get unresolved externals like this:
Cannot load library .../plugins/libMyPlugin.so: (undefined symbol: _ZN6Kernel16staticMetaObjectE)
What I don't understand: I use an abstract class between Interface and Pluginclass. That abstract class handles initialization and memory injecting/patching. So from this point of view, all plugins should be identical.
Kernel is the name of the patched singleton - as mentioned, a member of that abstract base class and initialized from abstract base class too.what makes the story even stranger is the fact that I have no problems with unresolved externals in the static version. So everything should be in place.
How can I find out the source of evil?
-
Are you building your common library as a static one ?
-
yes of cause. I have 2 static libraries.
My app is a C++ app and shared libs need a C-interface.
I have to confess, I don't know how to combine that. -
@django-Reinhard said in Are there any special rules with plugins?:
yes of cause. I have 2 static libraries.
Si that's one of your issues. Remember the static meta object copy issue I mentioned earlier ?
@django-Reinhard said in Are there any special rules with plugins?:
My app is a C++ app and shared libs need a C-interface
Why ?
-
Hi,
thank you for your attention!
@SGaist said in Are there any special rules with plugins?:
My app is a C++ app and shared libs need a C-interface
Why ?
Your talking shorthands is not always helpful.
Especially in this case.Wherever I read about shared libs, even in Qt documentation, it mentions, that shared libs need to use special c-functions for interaction.
I don't know it - it was my first time to deal with shared libs. When I read Qt docs about plugins, I thought: ok, that's feasible. Qt docs don't mention the problems, that might occure in context with plugins. In my point of view that memory duplication is so important - it should be documented.
The point is, you probably would not design a plugin as I did, as you know how to do things right. I just work based on trial and error.
So if you know some prosa about shared lib usage without c-interface function, I would be happy to learn about it.
-
@django-Reinhard Shared libs do not have to provide C interfaces, they can provide C++ interfaces including classes. You just need to export symbols (functions and classes) from your libs you want to access in your application. You can see here how to do this: https://doc.qt.io/qt-5/sharedlibrary.html
-
Thank you very much for the pointer!
I already read that page before, but I overlooked the object part obviously.
May be I'm too outdated for that - I used lots of libraries with that decl_import/decl_export thingi and most if not all had extern "C" included in that macro. So for me, that decl-stuff was synonym for C-usage.
Luckily that is wrong, so good times will arise ;)I'll gonna rethink my stuff for that new perspective.
Actually I got a bigger problem. But that's worth to start a new thread.