aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorGunnar Sletta <gunnar.sletta@jollamobile.com>2014-07-01 14:48:07 +0200
committerGunnar Sletta <gunnar.sletta@jollamobile.com>2014-07-04 08:44:06 +0200
commit48d93e0d854b3f9a2486a2393fee38496fd57bd9 (patch)
tree962a1a3fdb7a63653de15ba2cd0706209534a120 /src
parentf4a1a9be39fd59e38231544c84e4b931f42b8de4 (diff)
Avoid race condition in QQmlEngine on shutdown.
The QQmlTypeLoader was deleted (and its thread shut down) when the QQmlEnginePrivate was destroyed. However, the QQmlTypeLoader runs a thread which would happiliy make calls on the engine and its managed data. Fix this by stopping the QQmlTypeLoader's thread right away in QQmlEngine. Task-number: QTBUG-39905 Change-Id: Ida8e95d083f79237c74b036fd3521133a9fa4ac7 Reviewed-by: Erik Verbruggen <erik.verbruggen@digia.com>
Diffstat (limited to 'src')
-rw-r--r--src/qml/qml/qqmlengine.cpp2
-rw-r--r--src/qml/qml/qqmltypeloader.cpp15
-rw-r--r--src/qml/qml/qqmltypeloader_p.h1
3 files changed, 15 insertions, 3 deletions
diff --git a/src/qml/qml/qqmlengine.cpp b/src/qml/qml/qqmlengine.cpp
index 17e5c55efb..46fc3292c7 100644
--- a/src/qml/qml/qqmlengine.cpp
+++ b/src/qml/qml/qqmlengine.cpp
@@ -904,6 +904,8 @@ QQmlEngine::~QQmlEngine()
if (d->isDebugging)
QQmlDebugServer::instance()->removeEngine(this);
+ d->typeLoader.invalidate();
+
// Emit onDestruction signals for the root context before
// we destroy the contexts, engine, Singleton Types etc. that
// may be required to handle the destruction signal.
diff --git a/src/qml/qml/qqmltypeloader.cpp b/src/qml/qml/qqmltypeloader.cpp
index 1afc5bbb8c..c5a4d65725 100644
--- a/src/qml/qml/qqmltypeloader.cpp
+++ b/src/qml/qml/qqmltypeloader.cpp
@@ -897,11 +897,20 @@ QQmlDataLoader::QQmlDataLoader(QQmlEngine *engine)
/*! \internal */
QQmlDataLoader::~QQmlDataLoader()
{
+ invalidate();
+}
+
+void QQmlDataLoader::invalidate()
+{
for (NetworkReplies::Iterator iter = m_networkReplies.begin(); iter != m_networkReplies.end(); ++iter)
(*iter)->release();
+ m_networkReplies.clear();
- shutdownThread();
- delete m_thread;
+ if (m_thread) {
+ shutdownThread();
+ delete m_thread;
+ m_thread = 0;
+ }
}
void QQmlDataLoader::lock()
@@ -1228,7 +1237,7 @@ void QQmlDataLoader::setCachedUnit(QQmlDataBlob *blob, const QQmlPrivate::Cached
void QQmlDataLoader::shutdownThread()
{
- if (!m_thread->isShutdown())
+ if (m_thread && !m_thread->isShutdown())
m_thread->shutdown();
}
diff --git a/src/qml/qml/qqmltypeloader_p.h b/src/qml/qml/qqmltypeloader_p.h
index b09ac15861..3d0b77e2a5 100644
--- a/src/qml/qml/qqmltypeloader_p.h
+++ b/src/qml/qml/qqmltypeloader_p.h
@@ -233,6 +233,7 @@ public:
QQmlEngine *engine() const;
void initializeEngine(QQmlExtensionInterface *, const char *);
+ void invalidate();
protected:
void shutdownThread();