lock baseEnv in cache()
sync up; this doesn't actually do anything in qmake. as we modify the environment, it must be properly locked. this implies that initFrom() also needs to be called with a lock. Task-number: QTCREATORBUG-9835 Change-Id: I48bae9af9adaa0518e5a9db0ba08ff057ae14f9f Reviewed-by: Joerg Bornemann <joerg.bornemann@digia.com> (cherry picked from qtcreator/d022a2d19cecb00397c2a215fc4e3bf64b1e627b)
This commit is contained in:
parent
957134dc84
commit
652bdb8894
@ -56,6 +56,9 @@
|
|||||||
#include <qset.h>
|
#include <qset.h>
|
||||||
#include <qstringlist.h>
|
#include <qstringlist.h>
|
||||||
#include <qtextstream.h>
|
#include <qtextstream.h>
|
||||||
|
#ifdef PROEVALUATOR_THREAD_SAFE
|
||||||
|
# include <qthreadpool.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef Q_OS_UNIX
|
#ifdef Q_OS_UNIX
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
@ -1538,8 +1541,31 @@ QMakeEvaluator::VisitReturn QMakeEvaluator::evaluateBuiltinConditional(
|
|||||||
ProStringList newval;
|
ProStringList newval;
|
||||||
bool changed = false;
|
bool changed = false;
|
||||||
for (bool hostBuild = false; ; hostBuild = true) {
|
for (bool hostBuild = false; ; hostBuild = true) {
|
||||||
if (QMakeBaseEnv *baseEnv = m_option->baseEnvs.value(
|
#ifdef PROEVALUATOR_THREAD_SAFE
|
||||||
QMakeBaseKey(m_buildRoot, hostBuild))) {
|
m_option->mutex.lock();
|
||||||
|
#endif
|
||||||
|
QMakeBaseEnv *baseEnv =
|
||||||
|
m_option->baseEnvs.value(QMakeBaseKey(m_buildRoot, hostBuild));
|
||||||
|
#ifdef PROEVALUATOR_THREAD_SAFE
|
||||||
|
// It's ok to unlock this before locking baseEnv,
|
||||||
|
// as we have no intention to initialize the env.
|
||||||
|
m_option->mutex.unlock();
|
||||||
|
#endif
|
||||||
|
do {
|
||||||
|
if (!baseEnv)
|
||||||
|
break;
|
||||||
|
#ifdef PROEVALUATOR_THREAD_SAFE
|
||||||
|
QMutexLocker locker(&baseEnv->mutex);
|
||||||
|
if (baseEnv->inProgress) {
|
||||||
|
// The env is still in the works, but it may be already past the cache
|
||||||
|
// loading. So we need to wait for completion and amend it as usual.
|
||||||
|
QThreadPool::globalInstance()->releaseThread();
|
||||||
|
baseEnv->cond.wait(&baseEnv->mutex);
|
||||||
|
QThreadPool::globalInstance()->reserveThread();
|
||||||
|
}
|
||||||
|
if (!baseEnv->isOk)
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
QMakeEvaluator *baseEval = baseEnv->evaluator;
|
QMakeEvaluator *baseEval = baseEnv->evaluator;
|
||||||
const ProStringList &oldval = baseEval->values(dstvar);
|
const ProStringList &oldval = baseEval->values(dstvar);
|
||||||
if (mode == CacheSet) {
|
if (mode == CacheSet) {
|
||||||
@ -1570,7 +1596,7 @@ QMakeEvaluator::VisitReturn QMakeEvaluator::evaluateBuiltinConditional(
|
|||||||
}
|
}
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
}
|
} while (false);
|
||||||
if (hostBuild)
|
if (hostBuild)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
@ -1317,7 +1317,6 @@ QMakeEvaluator::VisitReturn QMakeEvaluator::visitProFile(
|
|||||||
QMakeBaseEnv *baseEnv = *baseEnvPtr;
|
QMakeBaseEnv *baseEnv = *baseEnvPtr;
|
||||||
|
|
||||||
#ifdef PROEVALUATOR_THREAD_SAFE
|
#ifdef PROEVALUATOR_THREAD_SAFE
|
||||||
{
|
|
||||||
QMutexLocker locker(&baseEnv->mutex);
|
QMutexLocker locker(&baseEnv->mutex);
|
||||||
m_option->mutex.unlock();
|
m_option->mutex.unlock();
|
||||||
if (baseEnv->inProgress) {
|
if (baseEnv->inProgress) {
|
||||||
@ -1357,7 +1356,6 @@ QMakeEvaluator::VisitReturn QMakeEvaluator::visitProFile(
|
|||||||
#ifdef PROEVALUATOR_THREAD_SAFE
|
#ifdef PROEVALUATOR_THREAD_SAFE
|
||||||
else if (!baseEnv->isOk)
|
else if (!baseEnv->isOk)
|
||||||
return ReturnFalse;
|
return ReturnFalse;
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
initFrom(*baseEnv->evaluator);
|
initFrom(*baseEnv->evaluator);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user