Guard coroutine calls

Fixes https://invent.kde.org/plasma/plasma-mobile/-/issues/480

This ensures that coroutines are properly guarded against object
deletion.
This commit is contained in:
Devin Lin 2026-01-07 21:02:02 -05:00
parent 5b48cc9cc9
commit cd7dd7c8e5
5 changed files with 71 additions and 24 deletions

View file

@ -3,6 +3,8 @@
#include "vibrationmanager.h"
#include <QPointer>
VibrationManager::VibrationManager(QObject *parent)
: QObject{parent}
{
@ -21,8 +23,14 @@ QCoro::Task<void> VibrationManager::vibrateTask(int durationMs)
const QString appId = QStringLiteral("org.kde.plasmashell");
const VibrationEvent event{1.0, static_cast<quint32>(durationMs)};
const VibrationEventList pattern = {event};
QPointer<VibrationManager> guard(this);
QDBusPendingReply<bool> reply = co_await m_interface->Vibrate(appId, pattern);
if (!guard) {
co_return;
}
if (!reply.isValid() || !reply.value()) {
qWarning() << "feedbackd vibration failed";
}

View file

@ -9,6 +9,7 @@
#include <NetworkManagerQt/Settings>
#include <NetworkManagerQt/Utils>
#include <QDBusReply>
#include <QPointer>
#include <KUser>
@ -226,7 +227,13 @@ QCoro::Task<void> SignalIndicator::activateProfile(const QString &connectionUni)
// activate connection manually
// despite the documentation saying otherwise, activateConnection seems to need the DBus path, not uuid of the connection
QPointer<SignalIndicator> guard(this);
QDBusReply<QDBusObjectPath> reply = co_await NetworkManager::activateConnection(con->path(), m_nmModem->uni(), {});
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qWarning() << QStringLiteral("Error activating connection:") << reply.error().message();
co_return;
@ -255,7 +262,13 @@ QCoro::Task<void> SignalIndicator::addProfile(const QString &name, const QString
gsmSetting->setInitialized(true);
QPointer<SignalIndicator> guard(this);
QDBusReply<QDBusObjectPath> reply = co_await NetworkManager::addAndActivateConnection(settings->toMap(), m_nmModem->uni(), {});
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qWarning() << "Error adding connection:" << reply.error().message();
} else {
@ -271,7 +284,13 @@ QCoro::Task<void> SignalIndicator::removeProfile(const QString &connectionUni)
co_return;
}
QPointer<SignalIndicator> guard(this);
QDBusPendingReply reply = co_await con->remove();
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qWarning() << "Error removing connection" << reply.error().message();
}
@ -307,7 +326,13 @@ QCoro::Task<void> SignalIndicator::updateProfile(const QString &connectionUni,
gsmSetting->setInitialized(true);
QPointer<SignalIndicator> guard(this);
QDBusPendingReply reply = co_await con->update(conSettings->toMap());
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qWarning() << "Error updating connection settings for" << connectionUni << ":" << reply.error().message() << ".";
} else {

View file

@ -9,6 +9,7 @@
#include <QDBusInterface>
#include <QDBusMessage>
#include <QDBusReply>
#include <QPointer>
#include <KLocalizedString>
#include <KPackage/Package>
@ -171,7 +172,13 @@ QCoro::Task<void> WallpaperPlugin::setHomescreenWallpaper(const QString &path)
for (uint screen = 0; screen < qApp->screens().size(); screen++) {
message.setArguments({"org.kde.image", QVariantMap{{"Image", path}}, screen});
QPointer<WallpaperPlugin> guard(this);
const QDBusReply<void> reply = co_await QDBusConnection::sessionBus().asyncCall(message);
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qWarning() << "Failed to set wallpaper for screen" << screen << ":" << reply.error();
}
@ -210,7 +217,13 @@ QCoro::Task<void> WallpaperPlugin::loadHomescreenSettings()
QLatin1String("wallpaper"));
message.setArguments({(uint)0}); // assume wallpaper on first screen
QPointer<WallpaperPlugin> guard(this);
QDBusReply<QVariantMap> reply = co_await QDBusConnection::sessionBus().asyncCall(message);
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qWarning() << "unable to load homescreen wallpaper settings:" << reply.error();
co_return;
@ -317,7 +330,13 @@ QCoro::Task<void> WallpaperPlugin::saveHomescreenSettings()
for (uint screen = 0; screen < qApp->screens().size(); screen++) {
QList<QVariant> args = {m_homescreenWallpaperPlugin, params, screen};
QPointer<WallpaperPlugin> guard(this);
const QDBusReply<void> response = co_await iface->asyncCallWithArgumentList(QStringLiteral("setWallpaper"), args);
if (!guard) {
co_return;
}
if (!response.isValid()) {
qWarning() << "Failed to set wallpaper:" << response.error();
}

View file

@ -133,8 +133,7 @@ WaydroidApplicationListModel *WaydroidDBusClient::applicationListModel() const
QCoro::Task<void> WaydroidDBusClient::setMultiWindowsTask(const bool multiWindows)
{
auto pendingReply = m_interface->setMultiWindows(multiWindows);
co_await pendingReply;
co_await m_interface->setMultiWindows(multiWindows);
}
QCoro::QmlTask WaydroidDBusClient::setMultiWindows(const bool multiWindows)
@ -149,8 +148,7 @@ bool WaydroidDBusClient::multiWindows() const
QCoro::Task<void> WaydroidDBusClient::setSuspendTask(const bool suspend)
{
auto pendingReply = m_interface->setSuspend(suspend);
co_await pendingReply;
co_await m_interface->setSuspend(suspend);
}
QCoro::QmlTask WaydroidDBusClient::setSuspend(const bool suspend)
@ -165,8 +163,7 @@ bool WaydroidDBusClient::suspend() const
QCoro::Task<void> WaydroidDBusClient::setUeventTask(const bool uevent)
{
auto pendingReply = m_interface->setUevent(uevent);
co_await pendingReply;
co_await m_interface->setUevent(uevent);
}
QCoro::QmlTask WaydroidDBusClient::setUevent(const bool uevent)
@ -176,8 +173,7 @@ QCoro::QmlTask WaydroidDBusClient::setUevent(const bool uevent)
QCoro::Task<void> WaydroidDBusClient::refreshSessionInfoTask()
{
auto pendingReply = m_interface->refreshSessionInfo();
co_await pendingReply;
co_await m_interface->refreshSessionInfo();
}
QCoro::QmlTask WaydroidDBusClient::refreshSessionInfo()
@ -187,8 +183,7 @@ QCoro::QmlTask WaydroidDBusClient::refreshSessionInfo()
QCoro::Task<void> WaydroidDBusClient::refreshAndroidIdTask()
{
auto pendingReply = m_interface->refreshAndroidId();
co_await pendingReply;
co_await m_interface->refreshAndroidId();
}
QCoro::QmlTask WaydroidDBusClient::refreshAndroidId()
@ -198,8 +193,7 @@ QCoro::QmlTask WaydroidDBusClient::refreshAndroidId()
QCoro::Task<void> WaydroidDBusClient::refreshApplicationsTask()
{
auto pendingReply = m_interface->refreshApplications();
co_await pendingReply;
co_await m_interface->refreshApplications();
}
QCoro::QmlTask WaydroidDBusClient::refreshApplications()
@ -214,8 +208,7 @@ bool WaydroidDBusClient::uevent() const
QCoro::Task<void> WaydroidDBusClient::initializeTask(const SystemType systemType, const RomType romType, const bool forced)
{
auto pendingReply = m_interface->initialize(systemType, romType, forced);
co_await pendingReply;
co_await m_interface->initialize(systemType, romType, forced);
}
QCoro::QmlTask WaydroidDBusClient::initialize(const SystemType systemType, const RomType romType, const bool forced)
@ -225,8 +218,7 @@ QCoro::QmlTask WaydroidDBusClient::initialize(const SystemType systemType, const
QCoro::Task<void> WaydroidDBusClient::startSessionTask()
{
auto pendingReply = m_interface->startSession();
co_await pendingReply;
co_await m_interface->startSession();
}
QCoro::QmlTask WaydroidDBusClient::startSession()
@ -236,8 +228,7 @@ QCoro::QmlTask WaydroidDBusClient::startSession()
QCoro::Task<void> WaydroidDBusClient::stopSessionTask()
{
auto pendingReply = m_interface->stopSession();
co_await pendingReply;
co_await m_interface->stopSession();
}
QCoro::QmlTask WaydroidDBusClient::stopSession()
@ -247,8 +238,7 @@ QCoro::QmlTask WaydroidDBusClient::stopSession()
QCoro::Task<void> WaydroidDBusClient::resetWaydroidTask()
{
auto pendingReply = m_interface->resetWaydroid();
co_await pendingReply;
co_await m_interface->resetWaydroid();
}
QCoro::QmlTask WaydroidDBusClient::resetWaydroid()
@ -258,8 +248,7 @@ QCoro::QmlTask WaydroidDBusClient::resetWaydroid()
QCoro::Task<void> WaydroidDBusClient::installApkTask(const QString apkFile)
{
auto pendingReply = m_interface->installApk(apkFile);
co_await pendingReply;
co_await m_interface->installApk(apkFile);
}
QCoro::QmlTask WaydroidDBusClient::installApk(const QString apkFile)
@ -269,8 +258,7 @@ QCoro::QmlTask WaydroidDBusClient::installApk(const QString apkFile)
QCoro::Task<void> WaydroidDBusClient::deleteApplicationTask(const QString appId)
{
auto pendingReply = m_interface->deleteApplication(appId);
co_await pendingReply;
co_await m_interface->deleteApplication(appId);
}
QCoro::QmlTask WaydroidDBusClient::deleteApplication(const QString appId)

View file

@ -13,6 +13,7 @@
#include <QDomElement>
#include <QFile>
#include <QLoggingCategory>
#include <QPointer>
#include <QStandardPaths>
#include <NetworkManagerQt/CdmaSetting>
@ -106,7 +107,13 @@ QCoro::Task<void> AutoDetectAPN::checkAndAddAutodetectedAPN()
ipv6Setting->setInitialized(true);
}
QPointer<AutoDetectAPN> guard(this);
QDBusReply<QDBusObjectPath> reply = co_await NetworkManager::addAndActivateConnection(settings->toMap(), nmModem->uni(), "");
if (!guard) {
co_return;
}
if (!reply.isValid()) {
qCWarning(LOGGING_CATEGORY) << "Error adding autodetected connection:" << reply.error().message();
} else {