fix: compiler warnings
Mostly QFutureWatcher leaks, fixed by using QFuture.then Also calculator false positive leak
This commit is contained in:
parent
a034467ed2
commit
501a14bd2a
5 changed files with 26 additions and 55 deletions
|
|
@ -105,34 +105,26 @@ void CachingImageManager::updateSource(const QString& path) {
|
||||||
|
|
||||||
m_shaPath = path;
|
m_shaPath = path;
|
||||||
|
|
||||||
const auto future = QtConcurrent::run(&CachingImageManager::sha256sum, path);
|
QtConcurrent::run(&CachingImageManager::sha256sum, path).then(this, [path, this](const QString& sha) {
|
||||||
|
|
||||||
const auto watcher = new QFutureWatcher<QString>(this);
|
|
||||||
|
|
||||||
connect(watcher, &QFutureWatcher<QString>::finished, this, [watcher, path, this]() {
|
|
||||||
if (m_path != path) {
|
if (m_path != path) {
|
||||||
// Object is destroyed or path has changed, ignore
|
|
||||||
watcher->deleteLater();
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const QSize size = effectiveSize();
|
const QSize size = effectiveSize();
|
||||||
|
|
||||||
if (!m_item || !size.width() || !size.height()) {
|
if (!m_item || !size.width() || !size.height()) {
|
||||||
watcher->deleteLater();
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const QString fillMode = m_item->property("fillMode").toString();
|
const QString fillMode = m_item->property("fillMode").toString();
|
||||||
// clang-format off
|
// clang-format off
|
||||||
const QString filename = QString("%1@%2x%3-%4.png")
|
const QString filename = QString("%1@%2x%3-%4.png")
|
||||||
.arg(watcher->result()).arg(size.width()).arg(size.height())
|
.arg(sha).arg(size.width()).arg(size.height())
|
||||||
.arg(fillMode == "PreserveAspectCrop" ? "crop" : fillMode == "PreserveAspectFit" ? "fit" : "stretch");
|
.arg(fillMode == "PreserveAspectCrop" ? "crop" : fillMode == "PreserveAspectFit" ? "fit" : "stretch");
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
const QUrl cache = m_cacheDir.resolved(QUrl(filename));
|
const QUrl cache = m_cacheDir.resolved(QUrl(filename));
|
||||||
if (m_cachePath == cache) {
|
if (m_cachePath == cache) {
|
||||||
watcher->deleteLater();
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -141,7 +133,6 @@ void CachingImageManager::updateSource(const QString& path) {
|
||||||
|
|
||||||
if (!cache.isLocalFile()) {
|
if (!cache.isLocalFile()) {
|
||||||
qWarning() << "CachingImageManager::updateSource: cachePath" << cache << "is not a local file";
|
qWarning() << "CachingImageManager::updateSource: cachePath" << cache << "is not a local file";
|
||||||
watcher->deleteLater();
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -157,11 +148,7 @@ void CachingImageManager::updateSource(const QString& path) {
|
||||||
if (m_shaPath == path) {
|
if (m_shaPath == path) {
|
||||||
m_shaPath = QString();
|
m_shaPath = QString();
|
||||||
}
|
}
|
||||||
|
|
||||||
watcher->deleteLater();
|
|
||||||
});
|
});
|
||||||
|
|
||||||
watcher->setFuture(future);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
QUrl CachingImageManager::cachePath() const {
|
QUrl CachingImageManager::cachePath() const {
|
||||||
|
|
|
||||||
|
|
@ -219,7 +219,7 @@ void FileSystemModel::watchDirIfRecursive(const QString& path) {
|
||||||
if (m_recursive && m_watchChanges) {
|
if (m_recursive && m_watchChanges) {
|
||||||
const auto currentDir = m_dir;
|
const auto currentDir = m_dir;
|
||||||
const bool showHidden = m_showHidden;
|
const bool showHidden = m_showHidden;
|
||||||
const auto future = QtConcurrent::run([showHidden, path]() {
|
auto future = QtConcurrent::run([showHidden, path]() {
|
||||||
QDir::Filters filters = QDir::Dirs | QDir::NoDotAndDotDot;
|
QDir::Filters filters = QDir::Dirs | QDir::NoDotAndDotDot;
|
||||||
if (showHidden) {
|
if (showHidden) {
|
||||||
filters |= QDir::Hidden;
|
filters |= QDir::Hidden;
|
||||||
|
|
@ -232,16 +232,12 @@ void FileSystemModel::watchDirIfRecursive(const QString& path) {
|
||||||
}
|
}
|
||||||
return dirs;
|
return dirs;
|
||||||
});
|
});
|
||||||
const auto watcher = new QFutureWatcher<QStringList>(this);
|
future.then(this, [currentDir, showHidden, this](const QStringList& paths) {
|
||||||
connect(watcher, &QFutureWatcher<QStringList>::finished, this, [currentDir, showHidden, watcher, this]() {
|
|
||||||
const auto paths = watcher->result();
|
|
||||||
if (currentDir == m_dir && showHidden == m_showHidden && !paths.isEmpty()) {
|
if (currentDir == m_dir && showHidden == m_showHidden && !paths.isEmpty()) {
|
||||||
// Ignore if dir or showHidden has changed
|
// Ignore if dir or showHidden has changed
|
||||||
m_watcher.addPaths(paths);
|
m_watcher.addPaths(paths);
|
||||||
}
|
}
|
||||||
watcher->deleteLater();
|
|
||||||
});
|
});
|
||||||
watcher->setFuture(future);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -295,7 +291,7 @@ void FileSystemModel::updateEntriesForDir(const QString& dir) {
|
||||||
oldPaths << entry->path();
|
oldPaths << entry->path();
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto future = QtConcurrent::run([=](QPromise<QPair<QSet<QString>, QSet<QString>>>& promise) {
|
auto future = QtConcurrent::run([=](QPromise<QPair<QSet<QString>, QSet<QString>>>& promise) {
|
||||||
const auto flags = recursive ? QDirIterator::Subdirectories : QDirIterator::NoIteratorFlags;
|
const auto flags = recursive ? QDirIterator::Subdirectories : QDirIterator::NoIteratorFlags;
|
||||||
|
|
||||||
std::optional<QDirIterator> iter;
|
std::optional<QDirIterator> iter;
|
||||||
|
|
@ -353,7 +349,7 @@ void FileSystemModel::updateEntriesForDir(const QString& dir) {
|
||||||
newPaths.insert(path);
|
newPaths.insert(path);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (promise.isCanceled() || newPaths == oldPaths) {
|
if (promise.isCanceled()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -365,23 +361,17 @@ void FileSystemModel::updateEntriesForDir(const QString& dir) {
|
||||||
}
|
}
|
||||||
m_futures.insert(dir, future);
|
m_futures.insert(dir, future);
|
||||||
|
|
||||||
const auto watcher = new QFutureWatcher<QPair<QSet<QString>, QSet<QString>>>(this);
|
future
|
||||||
|
.then(this,
|
||||||
connect(watcher, &QFutureWatcher<QPair<QSet<QString>, QSet<QString>>>::finished, this, [dir, watcher, this]() {
|
[dir, this](QPair<QSet<QString>, QSet<QString>> result) {
|
||||||
m_futures.remove(dir);
|
m_futures.remove(dir);
|
||||||
|
if (!result.first.isEmpty() || !result.second.isEmpty()) {
|
||||||
if (!watcher->future().isResultReadyAt(0)) {
|
applyChanges(result.first, result.second);
|
||||||
watcher->deleteLater();
|
}
|
||||||
return;
|
})
|
||||||
}
|
.onCanceled(this, [dir, this]() {
|
||||||
|
m_futures.remove(dir);
|
||||||
const auto result = watcher->result();
|
});
|
||||||
applyChanges(result.first, result.second);
|
|
||||||
|
|
||||||
watcher->deleteLater();
|
|
||||||
});
|
|
||||||
|
|
||||||
watcher->setFuture(future);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void FileSystemModel::applyChanges(const QSet<QString>& removedPaths, const QSet<QString>& addedPaths) {
|
void FileSystemModel::applyChanges(const QSet<QString>& removedPaths, const QSet<QString>& addedPaths) {
|
||||||
|
|
|
||||||
|
|
@ -221,7 +221,7 @@ AudioCollector::AudioCollector(QObject* parent)
|
||||||
, m_writeBuffer(&m_buffer2) {}
|
, m_writeBuffer(&m_buffer2) {}
|
||||||
|
|
||||||
AudioCollector::~AudioCollector() {
|
AudioCollector::~AudioCollector() {
|
||||||
stop();
|
AudioCollector::stop();
|
||||||
}
|
}
|
||||||
|
|
||||||
void AudioCollector::start() {
|
void AudioCollector::start() {
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,7 @@ AppEntry::AppEntry(QObject* entry, unsigned int frequency, QObject* parent)
|
||||||
, m_entry(entry)
|
, m_entry(entry)
|
||||||
, m_frequency(frequency) {
|
, m_frequency(frequency) {
|
||||||
const auto mo = m_entry->metaObject();
|
const auto mo = m_entry->metaObject();
|
||||||
const auto tmo = metaObject();
|
const auto tmo = &AppEntry::staticMetaObject;
|
||||||
|
|
||||||
for (const auto& prop :
|
for (const auto& prop :
|
||||||
{ "name", "comment", "execString", "startupClass", "genericName", "categories", "keywords" }) {
|
{ "name", "comment", "execString", "startupClass", "genericName", "categories", "keywords" }) {
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,6 @@
|
||||||
#include "qalculator.hpp"
|
#include "qalculator.hpp"
|
||||||
|
|
||||||
#include <libqalculate/qalculate.h>
|
#include <libqalculate/qalculate.h>
|
||||||
#include <qfuturewatcher.h>
|
|
||||||
#include <qtconcurrentrun.h>
|
#include <qtconcurrentrun.h>
|
||||||
|
|
||||||
namespace caelestia {
|
namespace caelestia {
|
||||||
|
|
@ -11,7 +10,10 @@ QMutex Qalculator::s_calculatorMutex;
|
||||||
Qalculator::Qalculator(QObject* parent)
|
Qalculator::Qalculator(QObject* parent)
|
||||||
: QObject(parent) {
|
: QObject(parent) {
|
||||||
if (!CALCULATOR) {
|
if (!CALCULATOR) {
|
||||||
new Calculator();
|
// Calculator constructor sets the global `calculator` pointer (CALCULATOR macro),
|
||||||
|
// but we need to assign it to a var so compiler doesn't flag it as a leak
|
||||||
|
static const auto* const instance = new Calculator();
|
||||||
|
Q_UNUSED(instance)
|
||||||
CALCULATOR->loadExchangeRates();
|
CALCULATOR->loadExchangeRates();
|
||||||
CALCULATOR->loadGlobalDefinitions();
|
CALCULATOR->loadGlobalDefinitions();
|
||||||
CALCULATOR->loadLocalDefinitions();
|
CALCULATOR->loadLocalDefinitions();
|
||||||
|
|
@ -79,7 +81,7 @@ void Qalculator::evalAsync(const QString& expr) {
|
||||||
emit busyChanged();
|
emit busyChanged();
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto future = QtConcurrent::run([expr]() -> QPair<QString, QString> {
|
QtConcurrent::run([expr]() -> QPair<QString, QString> {
|
||||||
QMutexLocker locker(&s_calculatorMutex);
|
QMutexLocker locker(&s_calculatorMutex);
|
||||||
|
|
||||||
EvaluationOptions eo;
|
EvaluationOptions eo;
|
||||||
|
|
@ -109,18 +111,12 @@ void Qalculator::evalAsync(const QString& expr) {
|
||||||
|
|
||||||
const QString rawStr = QString::fromStdString(result);
|
const QString rawStr = QString::fromStdString(result);
|
||||||
return { QString("%1 = %2").arg(parsed).arg(result), rawStr };
|
return { QString("%1 = %2").arg(parsed).arg(result), rawStr };
|
||||||
});
|
}).then(this, [this, gen](QPair<QString, QString> result) {
|
||||||
|
|
||||||
auto* watcher = new QFutureWatcher<QPair<QString, QString>>(this);
|
|
||||||
|
|
||||||
connect(watcher, &QFutureWatcher<QPair<QString, QString>>::finished, this, [this, watcher, gen]() {
|
|
||||||
watcher->deleteLater();
|
|
||||||
|
|
||||||
if (gen != m_generation) {
|
if (gen != m_generation) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto [formatted, raw] = watcher->result();
|
const auto& [formatted, raw] = result;
|
||||||
|
|
||||||
if (m_result != formatted) {
|
if (m_result != formatted) {
|
||||||
m_result = formatted;
|
m_result = formatted;
|
||||||
|
|
@ -135,8 +131,6 @@ void Qalculator::evalAsync(const QString& expr) {
|
||||||
emit busyChanged();
|
emit busyChanged();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
watcher->setFuture(future);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
QString Qalculator::result() const {
|
QString Qalculator::result() const {
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue