void tst_QThreadPool::tryStart() { class WaitingTask : public QRunnable { public: QSemaphore semaphore; WaitingTask() { setAutoDelete(false); } void run() { semaphore.acquire(); count.ref(); } }; count.store(0); WaitingTask task; QThreadPool threadPool; for (int i = 0; i < threadPool.maxThreadCount(); ++i) { threadPool.start(&task); } QVERIFY(!threadPool.tryStart(&task)); task.semaphore.release(threadPool.maxThreadCount()); threadPool.waitForDone(); QCOMPARE(count.load(), threadPool.maxThreadCount()); }
void tst_QThreadPool::setMaxThreadCount() { QFETCH(int, limit); QThreadPool *threadPool = QThreadPool::globalInstance(); int savedLimit = threadPool->maxThreadCount(); // maxThreadCount() should always return the previous argument to // setMaxThreadCount(), regardless of input threadPool->setMaxThreadCount(limit); QCOMPARE(threadPool->maxThreadCount(), limit); // the value returned from maxThreadCount() should always be valid input for setMaxThreadCount() threadPool->setMaxThreadCount(savedLimit); QCOMPARE(threadPool->maxThreadCount(), savedLimit); // setting the limit on children should have no effect on the parent { QThreadPool threadPool2(threadPool); savedLimit = threadPool2.maxThreadCount(); // maxThreadCount() should always return the previous argument to // setMaxThreadCount(), regardless of input threadPool2.setMaxThreadCount(limit); QCOMPARE(threadPool2.maxThreadCount(), limit); // the value returned from maxThreadCount() should always be valid input for setMaxThreadCount() threadPool2.setMaxThreadCount(savedLimit); QCOMPARE(threadPool2.maxThreadCount(), savedLimit); } }
void tst_QThreadPool::reserveThread() { QFETCH(int, limit); QThreadPool *threadpool = QThreadPool::globalInstance(); int savedLimit = threadpool->maxThreadCount(); threadpool->setMaxThreadCount(limit); // reserve up to the limit for (int i = 0; i < limit; ++i) threadpool->reserveThread(); // reserveThread() should always reserve a thread, regardless of // how many have been previously reserved threadpool->reserveThread(); QCOMPARE(threadpool->activeThreadCount(), (limit > 0 ? limit : 0) + 1); threadpool->reserveThread(); QCOMPARE(threadpool->activeThreadCount(), (limit > 0 ? limit : 0) + 2); // cleanup threadpool->releaseThread(); threadpool->releaseThread(); for (int i = 0; i < limit; ++i) threadpool->releaseThread(); // reserving threads in children should not effect the parent { QThreadPool threadpool2(threadpool); threadpool2.setMaxThreadCount(limit); // reserve up to the limit for (int i = 0; i < limit; ++i) threadpool2.reserveThread(); // reserveThread() should always reserve a thread, regardless // of how many have been previously reserved threadpool2.reserveThread(); QCOMPARE(threadpool2.activeThreadCount(), (limit > 0 ? limit : 0) + 1); threadpool2.reserveThread(); QCOMPARE(threadpool2.activeThreadCount(), (limit > 0 ? limit : 0) + 2); threadpool->reserveThread(); QCOMPARE(threadpool->activeThreadCount(), 1); threadpool->reserveThread(); QCOMPARE(threadpool->activeThreadCount(), 2); // cleanup threadpool2.releaseThread(); threadpool2.releaseThread(); threadpool->releaseThread(); threadpool->releaseThread(); while (threadpool2.activeThreadCount() > 0) threadpool2.releaseThread(); } // reset limit on global QThreadPool threadpool->setMaxThreadCount(savedLimit); }
void tst_QThreadPool::releaseThread() { QFETCH(int, limit); QThreadPool *threadpool = QThreadPool::globalInstance(); int savedLimit = threadpool->maxThreadCount(); threadpool->setMaxThreadCount(limit); // reserve up to the limit for (int i = 0; i < limit; ++i) threadpool->reserveThread(); // release should decrease the number of reserved threads int reserved = threadpool->activeThreadCount(); while (reserved-- > 0) { threadpool->releaseThread(); QCOMPARE(threadpool->activeThreadCount(), reserved); } QCOMPARE(threadpool->activeThreadCount(), 0); // releaseThread() can release more than have been reserved threadpool->releaseThread(); QCOMPARE(threadpool->activeThreadCount(), -1); threadpool->reserveThread(); QCOMPARE(threadpool->activeThreadCount(), 0); // releasing threads in children should not effect the parent { QThreadPool threadpool2(threadpool); threadpool2.setMaxThreadCount(limit); // reserve up to the limit for (int i = 0; i < limit; ++i) threadpool2.reserveThread(); // release should decrease the number of reserved threads int reserved = threadpool2.activeThreadCount(); while (reserved-- > 0) { threadpool2.releaseThread(); QCOMPARE(threadpool2.activeThreadCount(), reserved); QCOMPARE(threadpool->activeThreadCount(), 0); } QCOMPARE(threadpool2.activeThreadCount(), 0); QCOMPARE(threadpool->activeThreadCount(), 0); // releaseThread() can release more than have been reserved threadpool2.releaseThread(); QCOMPARE(threadpool2.activeThreadCount(), -1); QCOMPARE(threadpool->activeThreadCount(), 0); threadpool2.reserveThread(); QCOMPARE(threadpool2.activeThreadCount(), 0); QCOMPARE(threadpool->activeThreadCount(), 0); } // reset limit on global QThreadPool threadpool->setMaxThreadCount(savedLimit); }
explicit Polygonizer(feature::GenerateInfo const & info) : m_info(info) #if PARALLEL_POLYGONIZER , m_ThreadPoolSemaphore(m_ThreadPool.maxThreadCount() * 8) #endif { #if PARALLEL_POLYGONIZER LOG(LINFO, ("Polygonizer thread pool threads:", m_ThreadPool.maxThreadCount())); #endif if (info.m_splitByPolygons) { CHECK(borders::LoadCountriesList(info.m_targetDir, m_countries), ("Error loading country polygons files")); } else { // Insert fake country polygon equal to whole world to // create only one output file which contains all features m_countries.Add(borders::CountryPolygons(info.m_fileName), MercatorBounds::FullRect()); } }
void PulsarProcess::run() { if (!data.isValid()) { qDebug() << "No valid data available"; return; } QVector<PulsarWorker*> workers; QThreadPool *pool = CalculationPool::pool(); qDebug() << "splitting to" << pool->maxThreadCount() << "processes"; if (!Settings::settings()->preciseSearch()) { for (int D = 0; D < 200; D += 6) for (int i = 0; i < data.modules; i++) for (int j = 0; j < data.rays; j++) { workers.push_back(new PulsarWorker(i, j, D, data)); workers[workers.size() - 1]->setAutoDelete(false); pool->start(workers[workers.size() - 1]); } } else if (Settings::settings()->periodTester()) { workers.push_back(new PulsarWorker(Settings::settings()->module(), Settings::settings()->ray(), Settings::settings()->dispersion(), data)); workers[0]->setAutoDelete(false); pool->start(workers[0]); } else { int mx = 200; if (Settings::settings()->dispersion() > -0.5) mx = Settings::settings()->dispersion() + 6; int step = 1; if (data.oneStep > 0.05) step = 3; for (double D = max(Settings::settings()->dispersion() - 6, 0.0); D < mx; D += step) { workers.push_back(new PulsarWorker(Settings::settings()->module(), Settings::settings()->ray(), D, data)); workers[workers.size() - 1]->setAutoDelete(false); pool->start(workers[workers.size() - 1]); } } while (!pool->waitForDone(30000)) { bool finished = true; for (int i = 0; i < workers.size(); i++) finished &= workers[i]->finished; if (finished) break; } QVector<Pulsar> pulsars; for (int i = 0; i < workers.size(); i++) { for (int j = 0; j < workers[i]->res.size(); j++) pulsars.push_back(workers[i]->res[j]); // workers[i]->deleteLater(); } qDebug() << "workers deleted"; for (int i = 0; i < pulsars.size(); i++) for (int j = i + 1; j < pulsars.size(); j++) if ((pulsars[i].filtered && !pulsars[j].filtered) || ((pulsars[i].filtered == pulsars[j].filtered) && (pulsars[i].firstPoint > pulsars[j].firstPoint))) { Pulsar p = pulsars[i]; pulsars[i] = pulsars[j]; pulsars[j] = p; } QByteArray header = QString("file: %1\ntresolution %2\nStart time\tmodule\tray\tdispersion\tperiod\tsnr\tfirst_point\n").arg(data.name).arg(data.oneStep).toUtf8(); QFile *files[CATEGORIES]; bool filtered[CATEGORIES]; for (int i = 0; i < CATEGORIES; i++) filtered[i] = false; QDir().mkdir(savePath); for (int i = 0; i < CATEGORIES; i++) { files[i] = new QFile(savePath + QString("%1-%2-%3.pulsar").arg(data.name).arg(CATEGORIES_SIZES[i]).arg(CATEGORIES_SIZES[i + 1])); files[i]->open(QIODevice::WriteOnly); files[i]->write(header); } for (int i = 0; i < pulsars.size(); i++) for (int j = CATEGORIES - 1; j >= 0; j--) if (CATEGORIES_SIZES[j] < pulsars[i].snr || j == 0) { if (!filtered[j] && pulsars[i].filtered) { filtered[j] = true; files[j]->write(QByteArray("filtered next\n")); } QByteArray d = QString("%1\t%2\t%3\t%4\t%5\t%6\t%7\n"). arg(pulsars[i].time()). arg(pulsars[i].module + 1). arg(pulsars[i].ray + 1). arg(pulsars[i].dispersion). arg(QString::number(pulsars[i].period, 'f', 5)). arg(QString::number(pulsars[i].snr, 'f', 1)). arg(QString::number(pulsars[i].firstPoint)). toUtf8(); files[j]->write(d); break; } for (int i = 0; i < CATEGORIES; i++) files[i]->write("additional data:\n"); for (int i = 0; i < pulsars.size(); i++) for (int j = CATEGORIES - 1; j >= 0; j--) if (CATEGORIES_SIZES[j] < pulsars[i].snr || j == 0) { files[j]->write(pulsars[i].additionalData); break; } for (int i = 0; i < CATEGORIES; i++) { files[i]->close(); delete files[i]; } qDebug() << "files deleted"; }