diff options
author | Thiago Macieira <thiago.macieira@intel.com> | 2017-10-16 22:31:42 -0700 |
---|---|---|
committer | Friedemann Kleint <Friedemann.Kleint@qt.io> | 2017-10-27 20:00:27 +0000 |
commit | cf2220385506fe9f94ef1dbfa43518e489e04155 (patch) | |
tree | d9b409d8e5a19e12a58e7ded5992a5ce7fa9ebc8 /src | |
parent | efb1a13282ec0d09326b0550df67b7b8e7e9a31e (diff) |
Add a comment about the weird refcount for adopted QThreadData
It's perfectly benign, but I spent a lot of time debugging this and
trying to figure out how to solve something that didn't need solving. So
document for posterity.
For an adopted thread, the TLS destructors or the adopted thread watcher
on Windows will call QThreadData::deref():
- QThreadData::deref(), count drops to zero
-> delete this;
- ~QThreadData() deletes the QAdoptedThread
-> delete t;
- ~QThreadPrivate() calls deref() again
-> data->deref();
- QThreadData::deref(), count drops to -1, no action taken
- ~QObjectPrivate() calls deref() yet again
-> threadData->deref()
- QThreadData::deref(), count drops to -2, no action taken
Change-Id: Icaa86fc7b54d4b368c0efffd14ee448e0796e8d7
Reviewed-by: Friedemann Kleint <Friedemann.Kleint@qt.io>
Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
Diffstat (limited to 'src')
-rw-r--r-- | src/corelib/thread/qthread.cpp | 7 |
1 files changed, 7 insertions, 0 deletions
diff --git a/src/corelib/thread/qthread.cpp b/src/corelib/thread/qthread.cpp index e92be64dfa..cad7a14017 100644 --- a/src/corelib/thread/qthread.cpp +++ b/src/corelib/thread/qthread.cpp @@ -78,6 +78,13 @@ QThreadData::~QThreadData() QThreadData::clearCurrentThreadData(); } + // ~QThread() sets thread to nullptr, so if it isn't null here, it's + // because we're being run before the main object itself. This can only + // happen for QAdoptedThread. Note that both ~QThreadPrivate() and + // ~QObjectPrivate() will deref this object again, but that is acceptable + // because this destructor is still running (the _ref sub-object has not + // been destroyed) and there's no reentrancy. The refcount will become + // negative, but that's acceptable. QThread *t = thread; thread = 0; delete t; |