summaryrefslogtreecommitdiffstats
path: root/src/corelib/thread
diff options
context:
space:
mode:
authorRohan McGovern <rohan.mcgovern@nokia.com>2012-02-29 09:18:59 +1000
committerRohan McGovern <rohan.mcgovern@nokia.com>2012-02-29 09:23:14 +1000
commit98dd1781d9256f68025d2a2db408f4f5947f3214 (patch)
treedbe1424abd90014edb5546c920ca585ed62b46e3 /src/corelib/thread
parent6c1bdc1854a7700c2b3a345b95f6a2fdca84037d (diff)
parentfa1b9070af66edb81b2a3735c1951f78b22bd666 (diff)
Merge master -> api_changes
Includes fixes for tst_qfiledialog2, tst_qtextedit autotests on mac. Change-Id: I49cac26894d31291a8339ccc1eb80b6a940f0827
Diffstat (limited to 'src/corelib/thread')
-rw-r--r--src/corelib/thread/qthread.cpp9
-rw-r--r--src/corelib/thread/qthread.h2
-rw-r--r--src/corelib/thread/qthread_p.h17
-rw-r--r--src/corelib/thread/qthread_win.cpp27
4 files changed, 48 insertions, 7 deletions
diff --git a/src/corelib/thread/qthread.cpp b/src/corelib/thread/qthread.cpp
index be0a98d3b5..a071463178 100644
--- a/src/corelib/thread/qthread.cpp
+++ b/src/corelib/thread/qthread.cpp
@@ -763,5 +763,14 @@ void QThread::setEventDispatcher(QAbstractEventDispatcher *eventDispatcher)
}
}
+bool QThread::event(QEvent *event)
+{
+ if (event->type() == QEvent::Quit) {
+ quit();
+ return true;
+ } else {
+ return QObject::event(event);
+ }
+}
QT_END_NAMESPACE
diff --git a/src/corelib/thread/qthread.h b/src/corelib/thread/qthread.h
index 719f4afbbb..ba119afb5d 100644
--- a/src/corelib/thread/qthread.h
+++ b/src/corelib/thread/qthread.h
@@ -95,6 +95,8 @@ public:
QAbstractEventDispatcher *eventDispatcher() const;
void setEventDispatcher(QAbstractEventDispatcher *eventDispatcher);
+ bool event(QEvent *event);
+
public Q_SLOTS:
void start(Priority = InheritPriority);
void terminate();
diff --git a/src/corelib/thread/qthread_p.h b/src/corelib/thread/qthread_p.h
index d8374e9805..6597b56893 100644
--- a/src/corelib/thread/qthread_p.h
+++ b/src/corelib/thread/qthread_p.h
@@ -60,6 +60,7 @@
#include "QtCore/qstack.h"
#include "QtCore/qwaitcondition.h"
#include "QtCore/qmap.h"
+#include "QtCore/qcoreapplication.h"
#include "private/qobject_p.h"
@@ -144,6 +145,7 @@ public:
~QThreadPrivate();
mutable QMutex mutex;
+ QAtomicInt quitLockRef;
bool running;
bool finished;
@@ -179,6 +181,18 @@ public:
QThreadData *data;
static void createEventDispatcher(QThreadData *data);
+
+ void ref()
+ {
+ quitLockRef.ref();
+ }
+
+ void deref()
+ {
+ if (!quitLockRef.deref() && running) {
+ QCoreApplication::instance()->postEvent(q_ptr, new QEvent(QEvent::Quit));
+ }
+ }
};
#else // QT_NO_THREAD
@@ -195,6 +209,9 @@ public:
static QThread *threadForId(int) { return QThread::currentThread(); }
static void createEventDispatcher(QThreadData *data);
+ void ref() {}
+ void deref() {}
+
Q_DECLARE_PUBLIC(QThread)
};
diff --git a/src/corelib/thread/qthread_win.cpp b/src/corelib/thread/qthread_win.cpp
index afcfb2c949..38fb6ef8dd 100644
--- a/src/corelib/thread/qthread_win.cpp
+++ b/src/corelib/thread/qthread_win.cpp
@@ -72,7 +72,7 @@
QT_BEGIN_NAMESPACE
void qt_watch_adopted_thread(const HANDLE adoptedThreadHandle, QThread *qthread);
-void qt_adopted_thread_watcher_function(void *);
+DWORD WINAPI qt_adopted_thread_watcher_function(LPVOID);
static DWORD qt_current_thread_data_tls_index = TLS_OUT_OF_INDEXES;
void qt_create_tls()
@@ -147,7 +147,7 @@ void QAdoptedThread::init()
static QVector<HANDLE> qt_adopted_thread_handles;
static QVector<QThread *> qt_adopted_qthreads;
static QMutex qt_adopted_thread_watcher_mutex;
-static HANDLE qt_adopted_thread_watcher_handle = 0;
+static DWORD qt_adopted_thread_watcher_id = 0;
static HANDLE qt_adopted_thread_wakeup = 0;
/*! \internal
@@ -158,18 +158,25 @@ static HANDLE qt_adopted_thread_wakeup = 0;
void qt_watch_adopted_thread(const HANDLE adoptedThreadHandle, QThread *qthread)
{
QMutexLocker lock(&qt_adopted_thread_watcher_mutex);
+
+ if (GetCurrentThreadId() == qt_adopted_thread_watcher_id) {
+#if !defined(Q_OS_WINCE) || (defined(_WIN32_WCE) && (_WIN32_WCE>=0x600))
+ CloseHandle(adoptedThreadHandle);
+#endif
+ return;
+ }
+
qt_adopted_thread_handles.append(adoptedThreadHandle);
qt_adopted_qthreads.append(qthread);
// Start watcher thread if it is not already running.
- if (qt_adopted_thread_watcher_handle == 0) {
+ if (qt_adopted_thread_watcher_id == 0) {
if (qt_adopted_thread_wakeup == 0) {
qt_adopted_thread_wakeup = CreateEvent(0, false, false, 0);
qt_adopted_thread_handles.prepend(qt_adopted_thread_wakeup);
}
- qt_adopted_thread_watcher_handle =
- (HANDLE)_beginthread(qt_adopted_thread_watcher_function, 0, NULL);
+ CreateThread(0, 0, qt_adopted_thread_watcher_function, 0, 0, &qt_adopted_thread_watcher_id);
} else {
SetEvent(qt_adopted_thread_wakeup);
}
@@ -180,13 +187,13 @@ void qt_watch_adopted_thread(const HANDLE adoptedThreadHandle, QThread *qthread)
When this happens it derefs the QThreadData for the adopted thread
to make sure it gets cleaned up properly.
*/
-void qt_adopted_thread_watcher_function(void *)
+DWORD WINAPI qt_adopted_thread_watcher_function(LPVOID)
{
forever {
qt_adopted_thread_watcher_mutex.lock();
if (qt_adopted_thread_handles.count() == 1) {
- qt_adopted_thread_watcher_handle = 0;
+ qt_adopted_thread_watcher_id = 0;
qt_adopted_thread_watcher_mutex.unlock();
break;
}
@@ -244,6 +251,12 @@ void qt_adopted_thread_watcher_function(void *)
qt_adopted_qthreads.remove(qthreadIndex);
}
}
+
+ QThreadData *threadData = reinterpret_cast<QThreadData *>(TlsGetValue(qt_current_thread_data_tls_index));
+ if (threadData)
+ threadData->deref();
+
+ return 0;
}
#if !defined(QT_NO_DEBUG) && defined(Q_CC_MSVC) && !defined(Q_OS_WINCE)