Commit a0868529 authored by Dennis Nienhüser's avatar Dennis Nienhüser
Browse files

Stricter plugin load checks: Refuse to load plugins with older interface...

Stricter plugin load checks: Refuse to load plugins with older interface versions. Fixes incompatible/old plugins crashing Marble.
CCBUG: 239831
RB: 5149

svn path=/trunk/KDE/kdeedu/marble/; revision=1168304
parent 06e6d43c
......@@ -40,7 +40,6 @@ class PluginManager;
class MARBLE_EXPORT AbstractDataPlugin : public RenderPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RenderPluginInterface )
public:
AbstractDataPlugin();
......
......@@ -133,6 +133,23 @@ QList<RunnerPlugin *> PluginManager::runnerPlugins() const
return d->m_runnerPlugins;
}
/** Append obj to the given plugins list if it inherits both T and U */
template<class T, class U>
bool appendPlugin( QObject * obj, const QString &fileName, QList<T*> &plugins )
{
if ( qobject_cast<T*>( obj ) && qobject_cast<U*>( obj ) ) {
Q_ASSERT( obj->metaObject()->superClass() ); // all our plugins have a super class
mDebug() << obj->metaObject()->superClass()->className()
<< "plugin loaded from" << MarbleDirs::pluginPath( fileName );
T* plugin = qobject_cast<T*>( obj );
Q_ASSERT( plugin ); // checked above
plugins.append( plugin );
return true;
}
return false;
}
void PluginManagerPrivate::loadPlugins()
{
if (m_pluginsLoaded)
......@@ -165,38 +182,22 @@ void PluginManagerPrivate::loadPlugins()
QObject * obj = loader.instance();
RenderPlugin * renderPlugin = 0;
NetworkPlugin * networkPlugin = 0;
PositionProviderPlugin * positionProviderPlugin = 0;
RunnerPlugin * runnerPlugin = 0;
if ( obj ) {
if ( obj->inherits( "Marble::RenderPlugin" ) ) {
mDebug() << "render plugin found" << MarbleDirs::pluginPath( fileName );
renderPlugin = qobject_cast<RenderPlugin *>( obj );
m_renderPluginTemplates.append( renderPlugin );
bool isPlugin = appendPlugin<RenderPlugin, RenderPluginInterface>
( obj, fileName, m_renderPluginTemplates );
isPlugin = isPlugin || appendPlugin<NetworkPlugin, NetworkPluginInterface>
( obj, fileName, m_networkPluginTemplates );
isPlugin = isPlugin || appendPlugin<PositionProviderPlugin, PositionProviderPluginInterface>
( obj, fileName, m_positionProviderPluginTemplates );
isPlugin = isPlugin || appendPlugin<RunnerPlugin, RunnerPlugin>
( obj, fileName, m_runnerPlugins ); // intentionally T==U
if ( !isPlugin ) {
mDebug() << "Plugin failure:" << fileName << "is a plugin, but it does not implement the "
<< "right interfaces or it was compiled against an old version of Marble. Ignoring it.";
}
else if ( obj->inherits( "Marble::NetworkPlugin" ) ) {
mDebug() << "network plugin found" << MarbleDirs::pluginPath( fileName );
networkPlugin = qobject_cast<NetworkPlugin *>( obj );
m_networkPluginTemplates.append( networkPlugin );
}
else if ( obj->inherits( "Marble::PositionProviderPlugin" ) ) {
mDebug() << "position provider plugin found" << MarbleDirs::pluginPath( fileName );
positionProviderPlugin = qobject_cast<PositionProviderPlugin *>( obj );
m_positionProviderPluginTemplates.append( positionProviderPlugin );
} else if ( obj->inherits( "Marble::RunnerPlugin" ) ) {
mDebug() << "runner plugin found" << MarbleDirs::pluginPath( fileName );
runnerPlugin = qobject_cast<RunnerPlugin *>( obj );
Q_ASSERT( runnerPlugin && "Unexpected cast failure when loading RunnerPlugin" );
m_runnerPlugins.append( runnerPlugin );
} else {
mDebug() << "Unknown file or plugin type in plugin directoy: " << fileName;
}
}
if( !renderPlugin && !networkPlugin && !positionProviderPlugin && !runnerPlugin ) {
mDebug() << "Plugin Failure: " << fileName << " is not a valid Marble Plugin:";
mDebug() << loader.errorString();
} else {
mDebug() << "Plugin failure:" << fileName << "is not a valid Marble Plugin:"
<< loader.errorString();
}
}
......
......@@ -39,7 +39,6 @@ class MarbleDataFacade;
class MARBLE_EXPORT RenderPlugin : public QObject, public RenderPluginInterface
{
Q_OBJECT
Q_INTERFACES( Marble::RenderPluginInterface )
public:
/**
......
......@@ -26,8 +26,6 @@ class MARBLE_EXPORT RunnerPlugin : public QObject, public PluginInterface
{
Q_OBJECT
Q_INTERFACES( Marble::PluginInterface )
public:
enum Capability {
None = 0x0, // The plugin is useless
......@@ -104,4 +102,6 @@ private:
Q_DECLARE_OPERATORS_FOR_FLAGS(Marble::RunnerPlugin::Capabilities)
Q_DECLARE_INTERFACE( Marble::RunnerPlugin, "org.kde.Marble.RunnerPlugin/1.00" )
#endif // MARBLE_RUNNERPLUGIN_H
......@@ -20,6 +20,7 @@ namespace Marble
class QNamNetworkPlugin: public NetworkPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::NetworkPluginInterface )
public:
QNamNetworkPlugin();
......
......@@ -29,6 +29,7 @@ namespace Marble
class GeoCluePositionProviderPlugin: public PositionProviderPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::PositionProviderPluginInterface )
public:
GeoCluePositionProviderPlugin();
......
......@@ -25,6 +25,7 @@ class GpsdThread;
class GpsdPositionProviderPlugin: public PositionProviderPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::PositionProviderPluginInterface )
public:
GpsdPositionProviderPlugin();
......
......@@ -21,6 +21,7 @@ class MaemoPositionProviderPluginPrivate;
class MaemoPositionProviderPlugin: public PositionProviderPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::PositionProviderPluginInterface )
public:
MaemoPositionProviderPlugin();
......
......@@ -31,6 +31,7 @@ class MarbleWidget;
class FileViewFloatItem: public AbstractFloatItem
{
Q_OBJECT
Q_INTERFACES( Marble::RenderPluginInterface )
MARBLE_PLUGIN(FileViewFloatItem)
public:
......
......@@ -35,8 +35,9 @@ class WidgetGraphicsItem;
*/
class NavigationFloatItem: public AbstractFloatItem
{
Q_OBJECT
//Q_INTERFACES( MarbleLayerInterface )
Q_OBJECT
Q_INTERFACES( Marble::RenderPluginInterface )
MARBLE_PLUGIN( NavigationFloatItem )
public:
explicit NavigationFloatItem( const QPointF &point = QPointF( -10, -10 ) );
......
......@@ -20,6 +20,8 @@ namespace Marble
class GosmorePlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit GosmorePlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,7 @@ namespace Marble
class HostipPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit HostipPlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class LatLonPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit LatLonPlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class LocalDatabasePlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit LocalDatabasePlugin(QObject *parent = 0);
......
......@@ -20,6 +20,7 @@ namespace Marble
class NameFinderPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit NameFinderPlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class NominatimPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit NominatimPlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class OpenRouteServicePlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit OpenRouteServicePlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class RoutinoPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit RoutinoPlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class TravelingSalesmanPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit TravelingSalesmanPlugin( QObject *parent = 0 );
......
......@@ -20,6 +20,8 @@ namespace Marble
class YoursPlugin : public RunnerPlugin
{
Q_OBJECT
Q_INTERFACES( Marble::RunnerPlugin )
public:
explicit YoursPlugin( QObject *parent = 0 );
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment