Improve Cocoa platform plugin loading.

Loading both the debug and release version of the cocoa
plugins causes the objective-c runtime to print "duplicate
class definitions" warnings.

Fix this by directing the plugin loader to only load
one of the cocoa plugins if both are available. Implement
this as a special case directly in QFactoryLoader.

Define QT_NO_DEBUG_PLUGIN_CHECK to allow mixing
debug and release builds.

Task-number: QTBUG-28155

Change-Id: Ie1927b219cc501a821f91b7e4b56f0589e0acbf5
Reviewed-by: Lars Knoll <lars.knoll@digia.com>
Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
This commit is contained in:
Morten Johan Sorvig 2012-12-10 11:29:54 +01:00 committed by The Qt Project
parent 4955cd8539
commit 968b117375
4 changed files with 22 additions and 9 deletions

View File

@ -41,7 +41,6 @@ mac|darwin {
}
LIBS_PRIVATE += -framework CoreFoundation
}
mac:lib_bundle:DEFINES += QT_NO_DEBUG_PLUGIN_CHECK
win32:DEFINES-=QT_NO_CAST_TO_ASCII
DEFINES += $$MODULE_DEFINES

View File

@ -126,9 +126,30 @@ void QFactoryLoader::update()
QStringList plugins = QDir(path).entryList(QDir::Files);
QLibraryPrivate *library = 0;
#ifdef Q_OS_MAC
// Loading both the debug and release version of the cocoa plugins causes the objective-c runtime
// to print "duplicate class definitions" warnings. Detect if QFactoryLoader is about to load both,
// skip one of them (below).
//
// ### FIXME find a proper solution
//
const bool isLoadingDebugAndReleaseCocoa = plugins.contains("libqcocoa_debug.dylib") && plugins.contains("libqcocoa.dylib");
#endif
for (int j = 0; j < plugins.count(); ++j) {
QString fileName = QDir::cleanPath(path + QLatin1Char('/') + plugins.at(j));
#ifdef Q_OS_MAC
if (isLoadingDebugAndReleaseCocoa) {
#ifdef QT_DEBUG
if (fileName.contains(QStringLiteral("libqcocoa.dylib")))
continue; // Skip release plugin in debug mode
#else
if (fileName.contains(QStringLiteral("libqcocoa_debug.dylib")))
continue; // Skip debug plugin in release mode
#endif
}
#endif
if (qt_debug_component()) {
qDebug() << "QFactoryLoader::QFactoryLoader() looking at" << fileName;
}

View File

@ -73,7 +73,7 @@ QT_BEGIN_NAMESPACE
# define QLIBRARY_AS_DEBUG true
#endif
#if defined(Q_OS_UNIX) && !defined(Q_OS_MAC)
#if defined(Q_OS_UNIX)
// We don't use separate debug and release libs on UNIX, so we want
// to allow loading plugins, regardless of how they were built.
# define QT_NO_DEBUG_PLUGIN_CHECK

View File

@ -98,13 +98,6 @@ QT += core-private gui-private platformsupport-private
OTHER_FILES += cocoa.json
# Build the release libqcocoa.dylib only, skip the debug version.
# The Qt plugin loader will dlopen both if found, causing duplicate
# Objective-c class definitions for the classes defined in the plugin.
contains(QT_CONFIG,release):CONFIG -= debug
contains(QT_CONFIG,debug_and_release):CONFIG -= debug_and_release
contains(QT_CONFIG,build_all):CONFIG -= build_all
# Acccessibility debug support
# DEFINES += QT_COCOA_ENABLE_ACCESSIBILITY_INSPECTOR
# include ($$PWD/../../../../util/accessibilityinspector/accessibilityinspector.pri)