XdgDesktopPortal: Prevent c'tor re-entry

XdgDesktopPortal requires a base platform theme, which is created in
its c'tor. If XdgDesktopPortal was shipped as a plugin of its own,
it would find itself as a plugin, create itself as its own base theme
and thus end up in an infinite loop.

Factor out the key check from main.cpp as a static bool in
QXdgDesktopPortalTheme.
Ignore XdgDesktop keys when scanning for plugins suitable as a base
theme.

Fixes: QTBUG-134703
Pick-to: 6.9 6.8 6.5
Change-Id: I4aab1e77a48251581369f371e4c9af308ef0a02b
Reviewed-by: Liang Qi <liang.qi@qt.io>
This commit is contained in:
Axel Spoerl 2025-03-20 13:41:58 +01:00
parent 22e05d74b2
commit 3404a1491e
3 changed files with 14 additions and 6 deletions

View File

@ -20,12 +20,7 @@ public:
QPlatformTheme *QXdgDesktopPortalThemePlugin::create(const QString &key, const QStringList &params)
{
Q_UNUSED(params);
if (!key.compare("xdgdesktopportal"_L1, Qt::CaseInsensitive) ||
!key.compare("flatpak"_L1, Qt::CaseInsensitive) ||
!key.compare("snap"_L1, Qt::CaseInsensitive))
return new QXdgDesktopPortalTheme;
return nullptr;
return QXdgDesktopPortalTheme::isXdgPlugin(key) ? new QXdgDesktopPortalTheme : nullptr;
}
QT_END_NAMESPACE

View File

@ -88,6 +88,8 @@ QXdgDesktopPortalTheme::QXdgDesktopPortalTheme()
themeNames += QGuiApplicationPrivate::platform_integration->themeNames();
// 1) Look for a theme plugin.
for (const QString &themeName : std::as_const(themeNames)) {
if (QXdgDesktopPortalTheme::isXdgPlugin(themeName))
continue;
d->baseTheme = QPlatformThemeFactory::create(themeName, nullptr);
if (d->baseTheme)
break;
@ -97,6 +99,8 @@ QXdgDesktopPortalTheme::QXdgDesktopPortalTheme()
// create a theme
if (!d->baseTheme) {
for (const QString &themeName : std::as_const(themeNames)) {
if (QXdgDesktopPortalTheme::isXdgPlugin(themeName))
continue;
d->baseTheme = QGuiApplicationPrivate::platform_integration->createPlatformTheme(themeName);
if (d->baseTheme)
break;
@ -263,6 +267,13 @@ QString QXdgDesktopPortalTheme::standardButtonText(int button) const
return d->baseTheme->standardButtonText(button);
}
bool QXdgDesktopPortalTheme::isXdgPlugin(const QString &key)
{
return key.compare("xdgdesktopportal"_L1, Qt::CaseInsensitive) == 0 ||
key.compare("flatpak"_L1, Qt::CaseInsensitive) == 0 ||
key.compare("snap"_L1, Qt::CaseInsensitive) == 0;
}
QT_END_NAMESPACE
#include "qxdgdesktopportaltheme.moc"

View File

@ -48,6 +48,8 @@ public:
QString standardButtonText(int button) const override;
static bool isXdgPlugin(const QString &key);
private:
QScopedPointer<QXdgDesktopPortalThemePrivate> d_ptr;
Q_DISABLE_COPY_MOVE(QXdgDesktopPortalTheme)