plugin/qlibrary.cpp

Source codeSwitch to Preprocessed file
LineSource CodeCoverage
1 -
2/**************************************************************************** -
3** -
4** Copyright (C) 2013 Digia Plc and/or its subsidiary(-ies). -
5** Contact: http://www.qt-project.org/legal -
6** -
7** This file is part of the QtCore module of the Qt Toolkit. -
8** -
9** $QT_BEGIN_LICENSE:LGPL$ -
10** Commercial License Usage -
11** Licensees holding valid commercial Qt licenses may use this file in -
12** accordance with the commercial license agreement provided with the -
13** Software or, alternatively, in accordance with the terms contained in -
14** a written agreement between you and Digia. For licensing terms and -
15** conditions see http://qt.digia.com/licensing. For further information -
16** use the contact form at http://qt.digia.com/contact-us. -
17** -
18** GNU Lesser General Public License Usage -
19** Alternatively, this file may be used under the terms of the GNU Lesser -
20** General Public License version 2.1 as published by the Free Software -
21** Foundation and appearing in the file LICENSE.LGPL included in the -
22** packaging of this file. Please review the following information to -
23** ensure the GNU Lesser General Public License version 2.1 requirements -
24** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. -
25** -
26** In addition, as a special exception, Digia gives you certain additional -
27** rights. These rights are described in the Digia Qt LGPL Exception -
28** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. -
29** -
30** GNU General Public License Usage -
31** Alternatively, this file may be used under the terms of the GNU -
32** General Public License version 3.0 as published by the Free Software -
33** Foundation and appearing in the file LICENSE.GPL included in the -
34** packaging of this file. Please review the following information to -
35** ensure the GNU General Public License version 3.0 requirements will be -
36** met: http://www.gnu.org/copyleft/gpl.html. -
37** -
38** -
39** $QT_END_LICENSE$ -
40** -
41****************************************************************************/ -
42#include "qplatformdefs.h" -
43#include "qlibrary.h" -
44 -
45#ifndef QT_NO_LIBRARY -
46 -
47#include "qlibrary_p.h" -
48#include <qstringlist.h> -
49#include <qfile.h> -
50#include <qfileinfo.h> -
51#include <qmutex.h> -
52#include <qmap.h> -
53#include <private/qcoreapplication_p.h> -
54#ifdef Q_OS_MAC -
55# include <private/qcore_mac_p.h> -
56#endif -
57#ifndef NO_ERRNO_H -
58#include <errno.h> -
59#endif // NO_ERROR_H -
60#include <qdebug.h> -
61#include <qvector.h> -
62#include <qdir.h> -
63#include <qendian.h> -
64#include <qjsondocument.h> -
65#include <qjsonvalue.h> -
66#include "qelfparser_p.h" -
67 -
68QT_BEGIN_NAMESPACE -
69 -
70#ifdef QT_NO_DEBUG -
71# define QLIBRARY_AS_DEBUG false -
72#else -
73# define QLIBRARY_AS_DEBUG true -
74#endif -
75 -
76#if defined(Q_OS_UNIX) -
77// We don't use separate debug and release libs on UNIX, so we want -
78// to allow loading plugins, regardless of how they were built. -
79# define QT_NO_DEBUG_PLUGIN_CHECK -
80#endif -
81 -
82static QBasicMutex qt_library_mutex; -
83 -
84/*! -
85 \class QLibrary -
86 \inmodule QtCore -
87 \reentrant -
88 \brief The QLibrary class loads shared libraries at runtime. -
89 -
90 -
91 \ingroup plugins -
92 -
93 An instance of a QLibrary object operates on a single shared -
94 object file (which we call a "library", but is also known as a -
95 "DLL"). A QLibrary provides access to the functionality in the -
96 library in a platform independent way. You can either pass a file -
97 name in the constructor, or set it explicitly with setFileName(). -
98 When loading the library, QLibrary searches in all the -
99 system-specific library locations (e.g. \c LD_LIBRARY_PATH on -
100 Unix), unless the file name has an absolute path. -
101 -
102 If the file name is an absolute path then an attempt is made to -
103 load this path first. If the file cannot be found, QLibrary tries -
104 the name with different platform-specific file prefixes, like -
105 "lib" on Unix and Mac, and suffixes, like ".so" on Unix, ".dylib" -
106 on the Mac, or ".dll" on Windows. -
107 -
108 If the file path is not absolute then QLibrary modifies the search -
109 order to try the system-specific prefixes and suffixes first, -
110 followed by the file path specified. -
111 -
112 This makes it possible to specify shared libraries that are only -
113 identified by their basename (i.e. without their suffix), so the -
114 same code will work on different operating systems yet still -
115 minimise the number of attempts to find the library. -
116 -
117 The most important functions are load() to dynamically load the -
118 library file, isLoaded() to check whether loading was successful, -
119 and resolve() to resolve a symbol in the library. The resolve() -
120 function implicitly tries to load the library if it has not been -
121 loaded yet. Multiple instances of QLibrary can be used to access -
122 the same physical library. Once loaded, libraries remain in memory -
123 until the application terminates. You can attempt to unload a -
124 library using unload(), but if other instances of QLibrary are -
125 using the same library, the call will fail, and unloading will -
126 only happen when every instance has called unload(). -
127 -
128 A typical use of QLibrary is to resolve an exported symbol in a -
129 library, and to call the C function that this symbol represents. -
130 This is called "explicit linking" in contrast to "implicit -
131 linking", which is done by the link step in the build process when -
132 linking an executable against a library. -
133 -
134 The following code snippet loads a library, resolves the symbol -
135 "mysymbol", and calls the function if everything succeeded. If -
136 something goes wrong, e.g. the library file does not exist or the -
137 symbol is not defined, the function pointer will be 0 and won't be -
138 called. -
139 -
140 \snippet code/src_corelib_plugin_qlibrary.cpp 0 -
141 -
142 The symbol must be exported as a C function from the library for -
143 resolve() to work. This means that the function must be wrapped in -
144 an \c{extern "C"} block if the library is compiled with a C++ -
145 compiler. On Windows, this also requires the use of a \c dllexport -
146 macro; see resolve() for the details of how this is done. For -
147 convenience, there is a static resolve() function which you can -
148 use if you just want to call a function in a library without -
149 explicitly loading the library first: -
150 -
151 \snippet code/src_corelib_plugin_qlibrary.cpp 1 -
152 -
153 \sa QPluginLoader -
154*/ -
155 -
156/*! -
157 \enum QLibrary::LoadHint -
158 -
159 This enum describes the possible hints that can be used to change the way -
160 libraries are handled when they are loaded. These values indicate how -
161 symbols are resolved when libraries are loaded, and are specified using -
162 the setLoadHints() function. -
163 -
164 \value ResolveAllSymbolsHint -
165 Causes all symbols in a library to be resolved when it is loaded, not -
166 simply when resolve() is called. -
167 \value ExportExternalSymbolsHint -
168 Exports unresolved and external symbols in the library so that they can be -
169 resolved in other dynamically-loaded libraries loaded later. -
170 \value LoadArchiveMemberHint -
171 Allows the file name of the library to specify a particular object file -
172 within an archive file. -
173 If this hint is given, the filename of the library consists of -
174 a path, which is a reference to an archive file, followed by -
175 a reference to the archive member. -
176 \value PreventUnloadHint -
177 Prevents the library from being unloaded from the address space if close() -
178 is called. The library's static variables are not reinitialized if open() -
179 is called at a later time. -
180 -
181 \sa loadHints -
182*/ -
183 -
184 -
185#if defined(Q_OS_UNIX) && !defined(Q_OS_MAC) -
186 -
187static long qt_find_pattern(const char *s, ulong s_len, -
188 const char *pattern, ulong p_len) -
189{ -
190 /* -
191 we search from the end of the file because on the supported -
192 systems, the read-only data/text segments are placed at the end -
193 of the file. HOWEVER, when building with debugging enabled, all -
194 the debug symbols are placed AFTER the data/text segments. -
195 -
196 what does this mean? when building in release mode, the search -
197 is fast because the data we are looking for is at the end of the -
198 file... when building in debug mode, the search is slower -
199 because we have to skip over all the debugging symbols first -
200 */ -
201 -
202 if (! s || ! pattern || p_len > s_len) return -1;
never executed: return -1;
partially evaluated: ! s
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
partially evaluated: ! pattern
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
partially evaluated: p_len > s_len
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
0-227
203 ulong i, hs = 0, hp = 0, delta = s_len - p_len;
executed (the execution status of this line is deduced): ulong i, hs = 0, hp = 0, delta = s_len - p_len;
-
204 -
205 for (i = 0; i < p_len; ++i) {
evaluated: i < p_len
TRUEFALSE
yes
Evaluation Count:2724
yes
Evaluation Count:227
227-2724
206 hs += s[delta + i];
executed (the execution status of this line is deduced): hs += s[delta + i];
-
207 hp += pattern[i];
executed (the execution status of this line is deduced): hp += pattern[i];
-
208 }
executed: }
Execution Count:2724
2724
209 i = delta;
executed (the execution status of this line is deduced): i = delta;
-
210 for (;;) {
executed (the execution status of this line is deduced): for (;;) {
-
211 if (hs == hp && qstrncmp(s + i, pattern, p_len) == 0)
evaluated: hs == hp
TRUEFALSE
yes
Evaluation Count:236
yes
Evaluation Count:54628
evaluated: qstrncmp(s + i, pattern, p_len) == 0
TRUEFALSE
yes
Evaluation Count:227
yes
Evaluation Count:9
9-54628
212 return i;
executed: return i;
Execution Count:227
227
213 if (i == 0)
partially evaluated: i == 0
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:54637
0-54637
214 break;
never executed: break;
0
215 --i;
executed (the execution status of this line is deduced): --i;
-
216 hs -= s[i + p_len];
executed (the execution status of this line is deduced): hs -= s[i + p_len];
-
217 hs += s[i];
executed (the execution status of this line is deduced): hs += s[i];
-
218 }
executed: }
Execution Count:54637
54637
219 -
220 return -1;
never executed: return -1;
0
221} -
222 -
223/* -
224 This opens the specified library, mmaps it into memory, and searches -
225 for the QT_PLUGIN_VERIFICATION_DATA. The advantage of this approach is that -
226 we can get the verification data without have to actually load the library. -
227 This lets us detect mismatches more safely. -
228 -
229 Returns false if version information is not present, or if the -
230 information could not be read. -
231 Returns true if version information is present and successfully read. -
232*/ -
233static bool qt_unix_query(const QString &library, QLibraryPrivate *lib) -
234{ -
235 QFile file(library);
executed (the execution status of this line is deduced): QFile file(library);
-
236 if (!file.open(QIODevice::ReadOnly)) {
partially evaluated: !file.open(QIODevice::ReadOnly)
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:486
0-486
237 if (lib)
never evaluated: lib
0
238 lib->errorString = file.errorString();
never executed: lib->errorString = file.errorString();
0
239 if (qt_debug_component()) {
never evaluated: qt_debug_component()
0
240 qWarning("%s: %s", (const char*) QFile::encodeName(library),
never executed (the execution status of this line is deduced): QMessageLogger("plugin/qlibrary.cpp", 240, __PRETTY_FUNCTION__).warning("%s: %s", (const char*) QFile::encodeName(library),
-
241 qPrintable(qt_error_string(errno)));
never executed (the execution status of this line is deduced): QString(qt_error_string((*__errno_location ()))).toLocal8Bit().constData());
-
242 }
never executed: }
0
243 return false;
never executed: return false;
0
244 } -
245 -
246 QByteArray data;
executed (the execution status of this line is deduced): QByteArray data;
-
247 const char *filedata = 0;
executed (the execution status of this line is deduced): const char *filedata = 0;
-
248 ulong fdlen = file.size();
executed (the execution status of this line is deduced): ulong fdlen = file.size();
-
249 filedata = (char *) file.map(0, fdlen);
executed (the execution status of this line is deduced): filedata = (char *) file.map(0, fdlen);
-
250 if (filedata == 0) {
partially evaluated: filedata == 0
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:486
0-486
251 // try reading the data into memory instead -
252 data = file.readAll();
never executed (the execution status of this line is deduced): data = file.readAll();
-
253 filedata = data.constData();
never executed (the execution status of this line is deduced): filedata = data.constData();
-
254 fdlen = data.size();
never executed (the execution status of this line is deduced): fdlen = data.size();
-
255 }
never executed: }
0
256 -
257 /* -
258 ELF binaries on GNU, have .qplugin sections. -
259 */ -
260 bool hasMetaData = false;
executed (the execution status of this line is deduced): bool hasMetaData = false;
-
261 long pos = 0;
executed (the execution status of this line is deduced): long pos = 0;
-
262 const char pattern[] = "QTMETADATA ";
executed (the execution status of this line is deduced): const char pattern[] = "QTMETADATA ";
-
263 const ulong plen = qstrlen(pattern);
executed (the execution status of this line is deduced): const ulong plen = qstrlen(pattern);
-
264#if defined (Q_OF_ELF) && defined(Q_CC_GNU) -
265 int r = QElfParser().parse(filedata, fdlen, library, lib, &pos, &fdlen);
executed (the execution status of this line is deduced): int r = QElfParser().parse(filedata, fdlen, library, lib, &pos, &fdlen);
-
266 if (r == QElfParser::Corrupt || r == QElfParser::NotElf) {
evaluated: r == QElfParser::Corrupt
TRUEFALSE
yes
Evaluation Count:3
yes
Evaluation Count:483
evaluated: r == QElfParser::NotElf
TRUEFALSE
yes
Evaluation Count:255
yes
Evaluation Count:228
3-483
267 if (lib && qt_debug_component()) {
partially evaluated: lib
TRUEFALSE
yes
Evaluation Count:258
no
Evaluation Count:0
partially evaluated: qt_debug_component()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:258
0-258
268 qWarning("QElfParser: %s",qPrintable(lib->errorString));
never executed (the execution status of this line is deduced): QMessageLogger("plugin/qlibrary.cpp", 268, __PRETTY_FUNCTION__).warning("QElfParser: %s",QString(lib->errorString).toLocal8Bit().constData());
-
269 }
never executed: }
0
270 return false;
executed: return false;
Execution Count:258
258
271 } else if (r == QElfParser::QtMetaDataSection) {
evaluated: r == QElfParser::QtMetaDataSection
TRUEFALSE
yes
Evaluation Count:227
yes
Evaluation Count:1
1-227
272 long rel = qt_find_pattern(filedata + pos, fdlen, pattern, plen);
executed (the execution status of this line is deduced): long rel = qt_find_pattern(filedata + pos, fdlen, pattern, plen);
-
273 if (rel < 0)
partially evaluated: rel < 0
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
0-227
274 pos = -1;
never executed: pos = -1;
0
275 else -
276 pos += rel;
executed: pos += rel;
Execution Count:227
227
277 hasMetaData = true;
executed (the execution status of this line is deduced): hasMetaData = true;
-
278 }
executed: }
Execution Count:227
227
279#else -
280 pos = qt_find_pattern(filedata, fdlen, pattern, plen); -
281 if (pos > 0) -
282 hasMetaData = true; -
283#endif // defined(Q_OF_ELF) && defined(Q_CC_GNU) -
284 -
285 bool ret = false;
executed (the execution status of this line is deduced): bool ret = false;
-
286 -
287 if (pos >= 0) {
partially evaluated: pos >= 0
TRUEFALSE
yes
Evaluation Count:228
no
Evaluation Count:0
0-228
288 if (hasMetaData) {
evaluated: hasMetaData
TRUEFALSE
yes
Evaluation Count:227
yes
Evaluation Count:1
1-227
289 const char *data = filedata + pos;
executed (the execution status of this line is deduced): const char *data = filedata + pos;
-
290 QJsonDocument doc = QLibraryPrivate::fromRawMetaData(data);
executed (the execution status of this line is deduced): QJsonDocument doc = QLibraryPrivate::fromRawMetaData(data);
-
291 lib->metaData = doc.object();
executed (the execution status of this line is deduced): lib->metaData = doc.object();
-
292 if (qt_debug_component())
partially evaluated: qt_debug_component()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
0-227
293 qWarning("Found metadata in lib %s, metadata=\n%s\n",
never executed: QMessageLogger("plugin/qlibrary.cpp", 293, __PRETTY_FUNCTION__).warning("Found metadata in lib %s, metadata=\n%s\n", library.toLocal8Bit().constData(), doc.toJson().constData());
0
294 library.toLocal8Bit().constData(), doc.toJson().constData());
never executed: QMessageLogger("plugin/qlibrary.cpp", 293, __PRETTY_FUNCTION__).warning("Found metadata in lib %s, metadata=\n%s\n", library.toLocal8Bit().constData(), doc.toJson().constData());
0
295 ret = !doc.isNull();
executed (the execution status of this line is deduced): ret = !doc.isNull();
-
296 }
executed: }
Execution Count:227
227
297 }
executed: }
Execution Count:228
228
298 -
299 if (!ret && lib)
evaluated: !ret
TRUEFALSE
yes
Evaluation Count:1
yes
Evaluation Count:227
partially evaluated: lib
TRUEFALSE
yes
Evaluation Count:1
no
Evaluation Count:0
0-227
300 lib->errorString = QLibrary::tr("Plugin verification data mismatch in '%1'").arg(library);
executed: lib->errorString = QLibrary::tr("Plugin verification data mismatch in '%1'").arg(library);
Execution Count:1
1
301 file.close();
executed (the execution status of this line is deduced): file.close();
-
302 return ret;
executed: return ret;
Execution Count:228
228
303} -
304 -
305#endif // Q_OS_UNIX && !Q_OS_MAC -
306 -
307static void installCoverageTool(QLibraryPrivate *libPrivate) -
308{ -
309#ifdef __COVERAGESCANNER__ -
310 /* -
311 __COVERAGESCANNER__ is defined when Qt has been instrumented for code -
312 coverage by TestCocoon. CoverageScanner is the name of the tool that -
313 generates the code instrumentation. -
314 This code is required here when code coverage analysis with TestCocoon -
315 is enabled in order to allow the loading application to register the plugin -
316 and then store its execution report. The execution report gathers information -
317 about each part of the plugin's code that has been used when -
318 the plugin was loaded by the launching application. -
319 The execution report for the plugin will go to the same execution report -
320 as the one defined for the application loading it. -
321 */ -
322 -
323 int ret = __coveragescanner_register_library(libPrivate->fileName.toLocal8Bit());
executed (the execution status of this line is deduced): int ret = __coveragescanner_register_library(libPrivate->fileName.toLocal8Bit());
-
324 -
325 if (qt_debug_component()) {
partially evaluated: qt_debug_component()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:253
0-253
326 if (ret >= 0) {
never evaluated: ret >= 0
0
327 qDebug("%s: coverage data for %s registered",
never executed (the execution status of this line is deduced): QMessageLogger("plugin/qlibrary.cpp", 327, __PRETTY_FUNCTION__).debug("%s: coverage data for %s registered",
-
328 Q_FUNC_INFO,
never executed (the execution status of this line is deduced): __PRETTY_FUNCTION__,
-
329 qPrintable(libPrivate->fileName));
never executed (the execution status of this line is deduced): QString(libPrivate->fileName).toLocal8Bit().constData());
-
330 } else {
never executed: }
0
331 qWarning("%s: could not register %s: error %d; coverage data may be incomplete",
never executed (the execution status of this line is deduced): QMessageLogger("plugin/qlibrary.cpp", 331, __PRETTY_FUNCTION__).warning("%s: could not register %s: error %d; coverage data may be incomplete",
-
332 Q_FUNC_INFO,
never executed (the execution status of this line is deduced): __PRETTY_FUNCTION__,
-
333 qPrintable(libPrivate->fileName),
never executed (the execution status of this line is deduced): QString(libPrivate->fileName).toLocal8Bit().constData(),
-
334 ret);
never executed (the execution status of this line is deduced): ret);
-
335 }
never executed: }
0
336 } -
337#else -
338 Q_UNUSED(libPrivate); -
339#endif -
340}
executed: }
Execution Count:253
253
341 -
342typedef QMap<QString, QLibraryPrivate*> LibraryMap; -
343 -
344struct LibraryData { -
345 LibraryMap libraryMap; -
346 QSet<QLibraryPrivate*> loadedLibs; -
347}; -
348 -
349Q_GLOBAL_STATIC(LibraryData, libraryData)
never executed: delete x;
executed: return thisGlobalStatic.pointer.load();
Execution Count:4966
partially evaluated: !thisGlobalStatic.pointer.testAndSetOrdered(0, x)
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:44
evaluated: !thisGlobalStatic.pointer.load()
TRUEFALSE
yes
Evaluation Count:44
yes
Evaluation Count:4922
partially evaluated: !thisGlobalStatic.destroyed
TRUEFALSE
yes
Evaluation Count:44
no
Evaluation Count:0
0-4966
350 -
351static LibraryMap *libraryMap() -
352{ -
353 LibraryData *data = libraryData();
executed (the execution status of this line is deduced): LibraryData *data = libraryData();
-
354 return data ? &data->libraryMap : 0;
executed: return data ? &data->libraryMap : 0;
Execution Count:3770
3770
355} -
356 -
357QLibraryPrivate::QLibraryPrivate(const QString &canonicalFileName, const QString &version) -
358 : pHnd(0), fileName(canonicalFileName), fullVersion(version), instance(0), -
359 loadHints(0), -
360 libraryRefCount(1), libraryUnloadCount(0), pluginState(MightBeAPlugin) -
361{ libraryMap()->insert(canonicalFileName, this); }
executed: }
Execution Count:608
608
362 -
363QLibraryPrivate *QLibraryPrivate::findOrCreate(const QString &fileName, const QString &version) -
364{ -
365 QMutexLocker locker(&qt_library_mutex);
executed (the execution status of this line is deduced): QMutexLocker locker(&qt_library_mutex);
-
366 if (QLibraryPrivate *lib = libraryMap()->value(fileName)) {
evaluated: QLibraryPrivate *lib = libraryMap()->value(fileName)
TRUEFALSE
yes
Evaluation Count:147
yes
Evaluation Count:608
147-608
367 lib->libraryRefCount.ref();
executed (the execution status of this line is deduced): lib->libraryRefCount.ref();
-
368 return lib;
executed: return lib;
Execution Count:147
147
369 } -
370 -
371 return new QLibraryPrivate(fileName, version);
executed: return new QLibraryPrivate(fileName, version);
Execution Count:608
608
372} -
373 -
374QLibraryPrivate::~QLibraryPrivate() -
375{ -
376 LibraryMap * const map = libraryMap();
executed (the execution status of this line is deduced): LibraryMap * const map = libraryMap();
-
377 if (map) {
partially evaluated: map
TRUEFALSE
yes
Evaluation Count:2407
no
Evaluation Count:0
0-2407
378 QLibraryPrivate *that = map->take(fileName);
executed (the execution status of this line is deduced): QLibraryPrivate *that = map->take(fileName);
-
379 Q_ASSERT(this == that);
executed (the execution status of this line is deduced): qt_noop();
-
380 Q_UNUSED(that);
executed (the execution status of this line is deduced): (void)that;;
-
381 }
executed: }
Execution Count:2407
2407
382}
executed: }
Execution Count:2407
2407
383 -
384QFunctionPointer QLibraryPrivate::resolve(const char *symbol) -
385{ -
386 if (!pHnd)
partially evaluated: !pHnd
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:3475
0-3475
387 return 0;
never executed: return 0;
0
388 return resolve_sys(symbol);
executed: return resolve_sys(symbol);
Execution Count:3475
3475
389} -
390 -
391 -
392bool QLibraryPrivate::load() -
393{ -
394 libraryUnloadCount.ref();
executed (the execution status of this line is deduced): libraryUnloadCount.ref();
-
395 if (pHnd)
evaluated: pHnd
TRUEFALSE
yes
Evaluation Count:105
yes
Evaluation Count:260
105-260
396 return true;
executed: return true;
Execution Count:105
105
397 if (fileName.isEmpty())
partially evaluated: fileName.isEmpty()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:260
0-260
398 return false;
never executed: return false;
0
399 -
400 bool ret = load_sys();
executed (the execution status of this line is deduced): bool ret = load_sys();
-
401 if (qt_debug_component())
partially evaluated: qt_debug_component()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:260
0-260
402 qDebug() << "loaded library" << fileName;
never executed: QMessageLogger("plugin/qlibrary.cpp", 402, __PRETTY_FUNCTION__).debug() << "loaded library" << fileName;
0
403 if (ret) {
evaluated: ret
TRUEFALSE
yes
Evaluation Count:253
yes
Evaluation Count:7
7-253
404 //when loading a library we add a reference to it so that the QLibraryPrivate won't get deleted -
405 //this allows to unload the library at a later time -
406 if (LibraryData *lib = libraryData()) {
partially evaluated: LibraryData *lib = libraryData()
TRUEFALSE
yes
Evaluation Count:253
no
Evaluation Count:0
0-253
407 lib->loadedLibs += this;
executed (the execution status of this line is deduced): lib->loadedLibs += this;
-
408 libraryRefCount.ref();
executed (the execution status of this line is deduced): libraryRefCount.ref();
-
409 }
executed: }
Execution Count:253
253
410 -
411 installCoverageTool(this);
executed (the execution status of this line is deduced): installCoverageTool(this);
-
412 }
executed: }
Execution Count:253
253
413 -
414 return ret;
executed: return ret;
Execution Count:260
260
415} -
416 -
417bool QLibraryPrivate::unload() -
418{ -
419 if (!pHnd)
evaluated: !pHnd
TRUEFALSE
yes
Evaluation Count:1201
yes
Evaluation Count:945
945-1201
420 return false;
executed: return false;
Execution Count:1201
1201
421 if (!libraryUnloadCount.deref()) { // only unload if ALL QLibrary instance wanted to
evaluated: !libraryUnloadCount.deref()
TRUEFALSE
yes
Evaluation Count:943
yes
Evaluation Count:2
2-943
422 delete inst.data();
executed (the execution status of this line is deduced): delete inst.data();
-
423 if (unload_sys()) {
partially evaluated: unload_sys()
TRUEFALSE
yes
Evaluation Count:943
no
Evaluation Count:0
0-943
424 if (qt_debug_component())
partially evaluated: qt_debug_component()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:943
0-943
425 qWarning() << "QLibraryPrivate::unload succeeded on" << fileName;
never executed: QMessageLogger("plugin/qlibrary.cpp", 425, __PRETTY_FUNCTION__).warning() << "QLibraryPrivate::unload succeeded on" << fileName;
0
426 //when the library is unloaded, we release the reference on it so that 'this' -
427 //can get deleted -
428 if (LibraryData *lib = libraryData()) {
partially evaluated: LibraryData *lib = libraryData()
TRUEFALSE
yes
Evaluation Count:943
no
Evaluation Count:0
0-943
429 if (lib->loadedLibs.remove(this))
partially evaluated: lib->loadedLibs.remove(this)
TRUEFALSE
yes
Evaluation Count:943
no
Evaluation Count:0
0-943
430 libraryRefCount.deref();
executed: libraryRefCount.deref();
Execution Count:943
943
431 }
executed: }
Execution Count:943
943
432 pHnd = 0;
executed (the execution status of this line is deduced): pHnd = 0;
-
433 instance = 0;
executed (the execution status of this line is deduced): instance = 0;
-
434 }
executed: }
Execution Count:943
943
435 }
executed: }
Execution Count:943
943
436 -
437 return (pHnd == 0);
executed: return (pHnd == 0);
Execution Count:945
945
438} -
439 -
440void QLibraryPrivate::release() -
441{ -
442 QMutexLocker locker(&qt_library_mutex);
executed (the execution status of this line is deduced): QMutexLocker locker(&qt_library_mutex);
-
443 if (!libraryRefCount.deref())
evaluated: !libraryRefCount.deref()
TRUEFALSE
yes
Evaluation Count:2407
yes
Evaluation Count:189
189-2407
444 delete this;
executed: delete this;
Execution Count:2407
2407
445}
executed: }
Execution Count:2596
2596
446 -
447bool QLibraryPrivate::loadPlugin() -
448{ -
449 if (instance) {
evaluated: instance
TRUEFALSE
yes
Evaluation Count:1
yes
Evaluation Count:167
1-167
450 libraryUnloadCount.ref();
executed (the execution status of this line is deduced): libraryUnloadCount.ref();
-
451 return true;
executed: return true;
Execution Count:1
1
452 } -
453 if (pluginState == IsNotAPlugin)
partially evaluated: pluginState == IsNotAPlugin
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:167
0-167
454 return false;
never executed: return false;
0
455 if (load()) {
evaluated: load()
TRUEFALSE
yes
Evaluation Count:166
yes
Evaluation Count:1
1-166
456 instance = (QtPluginInstanceFunction)resolve("qt_plugin_instance");
executed (the execution status of this line is deduced): instance = (QtPluginInstanceFunction)resolve("qt_plugin_instance");
-
457 return instance;
executed: return instance;
Execution Count:166
166
458 } -
459 if (qt_debug_component())
partially evaluated: qt_debug_component()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:1
0-1
460 qWarning() << "QLibraryPrivate::loadPlugin failed on" << fileName << ":" << errorString;
never executed: QMessageLogger("plugin/qlibrary.cpp", 460, __PRETTY_FUNCTION__).warning() << "QLibraryPrivate::loadPlugin failed on" << fileName << ":" << errorString;
0
461 pluginState = IsNotAPlugin;
executed (the execution status of this line is deduced): pluginState = IsNotAPlugin;
-
462 return false;
executed: return false;
Execution Count:1
1
463} -
464 -
465/*! -
466 Returns true if \a fileName has a valid suffix for a loadable -
467 library; otherwise returns false. -
468 -
469 \table -
470 \header \li Platform \li Valid suffixes -
471 \row \li Windows \li \c .dll, \c .DLL -
472 \row \li Unix/Linux \li \c .so -
473 \row \li AIX \li \c .a -
474 \row \li HP-UX \li \c .sl, \c .so (HP-UXi) -
475 \row \li Mac OS X \li \c .dylib, \c .bundle, \c .so -
476 \endtable -
477 -
478 Trailing versioning numbers on Unix are ignored. -
479 */ -
480bool QLibrary::isLibrary(const QString &fileName) -
481{ -
482#if defined(Q_OS_WIN32) || defined(Q_OS_WINCE) -
483 return fileName.endsWith(QLatin1String(".dll"), Qt::CaseInsensitive); -
484#else -
485 QString completeSuffix = QFileInfo(fileName).completeSuffix();
executed (the execution status of this line is deduced): QString completeSuffix = QFileInfo(fileName).completeSuffix();
-
486 if (completeSuffix.isEmpty())
partially evaluated: completeSuffix.isEmpty()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:16
0-16
487 return false;
never executed: return false;
0
488 QStringList suffixes = completeSuffix.split(QLatin1Char('.'));
executed (the execution status of this line is deduced): QStringList suffixes = completeSuffix.split(QLatin1Char('.'));
-
489# if defined(Q_OS_DARWIN) -
490 -
491 // On Mac, libs look like libmylib.1.0.0.dylib -
492 const QString lastSuffix = suffixes.at(suffixes.count() - 1); -
493 const QString firstSuffix = suffixes.at(0); -
494 -
495 bool valid = (lastSuffix == QLatin1String("dylib") -
496 || firstSuffix == QLatin1String("so") -
497 || firstSuffix == QLatin1String("bundle")); -
498 -
499 return valid; -
500# else // Generic Unix -
501 QStringList validSuffixList;
executed (the execution status of this line is deduced): QStringList validSuffixList;
-
502 -
503# if defined(Q_OS_HPUX) -
504/* -
505 See "HP-UX Linker and Libraries User's Guide", section "Link-time Differences between PA-RISC and IPF": -
506 "In PA-RISC (PA-32 and PA-64) shared libraries are suffixed with .sl. In IPF (32-bit and 64-bit), -
507 the shared libraries are suffixed with .so. For compatibility, the IPF linker also supports the .sl suffix." -
508 */ -
509 validSuffixList << QLatin1String("sl"); -
510# if defined __ia64 -
511 validSuffixList << QLatin1String("so"); -
512# endif -
513# elif defined(Q_OS_AIX) -
514 validSuffixList << QLatin1String("a") << QLatin1String("so"); -
515# elif defined(Q_OS_UNIX) -
516 validSuffixList << QLatin1String("so");
executed (the execution status of this line is deduced): validSuffixList << QLatin1String("so");
-
517# endif -
518 -
519 // Examples of valid library names: -
520 // libfoo.so -
521 // libfoo.so.0 -
522 // libfoo.so.0.3 -
523 // libfoo-0.3.so -
524 // libfoo-0.3.so.0.3.0 -
525 -
526 int suffix;
executed (the execution status of this line is deduced): int suffix;
-
527 int suffixPos = -1;
executed (the execution status of this line is deduced): int suffixPos = -1;
-
528 for (suffix = 0; suffix < validSuffixList.count() && suffixPos == -1; ++suffix)
evaluated: suffix < validSuffixList.count()
TRUEFALSE
yes
Evaluation Count:16
yes
Evaluation Count:16
partially evaluated: suffixPos == -1
TRUEFALSE
yes
Evaluation Count:16
no
Evaluation Count:0
0-16
529 suffixPos = suffixes.indexOf(validSuffixList.at(suffix));
executed: suffixPos = suffixes.indexOf(validSuffixList.at(suffix));
Execution Count:16
16
530 -
531 bool valid = suffixPos != -1;
executed (the execution status of this line is deduced): bool valid = suffixPos != -1;
-
532 for (int i = suffixPos + 1; i < suffixes.count() && valid; ++i)
evaluated: i < suffixes.count()
TRUEFALSE
yes
Evaluation Count:14
yes
Evaluation Count:8
evaluated: valid
TRUEFALSE
yes
Evaluation Count:6
yes
Evaluation Count:8
6-14
533 if (i != suffixPos)
partially evaluated: i != suffixPos
TRUEFALSE
yes
Evaluation Count:6
no
Evaluation Count:0
0-6
534 suffixes.at(i).toInt(&valid);
executed: suffixes.at(i).toInt(&valid);
Execution Count:6
6
535 return valid;
executed: return valid;
Execution Count:16
16
536# endif -
537#endif -
538 -
539} -
540 -
541#if defined (Q_OS_WIN) && defined(_MSC_VER) && _MSC_VER >= 1400 && !defined(Q_CC_INTEL) -
542#define QT_USE_MS_STD_EXCEPTION 1 -
543const char* qt_try_versioninfo(void *pfn, bool *exceptionThrown) -
544{ -
545 *exceptionThrown = false; -
546 const char *szData = 0; -
547 typedef const char * (*VerificationFunction)(); -
548 VerificationFunction func = reinterpret_cast<VerificationFunction>(pfn); -
549 __try { -
550 if(func) -
551 szData = func(); -
552 } __except(EXCEPTION_EXECUTE_HANDLER) { -
553 *exceptionThrown = true; -
554 } -
555 return szData; -
556} -
557#endif -
558 -
559typedef const char * (*QtPluginQueryVerificationDataFunction)(); -
560 -
561bool qt_get_metadata(QtPluginQueryVerificationDataFunction pfn, QLibraryPrivate *priv, bool *exceptionThrown) -
562{ -
563 *exceptionThrown = false;
never executed (the execution status of this line is deduced): *exceptionThrown = false;
-
564 const char *szData = 0;
never executed (the execution status of this line is deduced): const char *szData = 0;
-
565 if (!pfn)
never evaluated: !pfn
0
566 return false;
never executed: return false;
0
567#ifdef QT_USE_MS_STD_EXCEPTION -
568 szData = qt_try_versioninfo((void *)pfn, exceptionThrown); -
569 if (*exceptionThrown) -
570 return false; -
571#else -
572 szData = pfn();
never executed (the execution status of this line is deduced): szData = pfn();
-
573#endif -
574 if (!szData)
never evaluated: !szData
0
575 return false;
never executed: return false;
0
576 QJsonDocument doc = QLibraryPrivate::fromRawMetaData(szData);
never executed (the execution status of this line is deduced): QJsonDocument doc = QLibraryPrivate::fromRawMetaData(szData);
-
577 if (doc.isNull())
never evaluated: doc.isNull()
0
578 return false;
never executed: return false;
0
579 priv->metaData = doc.object();
never executed (the execution status of this line is deduced): priv->metaData = doc.object();
-
580 return true;
never executed: return true;
0
581} -
582 -
583bool QLibraryPrivate::isPlugin() -
584{ -
585 if (pluginState == MightBeAPlugin)
evaluated: pluginState == MightBeAPlugin
TRUEFALSE
yes
Evaluation Count:467
yes
Evaluation Count:52
52-467
586 updatePluginState();
executed: updatePluginState();
Execution Count:467
467
587 -
588 return pluginState == IsAPlugin;
executed: return pluginState == IsAPlugin;
Execution Count:519
519
589} -
590 -
591void QLibraryPrivate::updatePluginState() -
592{ -
593 errorString.clear();
executed (the execution status of this line is deduced): errorString.clear();
-
594 if (pluginState != MightBeAPlugin)
evaluated: pluginState != MightBeAPlugin
TRUEFALSE
yes
Evaluation Count:2
yes
Evaluation Count:486
2-486
595 return;
executed: return;
Execution Count:2
2
596 -
597 bool success = false;
executed (the execution status of this line is deduced): bool success = false;
-
598 -
599#if defined(Q_OS_UNIX) && !defined(Q_OS_MAC) -
600 if (fileName.endsWith(QLatin1String(".debug"))) {
partially evaluated: fileName.endsWith(QLatin1String(".debug"))
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:486
0-486
601 // refuse to load a file that ends in .debug -
602 // these are the debug symbols from the libraries -
603 // the problem is that they are valid shared library files -
604 // and dlopen is known to crash while opening them -
605 -
606 // pretend we didn't see the file -
607 errorString = QLibrary::tr("The shared library was not found.");
never executed (the execution status of this line is deduced): errorString = QLibrary::tr("The shared library was not found.");
-
608 pluginState = IsNotAPlugin;
never executed (the execution status of this line is deduced): pluginState = IsNotAPlugin;
-
609 return;
never executed: return;
0
610 } -
611#endif -
612 -
613#if defined(Q_OS_UNIX) && !defined(Q_OS_MAC) -
614 if (!pHnd) {
partially evaluated: !pHnd
TRUEFALSE
yes
Evaluation Count:486
no
Evaluation Count:0
0-486
615 // use unix shortcut to avoid loading the library -
616 success = qt_unix_query(fileName, this);
executed (the execution status of this line is deduced): success = qt_unix_query(fileName, this);
-
617 } else
executed: }
Execution Count:486
486
618#endif -
619 { -
620 bool retryLoadLibrary = false; // Only used on Windows with MS compiler.(false in other cases)
never executed (the execution status of this line is deduced): bool retryLoadLibrary = false;
-
621 do { -
622 bool temporary_load = false;
never executed (the execution status of this line is deduced): bool temporary_load = false;
-
623#ifdef Q_OS_WIN -
624 HMODULE hTempModule = 0; -
625#endif -
626 if (!pHnd) {
never evaluated: !pHnd
0
627#ifdef Q_OS_WIN -
628 DWORD dwFlags = (retryLoadLibrary) ? 0: DONT_RESOLVE_DLL_REFERENCES; -
629 //avoid 'Bad Image' message box -
630 UINT oldmode = SetErrorMode(SEM_FAILCRITICALERRORS|SEM_NOOPENFILEERRORBOX); -
631 hTempModule = ::LoadLibraryEx((wchar_t*)QDir::toNativeSeparators(fileName).utf16(), 0, dwFlags); -
632 SetErrorMode(oldmode); -
633#else -
634 temporary_load = load_sys();
never executed (the execution status of this line is deduced): temporary_load = load_sys();
-
635#endif -
636 }
never executed: }
0
637 QtPluginQueryVerificationDataFunction getMetaData = NULL;
never executed (the execution status of this line is deduced): QtPluginQueryVerificationDataFunction getMetaData = __null;
-
638 -
639 bool exceptionThrown = false;
never executed (the execution status of this line is deduced): bool exceptionThrown = false;
-
640 bool ret = false;
never executed (the execution status of this line is deduced): bool ret = false;
-
641#ifdef Q_OS_WIN -
642 if (hTempModule) { -
643 getMetaData = (QtPluginQueryVerificationDataFunction) -
644#ifdef Q_OS_WINCE -
645 ::GetProcAddress(hTempModule, L"qt_plugin_query_metadata") -
646#else -
647 ::GetProcAddress(hTempModule, "qt_plugin_query_metadata") -
648#endif -
649 ; -
650 } else -
651#endif -
652 { -
653 getMetaData = (QtPluginQueryVerificationDataFunction) resolve("qt_plugin_query_metadata");
never executed (the execution status of this line is deduced): getMetaData = (QtPluginQueryVerificationDataFunction) resolve("qt_plugin_query_metadata");
-
654 } -
655 -
656 if (getMetaData)
never evaluated: getMetaData
0
657 ret = qt_get_metadata(getMetaData, this, &exceptionThrown);
never executed: ret = qt_get_metadata(getMetaData, this, &exceptionThrown);
0
658 -
659 if (!exceptionThrown) {
never evaluated: !exceptionThrown
0
660 if (!ret) {
never evaluated: !ret
0
661 if (temporary_load)
never evaluated: temporary_load
0
662 unload_sys();
never executed: unload_sys();
0
663 } else {
never executed: }
0
664 success = true;
never executed (the execution status of this line is deduced): success = true;
-
665 }
never executed: }
0
666 retryLoadLibrary = false;
never executed (the execution status of this line is deduced): retryLoadLibrary = false;
-
667 }
never executed: }
0
668#ifdef QT_USE_MS_STD_EXCEPTION -
669 else { -
670 // An exception was thrown when calling qt_plugin_query_verification_data(). -
671 // This usually happens when plugin is compiled with the /clr compiler flag, -
672 // & will only work if the dependencies are loaded & DLLMain() is called. -
673 // LoadLibrary() will do this, try once with this & if it fails don't load. -
674 retryLoadLibrary = !retryLoadLibrary; -
675 } -
676#endif -
677#ifdef Q_OS_WIN -
678 if (hTempModule) { -
679 BOOL ok = ::FreeLibrary(hTempModule); -
680 if (ok) { -
681 hTempModule = 0; -
682 } -
683 -
684 } -
685#endif -
686 } while (retryLoadLibrary); // Will be 'false' in all cases other than when an
never executed: }
never evaluated: retryLoadLibrary
0
687 // exception is thrown(will happen only when using a MS compiler) -
688 }
never executed: }
0
689 -
690 if (!success) {
evaluated: !success
TRUEFALSE
yes
Evaluation Count:259
yes
Evaluation Count:227
227-259
691 if (errorString.isEmpty()){
partially evaluated: errorString.isEmpty()
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:259
0-259
692 if (fileName.isEmpty())
never evaluated: fileName.isEmpty()
0
693 errorString = QLibrary::tr("The shared library was not found.");
never executed: errorString = QLibrary::tr("The shared library was not found.");
0
694 else -
695 errorString = QLibrary::tr("The file '%1' is not a valid Qt plugin.").arg(fileName);
never executed: errorString = QLibrary::tr("The file '%1' is not a valid Qt plugin.").arg(fileName);
0
696 } -
697 pluginState = IsNotAPlugin;
executed (the execution status of this line is deduced): pluginState = IsNotAPlugin;
-
698 return;
executed: return;
Execution Count:259
259
699 } -
700 -
701 pluginState = IsNotAPlugin; // be pessimistic
executed (the execution status of this line is deduced): pluginState = IsNotAPlugin;
-
702 -
703 uint qt_version = (uint)metaData.value(QLatin1String("version")).toDouble();
executed (the execution status of this line is deduced): uint qt_version = (uint)metaData.value(QLatin1String("version")).toDouble();
-
704 bool debug = metaData.value(QLatin1String("debug")).toBool();
executed (the execution status of this line is deduced): bool debug = metaData.value(QLatin1String("debug")).toBool();
-
705 if ((qt_version & 0x00ff00) > (QT_VERSION & 0x00ff00) || (qt_version & 0xff0000) != (QT_VERSION & 0xff0000)) {
partially evaluated: (qt_version & 0x00ff00) > (0x050002 & 0x00ff00)
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
partially evaluated: (qt_version & 0xff0000) != (0x050002 & 0xff0000)
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:227
0-227
706 if (qt_debug_component()) {
never evaluated: qt_debug_component()
0
707 qWarning("In %s:\n"
never executed (the execution status of this line is deduced): QMessageLogger("plugin/qlibrary.cpp", 707, __PRETTY_FUNCTION__).warning("In %s:\n"
-
708 " Plugin uses incompatible Qt library (%d.%d.%d) [%s]",
never executed (the execution status of this line is deduced): " Plugin uses incompatible Qt library (%d.%d.%d) [%s]",
-
709 (const char*) QFile::encodeName(fileName),
never executed (the execution status of this line is deduced): (const char*) QFile::encodeName(fileName),
-
710 (qt_version&0xff0000) >> 16, (qt_version&0xff00) >> 8, qt_version&0xff,
never executed (the execution status of this line is deduced): (qt_version&0xff0000) >> 16, (qt_version&0xff00) >> 8, qt_version&0xff,
-
711 debug ? "debug" : "release");
never executed (the execution status of this line is deduced): debug ? "debug" : "release");
-
712 }
never executed: }
0
713 errorString = QLibrary::tr("The plugin '%1' uses incompatible Qt library. (%2.%3.%4) [%5]")
never executed (the execution status of this line is deduced): errorString = QLibrary::tr("The plugin '%1' uses incompatible Qt library. (%2.%3.%4) [%5]")
-
714 .arg(fileName)
never executed (the execution status of this line is deduced): .arg(fileName)
-
715 .arg((qt_version&0xff0000) >> 16)
never executed (the execution status of this line is deduced): .arg((qt_version&0xff0000) >> 16)
-
716 .arg((qt_version&0xff00) >> 8)
never executed (the execution status of this line is deduced): .arg((qt_version&0xff00) >> 8)
-
717 .arg(qt_version&0xff)
never executed (the execution status of this line is deduced): .arg(qt_version&0xff)
-
718 .arg(debug ? QLatin1String("debug") : QLatin1String("release"));
never executed (the execution status of this line is deduced): .arg(debug ? QLatin1String("debug") : QLatin1String("release"));
-
719#ifndef QT_NO_DEBUG_PLUGIN_CHECK -
720 } else if(debug != QLIBRARY_AS_DEBUG) { -
721 //don't issue a qWarning since we will hopefully find a non-debug? --Sam -
722 errorString = QLibrary::tr("The plugin '%1' uses incompatible Qt library." -
723 " (Cannot mix debug and release libraries.)").arg(fileName); -
724#endif -
725 } else {
never executed: }
0
726 pluginState = IsAPlugin;
executed (the execution status of this line is deduced): pluginState = IsAPlugin;
-
727 }
executed: }
Execution Count:227
227
728} -
729 -
730/*! -
731 Loads the library and returns true if the library was loaded -
732 successfully; otherwise returns false. Since resolve() always -
733 calls this function before resolving any symbols it is not -
734 necessary to call it explicitly. In some situations you might want -
735 the library loaded in advance, in which case you would use this -
736 function. -
737 -
738 \sa unload() -
739*/ -
740bool QLibrary::load() -
741{ -
742 if (!d)
evaluated: !d
TRUEFALSE
yes
Evaluation Count:1
yes
Evaluation Count:198
1-198
743 return false;
executed: return false;
Execution Count:1
1
744 if (did_load)
partially evaluated: did_load
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:198
0-198
745 return d->pHnd;
never executed: return d->pHnd;
0
746 did_load = true;
executed (the execution status of this line is deduced): did_load = true;
-
747 return d->load();
executed: return d->load();
Execution Count:198
198
748} -
749 -
750/*! -
751 Unloads the library and returns true if the library could be -
752 unloaded; otherwise returns false. -
753 -
754 This happens automatically on application termination, so you -
755 shouldn't normally need to call this function. -
756 -
757 If other instances of QLibrary are using the same library, the -
758 call will fail, and unloading will only happen when every instance -
759 has called unload(). -
760 -
761 Note that on Mac OS X 10.3 (Panther), dynamic libraries cannot be unloaded. -
762 -
763 \sa resolve(), load() -
764*/ -
765bool QLibrary::unload() -
766{ -
767 if (did_load) {
evaluated: did_load
TRUEFALSE
yes
Evaluation Count:221
yes
Evaluation Count:26
26-221
768 did_load = false;
executed (the execution status of this line is deduced): did_load = false;
-
769 return d->unload();
executed: return d->unload();
Execution Count:221
221
770 } -
771 return false;
executed: return false;
Execution Count:26
26
772} -
773 -
774/*! -
775 Returns true if the library is loaded; otherwise returns false. -
776 -
777 \sa load() -
778 */ -
779bool QLibrary::isLoaded() const -
780{ -
781 return d && d->pHnd;
executed: return d && d->pHnd;
Execution Count:7621
7621
782} -
783 -
784 -
785/*! -
786 Constructs a library with the given \a parent. -
787 */ -
788QLibrary::QLibrary(QObject *parent) -
789 :QObject(parent), d(0), did_load(false) -
790{ -
791}
executed: }
Execution Count:51
51
792 -
793 -
794/*! -
795 Constructs a library object with the given \a parent that will -
796 load the library specified by \a fileName. -
797 -
798 We recommend omitting the file's suffix in \a fileName, since -
799 QLibrary will automatically look for the file with the appropriate -
800 suffix in accordance with the platform, e.g. ".so" on Unix, -
801 ".dylib" on Mac OS X, and ".dll" on Windows. (See \l{fileName}.) -
802 */ -
803QLibrary::QLibrary(const QString& fileName, QObject *parent) -
804 :QObject(parent), d(0), did_load(false) -
805{ -
806 setFileName(fileName);
executed (the execution status of this line is deduced): setFileName(fileName);
-
807}
executed: }
Execution Count:31
31
808 -
809 -
810/*! -
811 Constructs a library object with the given \a parent that will -
812 load the library specified by \a fileName and major version number \a verNum. -
813 Currently, the version number is ignored on Windows. -
814 -
815 We recommend omitting the file's suffix in \a fileName, since -
816 QLibrary will automatically look for the file with the appropriate -
817 suffix in accordance with the platform, e.g. ".so" on Unix, -
818 ".dylib" on Mac OS X, and ".dll" on Windows. (See \l{fileName}.) -
819*/ -
820QLibrary::QLibrary(const QString& fileName, int verNum, QObject *parent) -
821 :QObject(parent), d(0), did_load(false) -
822{ -
823 setFileNameAndVersion(fileName, verNum);
executed (the execution status of this line is deduced): setFileNameAndVersion(fileName, verNum);
-
824}
executed: }
Execution Count:125
125
825 -
826/*! -
827 Constructs a library object with the given \a parent that will -
828 load the library specified by \a fileName and full version number \a version. -
829 Currently, the version number is ignored on Windows. -
830 -
831 We recommend omitting the file's suffix in \a fileName, since -
832 QLibrary will automatically look for the file with the appropriate -
833 suffix in accordance with the platform, e.g. ".so" on Unix, -
834 ".dylib" on Mac OS X, and ".dll" on Windows. (See \l{fileName}.) -
835 */ -
836QLibrary::QLibrary(const QString& fileName, const QString &version, QObject *parent) -
837 :QObject(parent), d(0), did_load(false) -
838{ -
839 setFileNameAndVersion(fileName, version);
never executed (the execution status of this line is deduced): setFileNameAndVersion(fileName, version);
-
840}
never executed: }
0
841 -
842/*! -
843 Destroys the QLibrary object. -
844 -
845 Unless unload() was called explicitly, the library stays in memory -
846 until the application terminates. -
847 -
848 \sa isLoaded(), unload() -
849*/ -
850QLibrary::~QLibrary() -
851{ -
852 if (d)
evaluated: d
TRUEFALSE
yes
Evaluation Count:376
yes
Evaluation Count:1
1-376
853 d->release();
executed: d->release();
Execution Count:376
376
854}
executed: }
Execution Count:377
377
855 -
856 -
857/*! -
858 \property QLibrary::fileName -
859 \brief the file name of the library -
860 -
861 We recommend omitting the file's suffix in the file name, since -
862 QLibrary will automatically look for the file with the appropriate -
863 suffix (see isLibrary()). -
864 -
865 When loading the library, QLibrary searches in all system-specific -
866 library locations (e.g. \c LD_LIBRARY_PATH on Unix), unless the -
867 file name has an absolute path. After loading the library -
868 successfully, fileName() returns the fully-qualified file name of -
869 the library, including the full path to the library if one was given -
870 in the constructor or passed to setFileName(). -
871 -
872 For example, after successfully loading the "GL" library on Unix -
873 platforms, fileName() will return "libGL.so". If the file name was -
874 originally passed as "/usr/lib/libGL", fileName() will return -
875 "/usr/lib/libGL.so". -
876*/ -
877 -
878void QLibrary::setFileName(const QString &fileName) -
879{ -
880 QLibrary::LoadHints lh;
executed (the execution status of this line is deduced): QLibrary::LoadHints lh;
-
881 if (d) {
evaluated: d
TRUEFALSE
yes
Evaluation Count:3
yes
Evaluation Count:60
3-60
882 lh = d->loadHints;
executed (the execution status of this line is deduced): lh = d->loadHints;
-
883 d->release();
executed (the execution status of this line is deduced): d->release();
-
884 d = 0;
executed (the execution status of this line is deduced): d = 0;
-
885 did_load = false;
executed (the execution status of this line is deduced): did_load = false;
-
886 }
executed: }
Execution Count:3
3
887 d = QLibraryPrivate::findOrCreate(fileName);
executed (the execution status of this line is deduced): d = QLibraryPrivate::findOrCreate(fileName);
-
888 d->loadHints = lh;
executed (the execution status of this line is deduced): d->loadHints = lh;
-
889}
executed: }
Execution Count:63
63
890 -
891QString QLibrary::fileName() const -
892{ -
893 if (d)
partially evaluated: d
TRUEFALSE
yes
Evaluation Count:26
no
Evaluation Count:0
0-26
894 return d->qualifiedFileName.isEmpty() ? d->fileName : d->qualifiedFileName;
executed: return d->qualifiedFileName.isEmpty() ? d->fileName : d->qualifiedFileName;
Execution Count:26
26
895 return QString();
never executed: return QString();
0
896} -
897 -
898/*! -
899 \fn void QLibrary::setFileNameAndVersion(const QString &fileName, int versionNumber) -
900 -
901 Sets the fileName property and major version number to \a fileName -
902 and \a versionNumber respectively. -
903 The \a versionNumber is ignored on Windows. -
904 -
905 \sa setFileName() -
906*/ -
907void QLibrary::setFileNameAndVersion(const QString &fileName, int verNum) -
908{ -
909 QLibrary::LoadHints lh;
executed (the execution status of this line is deduced): QLibrary::LoadHints lh;
-
910 if (d) {
evaluated: d
TRUEFALSE
yes
Evaluation Count:25
yes
Evaluation Count:125
25-125
911 lh = d->loadHints;
executed (the execution status of this line is deduced): lh = d->loadHints;
-
912 d->release();
executed (the execution status of this line is deduced): d->release();
-
913 d = 0;
executed (the execution status of this line is deduced): d = 0;
-
914 did_load = false;
executed (the execution status of this line is deduced): did_load = false;
-
915 }
executed: }
Execution Count:25
25
916 d = QLibraryPrivate::findOrCreate(fileName, verNum >= 0 ? QString::number(verNum) : QString());
executed (the execution status of this line is deduced): d = QLibraryPrivate::findOrCreate(fileName, verNum >= 0 ? QString::number(verNum) : QString());
-
917 d->loadHints = lh;
executed (the execution status of this line is deduced): d->loadHints = lh;
-
918}
executed: }
Execution Count:150
150
919 -
920/*! -
921 \since 4.4 -
922 -
923 Sets the fileName property and full version number to \a fileName -
924 and \a version respectively. -
925 The \a version parameter is ignored on Windows. -
926 -
927 \sa setFileName() -
928*/ -
929void QLibrary::setFileNameAndVersion(const QString &fileName, const QString &version) -
930{ -
931 QLibrary::LoadHints lh;
executed (the execution status of this line is deduced): QLibrary::LoadHints lh;
-
932 if (d) {
partially evaluated: d
TRUEFALSE
no
Evaluation Count:0
yes
Evaluation Count:18
0-18
933 lh = d->loadHints;
never executed (the execution status of this line is deduced): lh = d->loadHints;
-
934 d->release();
never executed (the execution status of this line is deduced): d->release();
-
935 d = 0;
never executed (the execution status of this line is deduced): d = 0;
-
936 did_load = false;
never executed (the execution status of this line is deduced): did_load = false;
-
937 }
never executed: }
0
938 d = QLibraryPrivate::findOrCreate(fileName, version);
executed (the execution status of this line is deduced): d = QLibraryPrivate::findOrCreate(fileName, version);
-
939 d->loadHints = lh;
executed (the execution status of this line is deduced): d->loadHints = lh;
-
940}
executed: }
Execution Count:18
18
941 -
942/*! -
943 Returns the address of the exported symbol \a symbol. The library is -
944 loaded if necessary. The function returns 0 if the symbol could -
945 not be resolved or if the library could not be loaded. -
946 -
947 Example: -
948 \snippet code/src_corelib_plugin_qlibrary.cpp 2 -
949 -
950 The symbol must be exported as a C function from the library. This -
951 means that the function must be wrapped in an \c{extern "C"} if -
952 the library is compiled with a C++ compiler. On Windows you must -
953 also explicitly export the function from the DLL using the -
954 \c{__declspec(dllexport)} compiler directive, for example: -
955 -
956 \snippet code/src_corelib_plugin_qlibrary.cpp 3 -
957 -
958 with \c MY_EXPORT defined as -
959 -
960 \snippet code/src_corelib_plugin_qlibrary.cpp 4 -
961*/ -
962QFunctionPointer QLibrary::resolve(const char *symbol) -
963{ -
964 if (!isLoaded() && !load())
evaluated: !isLoaded()
TRUEFALSE
yes
Evaluation Count:11
yes
Evaluation Count:3299
evaluated: !load()
TRUEFALSE
yes
Evaluation Count:1
yes
Evaluation Count:10
1-3299
965 return 0;
executed: return 0;
Execution Count:1
1
966 return d->resolve(symbol);
executed: return d->resolve(symbol);
Execution Count:3309
3309
967} -
968 -
969/*! -
970 \overload -
971 -
972 Loads the library \a fileName and returns the address of the -
973 exported symbol \a symbol. Note that \a fileName should not -
974 include the platform-specific file suffix; (see \l{fileName}). The -
975 library remains loaded until the application exits. -
976 -
977 The function returns 0 if the symbol could not be resolved or if -
978 the library could not be loaded. -
979 -
980 \sa resolve() -
981*/ -
982QFunctionPointer QLibrary::resolve(const QString &fileName, const char *symbol) -
983{ -
984 QLibrary library(fileName);
never executed (the execution status of this line is deduced): QLibrary library(fileName);
-
985 return library.resolve(symbol);
never executed: return library.resolve(symbol);
0
986} -
987 -
988/*! -
989 \overload -
990 -
991 Loads the library \a fileName with major version number \a verNum and -
992 returns the address of the exported symbol \a symbol. -
993 Note that \a fileName should not include the platform-specific file suffix; -
994 (see \l{fileName}). The library remains loaded until the application exits. -
995 \a verNum is ignored on Windows. -
996 -
997 The function returns 0 if the symbol could not be resolved or if -
998 the library could not be loaded. -
999 -
1000 \sa resolve() -
1001*/ -
1002QFunctionPointer QLibrary::resolve(const QString &fileName, int verNum, const char *symbol) -
1003{ -
1004 QLibrary library(fileName, verNum);
executed (the execution status of this line is deduced): QLibrary library(fileName, verNum);
-
1005 return library.resolve(symbol);
executed: return library.resolve(symbol);
Execution Count:11
11
1006} -
1007 -
1008/*! -
1009 \overload -
1010 \since 4.4 -
1011 -
1012 Loads the library \a fileName with full version number \a version and -
1013 returns the address of the exported symbol \a symbol. -
1014 Note that \a fileName should not include the platform-specific file suffix; -
1015 (see \l{fileName}). The library remains loaded until the application exits. -
1016 \a version is ignored on Windows. -
1017 -
1018 The function returns 0 if the symbol could not be resolved or if -
1019 the library could not be loaded. -
1020 -
1021 \sa resolve() -
1022*/ -
1023QFunctionPointer QLibrary::resolve(const QString &fileName, const QString &version, const char *symbol) -
1024{ -
1025 QLibrary library(fileName, version);
never executed (the execution status of this line is deduced): QLibrary library(fileName, version);
-
1026 return library.resolve(symbol);
never executed: return library.resolve(symbol);
0
1027} -
1028 -
1029/*! -
1030 \since 4.2 -
1031 -
1032 Returns a text string with the description of the last error that occurred. -
1033 Currently, errorString will only be set if load(), unload() or resolve() for some reason fails. -
1034*/ -
1035QString QLibrary::errorString() const -
1036{ -
1037 return (!d || d->errorString.isEmpty()) ? tr("Unknown error") : d->errorString;
executed: return (!d || d->errorString.isEmpty()) ? tr("Unknown error") : d->errorString;
Execution Count:21
21
1038} -
1039 -
1040/*! -
1041 \property QLibrary::loadHints -
1042 \brief Give the load() function some hints on how it should behave. -
1043 -
1044 You can give some hints on how the symbols are resolved. Usually, -
1045 the symbols are not resolved at load time, but resolved lazily, -
1046 (that is, when resolve() is called). If you set the loadHint to -
1047 ResolveAllSymbolsHint, then all symbols will be resolved at load time -
1048 if the platform supports it. -
1049 -
1050 Setting ExportExternalSymbolsHint will make the external symbols in the -
1051 library available for resolution in subsequent loaded libraries. -
1052 -
1053 If LoadArchiveMemberHint is set, the file name -
1054 is composed of two components: A path which is a reference to an -
1055 archive file followed by the second component which is the reference to -
1056 the archive member. For instance, the fileName \c libGL.a(shr_64.o) will refer -
1057 to the library \c shr_64.o in the archive file named \c libGL.a. This -
1058 is only supported on the AIX platform. -
1059 -
1060 Setting PreventUnloadHint will only apply on Unix platforms. -
1061 -
1062 The interpretation of the load hints is platform dependent, and if -
1063 you use it you are probably making some assumptions on which platform -
1064 you are compiling for, so use them only if you understand the consequences -
1065 of them. -
1066 -
1067 By default, none of these flags are set, so libraries will be loaded with -
1068 lazy symbol resolution, and will not export external symbols for resolution -
1069 in other dynamically-loaded libraries. -
1070*/ -
1071void QLibrary::setLoadHints(LoadHints hints) -
1072{ -
1073 if (!d) {
partially evaluated: !d
TRUEFALSE
yes
Evaluation Count:3
no
Evaluation Count:0
0-3
1074 d = QLibraryPrivate::findOrCreate(QString()); // ugly, but we need a d-ptr
executed (the execution status of this line is deduced): d = QLibraryPrivate::findOrCreate(QString());
-
1075 d->errorString.clear();
executed (the execution status of this line is deduced): d->errorString.clear();
-
1076 }
executed: }
Execution Count:3
3
1077 d->loadHints = hints;
executed (the execution status of this line is deduced): d->loadHints = hints;
-
1078}
executed: }
Execution Count:3
3
1079 -
1080QLibrary::LoadHints QLibrary::loadHints() const -
1081{ -
1082 return d ? d->loadHints : (QLibrary::LoadHints)0;
executed: return d ? d->loadHints : (QLibrary::LoadHints)0;
Execution Count:6
6
1083} -
1084 -
1085/* Internal, for debugging */ -
1086bool qt_debug_component() -
1087{ -
1088 static int debug_env = -1; -
1089 if (debug_env == -1)
evaluated: debug_env == -1
TRUEFALSE
yes
Evaluation Count:44
yes
Evaluation Count:2896
44-2896
1090 debug_env = QT_PREPEND_NAMESPACE(qgetenv)("QT_DEBUG_PLUGINS").toInt();
executed: debug_env = ::qgetenv("QT_DEBUG_PLUGINS").toInt();
Execution Count:44
44
1091 -
1092 return debug_env != 0;
executed: return debug_env != 0;
Execution Count:2940
2940
1093} -
1094 -
1095QT_END_NAMESPACE -
1096 -
1097#endif // QT_NO_LIBRARY -
1098 -
Source codeSwitch to Preprocessed file

Generated by Squish Coco Non-Commercial