summaryrefslogtreecommitdiff
Unidiff
Diffstat (more/less context) (ignore whitespace changes)
-rw-r--r--libopie2/examples/opiecore/oplugins/oplugins.cpp37
-rw-r--r--libopie2/examples/opiecore/oplugins/oplugins.pro11
-rw-r--r--libopie2/opiecore/opiecore.pro4
-rw-r--r--libopie2/opiecore/opluginloader.cpp272
-rw-r--r--libopie2/opiecore/opluginloader.h22
5 files changed, 268 insertions, 78 deletions
diff --git a/libopie2/examples/opiecore/oplugins/oplugins.cpp b/libopie2/examples/opiecore/oplugins/oplugins.cpp
new file mode 100644
index 0000000..4aa2da5
--- a/dev/null
+++ b/libopie2/examples/opiecore/oplugins/oplugins.cpp
@@ -0,0 +1,37 @@
1/*
2 * You may copy, modify and or distribute without any limitation
3 */
4#include <opie2/odebug.h>
5#include <opie2/opluginloader.h>
6
7#include <opie2/todayplugininterface.h>
8
9using Opie::Core::OPluginItem;
10using Opie::Core::OGenericPluginLoader;
11
12void debugLst( const OPluginItem::List& lst ) {
13 for ( OPluginItem::List::ConstIterator it = lst.begin(); it != lst.end(); ++it )
14 odebug << "Name " << (*it).name() << " " << (*it).path() << " " << (*it).position() << oendl;
15}
16
17
18int main( void ) {
19 OGenericPluginLoader loader( "today", true );
20 loader.setAutoDelete( true );
21
22 odebug << "IS in Safe Mode" << loader.isInSafeMode() << oendl;
23
24 OPluginItem::List lst = loader.allAvailable( true );
25 debugLst( lst );
26
27 lst = loader.filtered( true );
28 debugLst( lst );
29
30 for ( OPluginItem::List::Iterator it = lst.begin(); it != lst.end(); ++it ) {
31 QUnknownInterface* iface = loader.load( *it, IID_TodayPluginInterface );
32 }
33
34 /*
35 * now it's autodelete so cleaned up for us
36 */
37}
diff --git a/libopie2/examples/opiecore/oplugins/oplugins.pro b/libopie2/examples/opiecore/oplugins/oplugins.pro
new file mode 100644
index 0000000..7286de9
--- a/dev/null
+++ b/libopie2/examples/opiecore/oplugins/oplugins.pro
@@ -0,0 +1,11 @@
1TEMPLATE = app
2CONFIG += qt warn_on
3
4SOURCES = oplugins.cpp
5
6INCLUDEPATH += $(OPIEDIR)/include
7DEPENDSPATH += $(OPIEDIR)/include
8
9LIBS += -lopiecore2
10
11include ( $(OPIEDIR)/include.pro )
diff --git a/libopie2/opiecore/opiecore.pro b/libopie2/opiecore/opiecore.pro
index a9562b5..5056d48 100644
--- a/libopie2/opiecore/opiecore.pro
+++ b/libopie2/opiecore/opiecore.pro
@@ -1,55 +1,57 @@
1TEMPLATE = lib 1TEMPLATE = lib
2CONFIG += qt warn_on 2CONFIG += qt warn_on
3DESTDIR = $(OPIEDIR)/lib 3DESTDIR = $(OPIEDIR)/lib
4HEADERS = oapplication.h \ 4HEADERS = oapplication.h \
5 oconfig.h \ 5 oconfig.h \
6 odebug.h \ 6 odebug.h \
7 oglobal.h \ 7 oglobal.h \
8 oglobalsettings.h \ 8 oglobalsettings.h \
9 okeyconfigmanager.h \ 9 okeyconfigmanager.h \
10 opluginloader.h \
10 oprocess.h \ 11 oprocess.h \
11 oprocctrl.h \ 12 oprocctrl.h \
12 osmartpointer.h \ 13 osmartpointer.h \
13 ostorageinfo.h \ 14 ostorageinfo.h \
14 xmltree.h 15 xmltree.h
15 16
16SOURCES = oapplication.cpp \ 17SOURCES = oapplication.cpp \
17 oconfig.cpp \ 18 oconfig.cpp \
18 odebug.cpp \ 19 odebug.cpp \
19 oglobal.cpp \ 20 oglobal.cpp \
20 oglobalsettings.cpp \ 21 oglobalsettings.cpp \
21 okeyconfigmanager.cpp \ 22 okeyconfigmanager.cpp \
23 opluginloader.cpp \
22 oprocess.cpp \ 24 oprocess.cpp \
23 oprocctrl.cpp \ 25 oprocctrl.cpp \
24 ostorageinfo.cpp \ 26 ostorageinfo.cpp \
25 xmltree.cpp 27 xmltree.cpp
26 28
27 29
28# The following files are currently not compileable on mac ! 30# The following files are currently not compileable on mac !
29# Therfore I removed them from the build .. (eilers) 31# Therfore I removed them from the build .. (eilers)
30 32
31CONFTEST = $$system( echo $CONFIG_TARGET_MACOSX ) 33CONFTEST = $$system( echo $CONFIG_TARGET_MACOSX )
32!contains( CONFTEST, y ) { 34!contains( CONFTEST, y ) {
33HEADERS += ofilenotify.h 35HEADERS += ofilenotify.h
34SOURCES += ofilenotify.cpp 36SOURCES += ofilenotify.cpp
35} else { 37} else {
36 message( "ofilenotify is not available in a mac build !" ) 38 message( "ofilenotify is not available in a mac build !" )
37} 39}
38 40
39include ( device/device.pro ) 41include ( device/device.pro )
40 42
41INTERFACES = 43INTERFACES =
42TARGET = opiecore2 44TARGET = opiecore2
43VERSION = 1.9.1 45VERSION = 1.9.1
44INCLUDEPATH += $(OPIEDIR)/include 46INCLUDEPATH += $(OPIEDIR)/include
45DEPENDPATH += $(OPIEDIR)/include 47DEPENDPATH += $(OPIEDIR)/include
46 48
47!contains( platform, x11 ) { 49!contains( platform, x11 ) {
48 LIBS = -lqpe 50 LIBS = -lqpe
49 include ( $(OPIEDIR)/include.pro ) 51 include ( $(OPIEDIR)/include.pro )
50} 52}
51 53
52contains( platform, x11 ) { 54contains( platform, x11 ) {
53 LIBS = -L$(OPIEDIR)/lib -Wl,-rpath,$(OPIEDIR)/lib 55 LIBS = -L$(OPIEDIR)/lib -Wl,-rpath,$(OPIEDIR)/lib
54} 56}
55 57
diff --git a/libopie2/opiecore/opluginloader.cpp b/libopie2/opiecore/opluginloader.cpp
index e5a0903..b473cd7 100644
--- a/libopie2/opiecore/opluginloader.cpp
+++ b/libopie2/opiecore/opluginloader.cpp
@@ -1,397 +1,541 @@
1/* 1/*
2 * LGPLv2 or later 2 * LGPLv2 or later
3 * zecke@handhelds.org 3 * zecke@handhelds.org
4 */ 4 */
5 5
6#include "opluginloader.h" 6#include "opluginloader.h"
7#include "oconfig.h"
8
9#include <qpe/qpeapplication.h>
10
11#include <qdir.h>
12#include <qdict.h>
13#include <qtl.h>
7 14
8#include <stdlib.h> 15#include <stdlib.h>
9 16
10 17
11 18
12namespace Opie { 19namespace Opie {
13namespace Core { 20namespace Core {
14namespace Internal { 21namespace Internal {
15struct OPluginLibraryHolder { 22struct OPluginLibraryHolder {
16 static OPluginLibraryHolder *self(); 23 static OPluginLibraryHolder *self();
17 QLibrary *getLibrary( const QString& ); 24 QLibrary *ref( const QString& );
18 void putLibrary( QLibrary* ); 25 void deref( QLibrary* );
19private: 26private:
27
20 OPluginLibraryHolder(); 28 OPluginLibraryHolder();
21 ~OPluginLibraryHolder(); 29 ~OPluginLibraryHolder();
22 OPluginLibraryHolder* m_self; 30 QDict<QLibrary> m_libs;
23 31 static OPluginLibraryHolder* m_self;
24}; 32};
33
34 OPluginLibraryHolder* OPluginLibraryHolder::m_self = 0;
35 OPluginLibraryHolder* OPluginLibraryHolder::self() {
36 if ( !m_self )
37 m_self = new OPluginLibraryHolder;
38
39 return m_self;
40 }
41
42 OPluginLibraryHolder::OPluginLibraryHolder() {}
43 OPluginLibraryHolder::~OPluginLibraryHolder() {}
44
45 /*
46 * We do simple ref counting... We will add the QLibrary again
47 * and again to the dictionary and on deref we will pop and pop it
48 * until there are no more library and we will unload and delete the library
49 * luckily dlopen does some ref counting as well so we don't need
50 * to hack QPEApplication
51 */
52 QLibrary* OPluginLibraryHolder::ref(const QString& str) {
53 QLibrary *lib = m_libs[str];
54
55 /* if not in the dict try to load it */
56 if ( !lib ) {
57 lib = new QLibrary( str, QLibrary::Immediately );
58 if ( !lib->isLoaded() ) {
59 delete lib;
60 return 0l;
61 }
62 }
63
64 /* now refcount one up */
65 m_libs.insert( str, lib );
66 return lib;
67 }
68
69 /*
70 * 'unshadow' the items until we're the last then unload and delete
71 */
72 void OPluginLibraryHolder::deref( QLibrary* lib ) {
73 if ( !lib )
74 return;
75
76 QString str = lib->library();
77 /* no need to check if the lib was inserted or such */
78 (void) m_libs.take( str );
79 if ( !m_libs[str] ) {
80 lib->unload();
81 delete lib;
82 }
83 }
84}
85
86/**
87 * We want values with 30,29,28 at the beginning of the list
88 */
89
90bool operator<( const OPluginItem& l, const OPluginItem& r ) {
91 return l.position() > r.position();
92}
93
94bool operator>( const OPluginItem& l, const OPluginItem& r ) {
95 return l.position() < r.position();
96}
97
98bool operator<=( const OPluginItem& l, const OPluginItem& r ) {
99 return l.position() >= r.position();
25} 100}
26 101
27}}
28/** 102/**
29 * \brief Creates an Empty OPluginItem 103 * \brief Creates an Empty OPluginItem
30 * 104 *
31 * create an empty pluginitem. Position is set to -1 and the 105 * create an empty pluginitem. Position is set to -1 and the
32 * other things are used with the default ctors 106 * other things are used with the default ctors
33 */ 107 */
34OPluginItem::OPluginItem() 108OPluginItem::OPluginItem()
35 : m_pos( -1 ) { 109 : m_pos( -1 ) {
36} 110}
37 111
38/** 112/**
39 * \brief Create an OPluginItem 113 * \brief Create an OPluginItem
40 * 114 *
41 * Create a Plugin Item with all information. 115 * Create a Plugin Item with all information.
42 * 116 *
43 * @param name The if available translated Name 117 * @param name The if available translated Name
44 * @param conf The name of the config group
45 * @param path The path to the plugin 118 * @param path The path to the plugin
46 * @param pos The position of the plugin if used for sorting 119 * @param pos The position of the plugin if used for sorting
47 * 120 *
48 */ 121 */
49OPluginItem::OPluginItem( const QString& name, const QCString& conf, 122OPluginItem::OPluginItem( const QString& name, const QString& path, int pos )
50 const QString& path, int pos = -1 ) 123 : m_name( name ), m_path( path ), m_pos( pos ) {
51 : m_name( name ), m_conf( conf ), m_path( path ), m_pos( pos ) {
52} 124}
53 125
54/** 126/**
55 * \brief simple d'tor 127 * \brief simple d'tor
56 */ 128 */
57OPluginItem::~OPluginItem() { 129OPluginItem::~OPluginItem() {
58} 130}
59 131
60/** 132/**
61 * operator to test equalness of two OPluginItem 133 * operator to test equalness of two OPluginItem
62 */ 134 */
63bool OPluginItem::operator==( const OPluginItem& r )const{ 135bool OPluginItem::operator==( const OPluginItem& r )const{
64 if ( m_pos != r.m_pos ) return false; 136 if ( m_pos != r.m_pos ) return false;
65 if ( m_name != r.m_name ) return false; 137 if ( m_name != r.m_name ) return false;
66 if ( m_conf != r.m_conf ) return false;
67 if ( m_path != r.m_path ) return false; 138 if ( m_path != r.m_path ) return false;
68 return true; 139 return true;
69} 140}
70 141
71bool OPluginItem::operator!=( const OPluginItem& r ) { 142bool OPluginItem::operator!=( const OPluginItem& r )const{
72 return !( *this == r ); 143 return !( *this == r );
73} 144}
74 145
75/** 146/**
76 * return the name of this Plugin 147 * return the name of this Plugin
77 */ 148 */
78QString OPluginItem::name()const { 149QString OPluginItem::name()const {
79 return m_name; 150 return m_name;
80} 151}
81 152
82/** 153/**
83 * return the config key
84 */
85QCString OPluginItem::configKey()const{
86 return m_conf;
87}
88
89/**
90 * return the path of the plugin 154 * return the path of the plugin
91 */ 155 */
92QString OPluginItem::path()const { 156QString OPluginItem::path()const {
93 return m_path; 157 return m_path;
94} 158}
95 159
96int OPluginItem::position()const{ 160int OPluginItem::position()const{
97 return m_pos; 161 return m_pos;
98} 162}
99 163
100/** 164/**
101 * Set the name of the Plugin Item 165 * Set the name of the Plugin Item
102 * @param name 166 * @param name
103 */ 167 */
104void OPluginItem::setName( const QString& name ) { 168void OPluginItem::setName( const QString& name ) {
105 m_name = name; 169 m_name = name;
106} 170}
107 171
108/** 172/**
109 * Set the config key
110 * @param key The config key/group of this plugin
111 */
112void OPluginItem::setConfigKey( const QCString& conf ) {
113 m_conf = conf;
114}
115
116/**
117 * Set the path of Plugin Item 173 * Set the path of Plugin Item
118 * @param name The path of the plugin 174 * @param name The path of the plugin
119 */ 175 */
120void OPluginItem::setPath( const QString& name ) { 176void OPluginItem::setPath( const QString& name ) {
121 m_name = name; 177 m_name = name;
122} 178}
123 179
124/** 180/**
125 * Set the position 181 * Set the position
126 * @param pos The position 182 * @param pos The position
127 */ 183 */
128void OPluginItem::setPosition( int pos ) { 184void OPluginItem::setPosition( int pos ) {
129 m_pos = pos; 185 m_pos = pos;
130} 186}
131 187
132 188
133 189
134/** 190/**
135 * \brief create a PluginLoader 191 * \brief create a PluginLoader
136 * 192 *
137 * Create a PluginLoader autoDelete is set to false 193 * Create a PluginLoader autoDelete is set to false
138 * 194 *
139 * \code 195 * \code
140 * Opie::Core::OGenericPluginLoader loader("myapp-plugin"); 196 * Opie::Core::OGenericPluginLoader loader("myapp-plugin");
141 * Opie::Core::OPluginItem::List lst = loader.filtered(); 197 * Opie::Core::OPluginItem::List lst = loader.filtered();
142 * for(Opie::Core::OPluginItem::List::Iterator it = lst.begin(); it!=lst.end();++it){ 198 * for(Opie::Core::OPluginItem::List::Iterator it = lst.begin(); it!=lst.end();++it){
143 * MyIface* iface = static_cast<MyIface*>(loader.load(*it,IID_MyIface)); 199 * MyIface* iface = static_cast<MyIface*>(loader.load(*it,IID_MyIface));
144 * } 200 * }
145 * \endcode 201 * \endcode
146 * 202 *
147 * \code 203 * \code
148 * Opie::Core::OGenericPluginLoader loader("myapp-plugin"); 204 * Opie::Core::OGenericPluginLoader loader("myapp-plugin");
149 * Opie::Core::OPluginItem::List lst = loader.filtered(); 205 * Opie::Core::OPluginItem::List lst = loader.filtered();
150 * for(Opie::Core::OPluginItem::List::Iterator it = lst.begin(); it!=lst.end();++it){ 206 * for(Opie::Core::OPluginItem::List::Iterator it = lst.begin(); it!=lst.end();++it){
151 * MyIface* iface = static_cast<MyIface*>(loader.load(*it,IID_MyIface)); 207 * MyIface* iface = static_cast<MyIface*>(loader.load(*it,IID_MyIface));
152 * } 208 * }
153 * ... 209 * ...
154 * loader.clear(); 210 * loader.clear();
155 * 211 *
156 * \endcode 212 * \endcode
157 * 213 *
158 * @param name The name of the plugin directory. 214 * @param name The name of the plugin directory.
159 * @param isSorted Tell the PluginLoader if your Plugins are sorted 215 * @param isSorted Tell the PluginLoader if your Plugins are sorted
160 */ 216 */
161OGenericPluginLoader::OGenericPluginLoader( const QString& name, bool isSorted) 217OGenericPluginLoader::OGenericPluginLoader( const QString& name, bool isSorted)
162 : m_dir( name ), m_autoDelete( false ), m_isSafeMode( false ), 218 : m_dir( name ), m_autoDelete( false ), m_isSafeMode( false ),
163 m_isSorted( isSorted ), m_readConfig( false ) 219 m_isSorted( isSorted )
164{ 220{
165 setPluginDir( QPEApplication::qpeDir() + "/plugins/"+name ); 221 setPluginDir( QPEApplication::qpeDir() + "/plugins/"+name );
222 readConfig();
166} 223}
167 224
168 225
169/** 226/**
170 * calls clear if autoDelete is true. This will release all interfaces 227 * calls clear if autoDelete is true. This will release all interfaces
171 * and remove the library from this process if the refcount falls to zero 228 * and remove the library from this process if the refcount falls to zero
172 */ 229 */
173OGenericPluginLoader::~OGenericPluginLoader() { 230OGenericPluginLoader::~OGenericPluginLoader() {
174 if ( m_autoDelete ) 231 if ( m_autoDelete )
175 clear(); 232 clear();
176} 233}
177 234
178/** 235/**
179 * enable autoDelete. This will call clear on the d'tor 236 * enable autoDelete. This will call clear on the d'tor
180 * 237 *
181 * @see ~OGenericPluginLoader 238 * @see ~OGenericPluginLoader
182 * @see clear() 239 * @see clear()
183 */ 240 */
184void OGenericPluginLoader::setAutoDelete( bool t ) { 241void OGenericPluginLoader::setAutoDelete( bool t ) {
185 m_autoDelete = t; 242 m_autoDelete = t;
186} 243}
187 244
188/** 245/**
189 * see if autoDelet is enabled 246 * see if autoDelet is enabled
190 */ 247 */
191bool OGenericPluginLoader::autoDelete()const{ 248bool OGenericPluginLoader::autoDelete()const{
192 return m_autoDelete; 249 return m_autoDelete;
193} 250}
194 251
195/** 252/**
196 * This will unload all returned QUnknownInterfaces by load. Unload 253 * This will unload all returned QUnknownInterfaces by load. Unload
197 * will be called. 254 * will be called.
198 */ 255 */
199void OGenericPluginLoader::clear() { 256void OGenericPluginLoader::clear() {
200 QPtrDictIterator<QLibrary> it( m_library ); 257 QPtrDictIterator<QLibrary> it( m_library );
201 for ( ;it.current(); ) 258 for ( ;it.current(); )
202 unload( static_cast<QUnknownInterface*>( it.currentKey() ) ); 259 unload( static_cast<QUnknownInterface*>( it.currentKey() ) );
203} 260}
204 261
205/** 262/**
206 * This will take the iface from the internal QPtrDict, Release it, 263 * This will take the iface from the internal QPtrDict, Release it,
207 * and deref the libray used. 264 * and deref the libray used.
208 * The visibility depends on the QPtrDict. 265 * The visibility depends on the QPtrDict.
209 * @see QPtrDict::insert 266 * @see QPtrDict::insert
210 */ 267 */
211void OGenericPluginLoader::unload( QUnknownInterface* iface ) { 268void OGenericPluginLoader::unload( QUnknownInterface* iface ) {
212 if ( !iface ) 269 if ( !iface )
213 return; 270 return;
214 271
215 iface->release(); 272 iface->release();
216 OPluginLibraryHolder::self()->deref( m_library.take( iface ) ); 273 Internal::OPluginLibraryHolder::self()->deref( m_library.take( iface ) );
217} 274}
218 275
219/** 276/**
220 * This tells you 277 * This tells you
221 * if by previous tries to load, loading crashed your application. 278 * if by previous tries to load, loading crashed your application.
222 * If isInSafeMode you can use the GUI to configure the plugins prior to loading 279 * If isInSafeMode you can use the GUI to configure the plugins prior to loading
223 * 280 *
224 * @return true if prior loading failed 281 * @return true if prior loading failed
225 */ 282 */
226bool OGenericPluginLoader::isInSafeMode()const { 283bool OGenericPluginLoader::isInSafeMode()const {
227 if ( !m_readConfig )
228 readConfig();
229 return m_isSafeMode; 284 return m_isSafeMode;
230} 285}
231 286
232/**
233 * return if the plugin list is sorted.
234 */
235bool OGenericPluginLoader::isSorted()const {
236 if ( !m_readConfig )
237 readConfig();
238 return m_isSorted;
239}
240 287
241/** 288/**
242 * Return the list of all available plugins. This will go through all plugin 289 * Return the list of all available plugins. This will go through all plugin
243 * directories and search for your type of plugins ( by subdir ) 290 * directories and search for your type of plugins ( by subdir )
244 * 291 *
245 * @param sorted Tell if you want to have the positions sorted. This only makes sense if you 292 * @param sorted Tell if you want to have the positions sorted. This only makes sense if you
246 */ 293 */
247OPluginItem::List OGenericPluginLoader::allAvailable( bool sorted )const { 294OPluginItem::List OGenericPluginLoader::allAvailable( bool sorted )const {
248 OPluginItem::List lst; 295 OPluginItem::List lst;
249 for ( QStringList::ConstIterator it = m_plugDirs.begin(); it != m_plugDirs.end(); ++it ) 296 for ( QStringList::ConstIterator it = m_plugDirs.begin(); it != m_plugDirs.end(); ++it )
250 lst += plugins( *it, sorted, false ); 297 lst += plugins( *it, sorted, false );
251 298
252 if ( sorted ) 299 if ( sorted )
253 qHeapSort( lst ); 300 qHeapSort( lst );
254 return lst; 301 return lst;
255} 302}
256 303
257/** 304/**
258 * Return only activated plugins. 305 * Return only activated plugins.
259 * 306 *
260 * @param sorted If the list should be sorted 307 * @param sorted If the list should be sorted
261 */ 308 */
262OPluginItem::List OGenericPluginLoader::filtered( bool sorted )const { 309OPluginItem::List OGenericPluginLoader::filtered( bool sorted )const {
263 OPluginItem::List lst; 310 OPluginItem::List lst;
264 for ( QStringList::ConstIterator it = m_plugDirs.begin(); it != m_plugDirs.end(); ++it ) 311 for ( QStringList::ConstIterator it = m_plugDirs.begin(); it != m_plugDirs.end(); ++it )
265 lst += plugins( *it, sorted, true ); 312 lst += plugins( *it, sorted, true );
266 313
267 if ( sorted ) 314 if ( sorted )
268 qHeapSort( lst ); 315 qHeapSort( lst );
269 return lst; 316 return lst;
270} 317}
271 318
272 319
273/** 320/**
274 * 321 *
275 */ 322 */
276QUnknownInterface* OGenericPluginLoader::load( const OPluginItem& item, const QUuid& uuid) { 323QUnknownInterface* OGenericPluginLoader::load( const OPluginItem& item, const QUuid& uuid) {
277 /* 324 /*
278 * Check if there could be a library 325 * Check if there could be a library
279 */ 326 */
280 QString pa = item.path(); 327 QString pa = item.path();
281 if ( pa.isEmpty() ) 328 if ( pa.isEmpty() )
282 return 0l; 329 return 0l;
283 330
284 /* 331 /*
285 * See if we get a library 332 * See if we get a library
286 * return if we've none 333 * return if we've none
287 */ 334 */
288 setSafeMode( true ); 335 setSafeMode( pa, true );
289 QLibrary *lib = OPluginLibraryHolder::self()->getLibrary( pa ); 336 QLibrary *lib = Internal::OPluginLibraryHolder::self()->ref( pa );
290 if ( !lib ) { 337 if ( !lib ) {
291 setSafeMode(); 338 setSafeMode();
292 return 0l; 339 return 0l;
293 } 340 }
294 341
295 /** 342 /**
296 * try to load the plugin and just in case initialize the pointer to a pointer again 343 * try to load the plugin and just in case initialize the pointer to a pointer again
297 */ 344 */
298 QUnknownInterface** iface = 0; 345 QUnknownInterface* iface=0;
299 if ( lib->queryInterface( uuid, iface ) == QS_OK ) { 346 if ( lib->queryInterface( uuid, &iface ) == QS_OK ) {
300 installTranslators(pa.left( pa.find("."))); 347 installTranslators(pa.left( pa.find(".")));
301 m_library.insert( *iface, lib ); 348 m_library.insert( iface, lib );
302 }else 349 }else
303 *iface = 0; 350 iface = 0;
304 351
305 setSafeMode(); 352 setSafeMode();
306 353
307 return *iface; 354 return iface;
308} 355}
309 356
357/**
358 * @internal and reads in the safe mode
359 */
310void OGenericPluginLoader::readConfig() { 360void OGenericPluginLoader::readConfig() {
311 m_readConfig = true;
312
313 /* read the config for SafeMode */ 361 /* read the config for SafeMode */
314 OConfig conf( m_name + "-odpplugins" ); 362 OConfig conf( m_dir + "-odpplugins" );
315 conf.setGroup( "General" ); 363 conf.setGroup( "General" );
316 m_isSafeMode = conf.readBoolEntry( "SafeMode", false ); 364 m_isSafeMode = conf.readBoolEntry( "SafeMode", false );
317} 365}
318 366
319void OGenericPluginLoader::setSafeMode(bool b) { 367/**
320 OConfig conf( m_name + "-odpplugins" ); 368 * Enter or leave SafeMode
369 */
370void OGenericPluginLoader::setSafeMode(const QString& str, bool b) {
371 OConfig conf( m_dir + "-odpplugins" );
321 conf.setGroup( "General" ); 372 conf.setGroup( "General" );
322 conf.writeEntry( "SafeMode", b ); 373 conf.writeEntry( "SafeMode", b );
374 conf.writeEntry( "CrashedPlugin", str );
323} 375}
324 376
377/**
378 * @internal
379 *
380 * Set the List of Plugin Dirs to lst. Currently only QPEApplication::qpeDir()+"/plugins/"+mytype
381 * is used as plugin dir
382 */
325void OGenericPluginLoader::setPluginDirs( const QStringList& lst ) { 383void OGenericPluginLoader::setPluginDirs( const QStringList& lst ) {
326 m_plugDirs = lst; 384 m_plugDirs = lst;
327} 385}
328 386
387/**
388 *
389 * @internal
390 * Set the Plugin Dir to str. Str will be the only element in the list of plugin dirs
391 */
329void OGenericPluginLoader::setPluginDir( const QString& str) { 392void OGenericPluginLoader::setPluginDir( const QString& str) {
330 m_plugDirs.clear(); 393 m_plugDirs.clear();
331 m_plugDirs.append( str ); 394 m_plugDirs.append( str );
332} 395}
333 396
334bool &OGenericPluginLoader::isSafeMode()const {
335 return m_isSafeMode;
336}
337 397
338bool &OGenericPluginLoader::isSorted()const { 398/**
399 * @internal
400 */
401bool OGenericPluginLoader::isSorted()const{
339 return m_isSorted; 402 return m_isSorted;
340} 403}
341 404
342OPluginItem::List OGenericPluginLoader::plugins( const QString& dir, bool sorted, bool disabled ) { 405/*
406 * make libfoo.so.1.0.0 -> foo on UNIX
407 * make libfoo.dylib -> foo on MAC OS X Unix
408 * windows is obviously missing
409 */
410/**
411 * @internal
412 */
413QString OGenericPluginLoader::unlibify( const QString& str ) {
414 QString st = str.mid( str.find( "lib" )+3 );
343#ifdef Q_OS_MACX 415#ifdef Q_OS_MACX
344 QDir dir( dir, "lib*.dylib" ); 416 return st.left( st.findRev( ".dylib" ) );
345#else 417#else
346 QDir dir( dir, "lib*.so" ); 418 return st.left( st.findRev( ".so" ) );
347#endif 419#endif
420}
421
422/**
423 * Return a List of Plugins for a dir and add positions and remove disabled.
424 * If a plugin is on the excluded list assign position -2
425 *
426 * @param dir The dir to look in
427 * @param sorted Should positions be read?
428 * @param disabled Remove excluded from the list
429 */
430OPluginItem::List OGenericPluginLoader::plugins( const QString& _dir, bool sorted, bool disabled )const {
431#ifdef Q_OS_MACX
432 QDir dir( _dir, "lib*.dylib" );
433#else
434 QDir dir( _dir, "lib*.so" );
435#endif
436
437 OPluginItem::List lst;
438
348 /* 439 /*
349 * get excluded list and then iterate over them 440 * get excluded list and then iterate over them
441 * Excluded list contains the name
442 * Position is a list with 'name.pos.name.pos.name.pos'
443 *
444 * For the look up we will create two QMap<QString,pos>
350 */ 445 */
351 OConfig cfg( m_name+"odpplugins" ); 446 QMap<QString, int> positionMap;
352 cfg.setGroup( dir ); 447 QMap<QString, int> excludedMap;
353 QStringList excludes = cfg.readListEntry( "Excluded" ); 448
449
450 OConfig cfg( m_dir+"odpplugins" );
451 cfg.setGroup( _dir );
452
453
454 QStringList excludes = cfg.readListEntry( "Excluded", ',' );
455 for ( QStringList::Iterator it = excludes.begin(); it != excludes.end(); ++it )
456 excludedMap.insert( *it, -2 );
457
458 if ( m_isSorted ) {
459 QStringList pos = cfg.readListEntry( "Positions", '.' );
460 QStringList::Iterator it = pos.begin();
461 while ( it != pos.end() )
462 positionMap.insert( *it++, (*it++).toInt() );
463 }
464
465
466
354 467
355 QStringList list = dir.entryList(); 468 QStringList list = dir.entryList();
356// for ( 469 QStringList::Iterator it;
470 for (QStringList::Iterator it = list.begin(); it != list.end(); ++it ) {
471 QString str = unlibify( *it );
472 OPluginItem item( str, _dir + "/" + *it );
357 473
358} 474 bool ex = excludedMap.contains( str );
475 /*
476 * if disabled but we should show all assign a -2
477 * else continue because we don't want to add the item
478 * else if sorted we assign the right position
479 */
480 if ( ex && !disabled)
481 item.setPosition( -2 );
482 else if ( ex && disabled )
483 continue;
484 else if ( sorted )
485 item.setPosition( positionMap[str] );
486
487 lst.append( item );
488 }
359 489
490 return lst;
491}
360 492
493/**
494 * @internal generate a list of languages from $LANG
495 */
361QStringList OGenericPluginLoader::languageList() { 496QStringList OGenericPluginLoader::languageList() {
362 if ( languageList.isEmpty() ) { 497 if ( m_languages.isEmpty() ) {
363 /* 498 /*
364 * be_BY.CP1251 We will add, be_BY.CP1251,be_BY,be 499 * be_BY.CP1251 We will add, be_BY.CP1251,be_BY,be
365 * to our list of languages. 500 * to our list of languages.
366 */ 501 */
367 QString str = ::getenv( "LANG" ); 502 QString str = ::getenv( "LANG" );
368 m_languages += str; 503 m_languages += str;
369 int pos = str.find( '.' ); 504 int pos = str.find( '.' );
370 505
371 if ( pos > 0 ) 506 if ( pos > 0 )
372 m_languages += str.left( pos ); 507 m_languages += str.left( pos );
373 508
374 int n_pos = str.find( '_' ); 509 int n_pos = str.find( '_' );
375 if ( pos > 0 && n_pos >= pos ) 510 if ( pos > 0 && n_pos >= pos )
376 m_languages += str.left( n_pos ); 511 m_languages += str.left( n_pos );
377 512
378 } 513 }
379 return m_languages; 514 return m_languages;
380} 515}
381 516
382void OGenericPluginLoader::installTranslators(const QString& type) { 517void OGenericPluginLoader::installTranslators(const QString& type) {
383 QStringList lst = languageList(); 518 QStringList lst = languageList();
519
520 /*
521 * for each language and maybe later for each language dir...
522 * try to load a Translator
523 */
384 for ( QStringList::Iterator it = lst.begin(); it != lst.end(); ++it ) { 524 for ( QStringList::Iterator it = lst.begin(); it != lst.end(); ++it ) {
385 QTranslator* trans = new QTranslator( qApp ); 525 QTranslator* trans = new QTranslator( qApp );
386 QString tfn = QPEApplication::qpeDir()+"/i18n/" + lang + "/" + type + ".qm" ; 526 QString tfn = QPEApplication::qpeDir()+"/i18n/" + *it + "/" + type + ".qm" ;
527
528 /*
529 * If loaded then install else clean up and don't leak
530 */
387 if ( trans->load( tfn ) ) 531 if ( trans->load( tfn ) )
388 qApp->installTranslator( trans ); 532 qApp->installTranslator( trans );
389 else 533 else
390 delete trans; 534 delete trans;
391 } 535 }
392} 536}
393 537
394 538
395 539
396} 540}
397} 541}
diff --git a/libopie2/opiecore/opluginloader.h b/libopie2/opiecore/opluginloader.h
index a7df4a8..421d1f6 100644
--- a/libopie2/opiecore/opluginloader.h
+++ b/libopie2/opiecore/opluginloader.h
@@ -1,191 +1,187 @@
1/* 1/*
2 * LGPLv2 or later 2 * LGPLv2 or later
3 * zecke@handhelds.org 3 * zecke@handhelds.org
4 */ 4 */
5#ifndef ODP_CORE_OPLUGIN_LOADER_H 5#ifndef ODP_CORE_OPLUGIN_LOADER_H
6#define ODP_CORE_OPLUGIN_LOADER_H 6#define ODP_CORE_OPLUGIN_LOADER_H
7 7
8#include <qpe/qlibrary.h> 8#include <qpe/qlibrary.h>
9 9
10#include <qptrdict.h>
10#include <qstringlist.h> 11#include <qstringlist.h>
11 12
12namespace Opie { 13namespace Opie {
13namespace Core { 14namespace Core {
14class OConfig; 15class OConfig;
15namespace Internal { 16namespace Internal {
16class OPluginLibraryHolder; 17class OPluginLibraryHolder;
17} 18}
18 19
19template class QPtrDict<QLibrary>; 20template class QPtrDict<QLibrary>;
20 21
21/** 22/**
22 * \brief A small item representing the Plugin Information 23 * \brief A small item representing the Plugin Information
23 * This class contains the information about a Plugin. It contains 24 * This class contains the information about a Plugin. It contains
24 * a translated name if available to the system, a config key, 25 * a translated name if available to the system, a config key,
25 * and the path location. 26 * and the path location.
26 * 27 *
27 * @since 1.2 28 * @since 1.2
28 * 29 *
29 */ 30 */
30class OPluginItem { 31class OPluginItem {
31public: 32public:
32 typedef QValueList<OPluginItem> List; 33 typedef QValueList<OPluginItem> List;
33 OPluginItem(); 34 OPluginItem();
34 OPluginItem( const QString& name, const QCString& confopt, const QString& path, int pos = -1 ); 35 OPluginItem( const QString& name, const QString& path, int pos = -1 );
35 ~OPluginItem(); 36 ~OPluginItem();
36 37
37 bool operator==( const OPluginItem& )const; 38 bool operator==( const OPluginItem& )const;
38 bool operator!=( const OPluginItem& )const; 39 bool operator!=( const OPluginItem& )const;
39 40
40 41
41 QString name()const; 42 QString name()const;
42 QCString configKey()const;
43 QString path()const; 43 QString path()const;
44 int position()const; 44 int position()const;
45 45
46 void setName( const QString& ); 46 void setName( const QString& );
47 void setConfigKey( const QCString& );
48 void setPath( const QString& ); 47 void setPath( const QString& );
49 void setPosition( int ); 48 void setPosition( int );
50 49
51private: 50private:
52 QString m_name; 51 QString m_name;
53 QCString m_conf;
54 QString m_path; 52 QString m_path;
55 int m_pos; 53 int m_pos;
56 struct Private; 54 struct Private;
57 Private *d; 55 Private *d;
58}; 56};
59 57
60/** 58/**
61 * \brief A generic class to easily load and manage plugins 59 * \brief A generic class to easily load and manage plugins
62 * 60 *
63 * This is the generic non sepcialised loader for plugins. Normally 61 * This is the generic non sepcialised loader for plugins. Normally
64 * you would prefer using the OPluginLoader directly. This class 62 * you would prefer using the OPluginLoader directly. This class
65 * exists to minimize the application binary size due the usage 63 * exists to minimize the application binary size due the usage
66 * of templates in the specialized API 64 * of templates in the specialized API
67 * 65 *
68 * @since 1.2 66 * @since 1.2
69 * @see OPluginLoader 67 * @see OPluginLoader
70 */ 68 */
71class OGenericPluginLoader { 69class OGenericPluginLoader {
72public: 70public:
73 typedef OPluginItem::List List; 71 typedef OPluginItem::List List;
74 OGenericPluginLoader( const QString &name, bool isSorted = false ); 72 OGenericPluginLoader( const QString &name, bool isSorted = false );
75 virtual ~OGenericPluginLoader(); 73 virtual ~OGenericPluginLoader();
76 74
77 void setAutoDelete( bool ); 75 void setAutoDelete( bool );
78 bool autoDelete()const; 76 bool autoDelete()const;
79 void clear(); 77 void clear();
80 78
81 79
82 bool isInSafeMode()const; 80 bool isInSafeMode()const;
83 81
84 82
85 List allAvailable(bool sorted = FALSE)const; 83 List allAvailable(bool sorted = FALSE)const;
86 List filtered(bool sorted = FALSE)const; 84 List filtered(bool sorted = FALSE)const;
87 85
88 86
89 virtual QUnknownInterface* load( const OPluginItem& item, const QUuid& ); 87 virtual QUnknownInterface* load( const OPluginItem& item, const QUuid& );
90 virtual void unload( QUnknownInterface* ); 88 virtual void unload( QUnknownInterface* );
91 89
92protected: 90protected:
93 virtual void readConfig(); 91 void readConfig();
94 virtual List plugins( const QString& dir, bool sorted, bool disabled )const; 92 virtual List plugins( const QString& dir, bool sorted, bool disabled )const;
95 void setPluginDirs( const QStringList& ); 93 void setPluginDirs( const QStringList& );
96 void setPluginDir( const QString& ); 94 void setPluginDir( const QString& );
97 bool &isSafeMode()const; 95 bool isSorted()const;
98 bool &isSorted()const; 96 void setSafeMode(const QString& app = QString::null, bool b = false);
99 void readConfig()const; 97 static QString unlibify( const QString& str );
100 void setSafeMode(bool b = false);
101 98
102private: 99private:
103 QString languageList(); 100 QStringList languageList();
104 void installTranslators(const QString& type); 101 void installTranslators(const QString& type);
105 QString m_dir; 102 QString m_dir;
106 QStringList m_plugDirs; 103 QStringList m_plugDirs;
107 QStringList m_languages; 104 QStringList m_languages;
108 bool m_autoDelete : 1; 105 bool m_autoDelete : 1;
109 bool m_isSafeMode : 1; 106 bool m_isSafeMode : 1;
110 bool m_readConfig : 1;
111 bool m_isSorted : 1; 107 bool m_isSorted : 1;
112 QPtrDict<QLibrary> m_library; 108 QPtrDict<QLibrary> m_library;
113 109
114 struct Private; 110 struct Private;
115 Private* d; 111 Private* d;
116}; 112};
117 113
118/** 114/**
119 * \brief The class to load your QCOM+ plugins 115 * \brief The class to load your QCOM+ plugins
120 * 116 *
121 * This class takes care of activation and even the order 117 * This class takes care of activation and even the order
122 * if you need it. It is normally good to place a .directory file 118 * if you need it. It is normally good to place a .directory file
123 * into your plugin directory if you need order of activation. 119 * into your plugin directory if you need order of activation.
124 * 120 *
125 * You'll create the OPluginLoader and then use it to load the filtered 121 * You'll create the OPluginLoader and then use it to load the filtered
126 * plugins. 122 * plugins.
127 * 123 *
128 * There is also a GUI for the configuration and a Manager to write the 124 * There is also a GUI for the configuration and a Manager to write the
129 * mentioned .directory file 125 * mentioned .directory file
130 * 126 *
131 * On crash the safe mode is activated for the next run. You can then decide 127 * On crash the safe mode is activated for the next run. You can then decide
132 * if you want to load plugins or come up with the Configuration on 128 * if you want to load plugins or come up with the Configuration on
133 * next start yourself then. 129 * next start yourself then.
134 * 130 *
135 * @since 1.2 131 * @since 1.2
136 */ 132 */
137class OPluginLoader : public OGenericPluginLoader { 133class OPluginLoader : public OGenericPluginLoader {
138public: 134public:
139 OPluginLoader( const QString& name, bool sorted = false ); 135 OPluginLoader( const QString& name, bool sorted = false );
140 ~OPluginLoader(); 136 ~OPluginLoader();
141 137
142 temlate<class IFace> 138 template<class IFace>
143 IFace* load( const QString& name, const QUuid& ); 139 IFace* load( const QString& name, const QUuid& );
144 temlate<class IFace> 140 template<class IFace>
145 IFace* load( const OPluginItem& item, const QUuid& ); 141 IFace* load( const OPluginItem& item, const QUuid& );
146}; 142};
147 143
148/** 144/**
149 * \brief A class to manager order and activation of plugins 145 * \brief A class to manager order and activation of plugins
150 * 146 *
151 * Manage order and activation. This is used by the Opie::Ui::OPluginConfig 147 * Manage order and activation. This is used by the Opie::Ui::OPluginConfig
152 * This class controls the activation and order of plugins depending 148 * This class controls the activation and order of plugins depending
153 * on the OPluginLoader you supply. 149 * on the OPluginLoader you supply.
154 * 150 *
155 * @see OPluginConfig 151 * @see OPluginConfig
156 * 152 *
157 */ 153 */
158class OPluginManager { 154class OPluginManager {
159public: 155public:
160 OPluginManager( OGenericPluginLoader* , const QString& name); 156 OPluginManager( OGenericPluginLoader* , const QString& name);
161 OPluginManager( OConfig* conf, const QString&, 157 OPluginManager( OConfig* conf, const QString&,
162 const QCString& group, const OPluginItem::List& ); 158 const QCString& group, const OPluginItem::List& );
163 ~OPluginManager(); 159 ~OPluginManager();
164 160
165 QString name(); 161 QString name();
166 void setName( const QString& ); 162 void setName( const QString& );
167 163
168 void setPosition( const OPluginItem& ); 164 void setPosition( const OPluginItem& );
169 void enable( const OPluginItem& ); 165 void enable( const OPluginItem& );
170 void disable( const OPluginItem& ); 166 void disable( const OPluginItem& );
171 void setEnabled( const OPluginItem&, bool = true); 167 void setEnabled( const OPluginItem&, bool = true);
172 168
173 void load(); 169 void load();
174 void save(); 170 void save();
175}; 171};
176 172
177template<class IFace> 173template<class IFace>
178IFace* OPluginLoader::load( const QString& name, const QUuid& uid ) { 174IFace* OPluginLoader::load( const QString& name, const QUuid& uid ) {
179 return static_cast<IFace*>( OGenericPluginLoader::load( item, uid ) ); 175 return static_cast<IFace*>( OGenericPluginLoader::load( item, uid ) );
180} 176}
181 177
182template<class IFace> 178template<class IFace>
183IFace* OPluginLoader::load( const OPluginItem& item, const QUuid& uid ) { 179IFace* OPluginLoader::load( const OPluginItem& item, const QUuid& uid ) {
184 return static_cast<IFace*>( OGenericPluginLoader::load( item, uid ) ); 180 return static_cast<IFace*>( OGenericPluginLoader::load( item, uid ) );
185} 181}
186 182
187} 183}
188} 184}
189 185
190 186
191#endif 187#endif