From a1a89d3d1efcf863c33a827a5a5d917f839dbb02 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Martin=20Gr=C3=A4=C3=9Flin?= Date: Tue, 7 Jul 2015 11:48:42 +0200 Subject: [PATCH] Disable Activities support on Wayland This is a temporary workaround for bug 349992 which causes freezes during startup as kwin and kamd dead lock each other on DBus. To workaround we don't call Activities::create and check in every usage of Activities::self() whether the pointer is valid. As a result kwin_wayland now starts pretty fast. CCBUG: 349992 --- client.cpp | 8 +++++++- dbusinterface.cpp | 6 ++++++ effects.cpp | 12 ++++++++---- manage.cpp | 2 +- scripting/scripting_model.cpp | 23 +++++++++++++---------- scripting/workspace_wrapper.cpp | 19 +++++++++++++------ tabbox/tabbox.cpp | 4 +++- toplevel.cpp | 3 +++ useractions.cpp | 9 +++++++++ workspace.cpp | 17 +++++++++++++++-- 10 files changed, 78 insertions(+), 25 deletions(-) diff --git a/client.cpp b/client.cpp index 0d6600acae..98bc6f9751 100644 --- a/client.cpp +++ b/client.cpp @@ -1252,6 +1252,9 @@ void Client::doSetDesktop(int desktop, int was_desk) void Client::setOnActivity(const QString &activity, bool enable) { #ifdef KWIN_BUILD_ACTIVITIES + if (! Activities::self()) { + return; + } QStringList newActivitiesList = activities(); if (newActivitiesList.contains(activity) == enable) //nothing to do return; @@ -1275,6 +1278,9 @@ void Client::setOnActivity(const QString &activity, bool enable) void Client::setOnActivities(QStringList newActivitiesList) { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return; + } QString joinedActivitiesList = newActivitiesList.join(QStringLiteral(",")); joinedActivitiesList = rules()->checkActivity(joinedActivitiesList, false); newActivitiesList = joinedActivitiesList.split(QStringLiteral(","), QString::SkipEmptyParts); @@ -2029,7 +2035,7 @@ void Client::readActivities(Xcb::StringProperty &property) //if the activities are not synced, and there are existing clients with //activities specified, somebody has restarted kwin. we can not validate //activities in this case. we need to trust the old values. - if (Activities::self()->serviceStatus() != KActivities::Consumer::Unknown) { + if (Activities::self() && Activities::self()->serviceStatus() != KActivities::Consumer::Unknown) { QStringList allActivities = Activities::self()->all(); if (allActivities.isEmpty()) { qCDebug(KWIN_CORE) << "no activities!?!?"; diff --git a/dbusinterface.cpp b/dbusinterface.cpp index e852c139c2..01079a1b2a 100644 --- a/dbusinterface.cpp +++ b/dbusinterface.cpp @@ -130,6 +130,9 @@ WRAP(QString, supportInformation) bool DBusInterface::startActivity(const QString &in0) { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return false; + } return Activities::self()->start(in0); #else Q_UNUSED(in0) @@ -140,6 +143,9 @@ bool DBusInterface::startActivity(const QString &in0) bool DBusInterface::stopActivity(const QString &in0) { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return false; + } return Activities::self()->stop(in0); #else Q_UNUSED(in0) diff --git a/effects.cpp b/effects.cpp index 6f239bb2b8..34810ca69d 100644 --- a/effects.cpp +++ b/effects.cpp @@ -280,10 +280,11 @@ EffectsHandlerImpl::EffectsHandlerImpl(Compositor *compositor, Scene *scene) connect(screens(), &Screens::sizeChanged, this, &EffectsHandler::virtualScreenSizeChanged); connect(screens(), &Screens::geometryChanged, this, &EffectsHandler::virtualScreenGeometryChanged); #ifdef KWIN_BUILD_ACTIVITIES - Activities *activities = Activities::self(); - connect(activities, &Activities::added, this, &EffectsHandler::activityAdded); - connect(activities, &Activities::removed, this, &EffectsHandler::activityRemoved); - connect(activities, &Activities::currentChanged, this, &EffectsHandler::currentActivityChanged); + if (Activities *activities = Activities::self()) { + connect(activities, &Activities::added, this, &EffectsHandler::activityAdded); + connect(activities, &Activities::removed, this, &EffectsHandler::activityRemoved); + connect(activities, &Activities::currentChanged, this, &EffectsHandler::currentActivityChanged); + } #endif connect(ws, &Workspace::stackingOrderChanged, this, &EffectsHandler::stackingOrderChanged); #ifdef KWIN_BUILD_TABBOX @@ -919,6 +920,9 @@ void EffectsHandlerImpl::setShowingDesktop(bool showing) QString EffectsHandlerImpl::currentActivity() const { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return QString(); + } return Activities::self()->current(); #else return QString(); diff --git a/manage.cpp b/manage.cpp index d161ddc502..4dd10331c1 100644 --- a/manage.cpp +++ b/manage.cpp @@ -219,7 +219,7 @@ bool Client::manage(xcb_window_t w, bool isMapped) if (desktop() == 0 && asn_valid && asn_data.desktop() != 0) desk = asn_data.desktop(); #ifdef KWIN_BUILD_ACTIVITIES - if (!isMapped && !noborder && isNormalWindow() && !activitiesDefined) { + if (Activities::self() && !isMapped && !noborder && isNormalWindow() && !activitiesDefined) { //a new, regular window, when we're not recovering from a crash, //and it hasn't got an activity. let's try giving it the current one. //TODO: decide whether to keep this before the 4.6 release diff --git a/scripting/scripting_model.cpp b/scripting/scripting_model.cpp index e92605097b..8b595f7c2b 100644 --- a/scripting/scripting_model.cpp +++ b/scripting/scripting_model.cpp @@ -330,14 +330,16 @@ AbstractLevel *AbstractLevel::create(const QList< ClientModel::LevelRestriction switch (restriction) { case ClientModel::ActivityRestriction: { #ifdef KWIN_BUILD_ACTIVITIES - const QStringList &activities = Activities::self()->all(); - for (QStringList::const_iterator it = activities.begin(); it != activities.end(); ++it) { - AbstractLevel *childLevel = create(childRestrictions, childrenRestrictions, model, currentLevel); - if (!childLevel) { - continue; + if (Activities::self()) { + const QStringList &activities = Activities::self()->all(); + for (QStringList::const_iterator it = activities.begin(); it != activities.end(); ++it) { + AbstractLevel *childLevel = create(childRestrictions, childrenRestrictions, model, currentLevel); + if (!childLevel) { + continue; + } + childLevel->setActivity(*it); + currentLevel->addChild(childLevel); } - childLevel->setActivity(*it); - currentLevel->addChild(childLevel); } break; #else @@ -421,9 +423,10 @@ ForkLevel::ForkLevel(const QList &childRestrictio connect(VirtualDesktopManager::self(), SIGNAL(countChanged(uint,uint)), SLOT(desktopCountChanged(uint,uint))); connect(screens(), SIGNAL(countChanged(int,int)), SLOT(screenCountChanged(int,int))); #ifdef KWIN_BUILD_ACTIVITIES - Activities *activities = Activities::self(); - connect(activities, SIGNAL(added(QString)), SLOT(activityAdded(QString))); - connect(activities, SIGNAL(removed(QString)), SLOT(activityRemoved(QString))); + if (Activities *activities = Activities::self()) { + connect(activities, SIGNAL(added(QString)), SLOT(activityAdded(QString))); + connect(activities, SIGNAL(removed(QString)), SLOT(activityRemoved(QString))); + } #endif } diff --git a/scripting/workspace_wrapper.cpp b/scripting/workspace_wrapper.cpp index cae42922e4..05aecb6eb6 100644 --- a/scripting/workspace_wrapper.cpp +++ b/scripting/workspace_wrapper.cpp @@ -48,12 +48,13 @@ WorkspaceWrapper::WorkspaceWrapper(QObject* parent) : QObject(parent) connect(vds, SIGNAL(layoutChanged(int,int)), SIGNAL(desktopLayoutChanged())); connect(ws, &Workspace::clientDemandsAttentionChanged, this, &WorkspaceWrapper::clientDemandsAttentionChanged); #ifdef KWIN_BUILD_ACTIVITIES - KWin::Activities *activities = KWin::Activities::self(); - connect(activities, SIGNAL(currentChanged(QString)), SIGNAL(currentActivityChanged(QString))); - connect(activities, SIGNAL(added(QString)), SIGNAL(activitiesChanged(QString))); - connect(activities, SIGNAL(added(QString)), SIGNAL(activityAdded(QString))); - connect(activities, SIGNAL(removed(QString)), SIGNAL(activitiesChanged(QString))); - connect(activities, SIGNAL(removed(QString)), SIGNAL(activityRemoved(QString))); + if (KWin::Activities *activities = KWin::Activities::self()) { + connect(activities, SIGNAL(currentChanged(QString)), SIGNAL(currentActivityChanged(QString))); + connect(activities, SIGNAL(added(QString)), SIGNAL(activitiesChanged(QString))); + connect(activities, SIGNAL(added(QString)), SIGNAL(activityAdded(QString))); + connect(activities, SIGNAL(removed(QString)), SIGNAL(activitiesChanged(QString))); + connect(activities, SIGNAL(removed(QString)), SIGNAL(activityRemoved(QString))); + } #endif connect(screens(), &Screens::sizeChanged, this, &WorkspaceWrapper::virtualScreenSizeChanged); connect(screens(), &Screens::geometryChanged, this, &WorkspaceWrapper::virtualScreenGeometryChanged); @@ -101,6 +102,9 @@ GETTER(QList< KWin::Client* >, clientList) QString WorkspaceWrapper::currentActivity() const { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return QString(); + } return Activities::self()->current(); #else return QString(); @@ -110,6 +114,9 @@ QString WorkspaceWrapper::currentActivity() const QStringList WorkspaceWrapper::activityList() const { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return QStringList(); + } return Activities::self()->all(); #else return QStringList(); diff --git a/tabbox/tabbox.cpp b/tabbox/tabbox.cpp index 1bf0cc716b..311f54dcfb 100644 --- a/tabbox/tabbox.cpp +++ b/tabbox/tabbox.cpp @@ -76,7 +76,9 @@ TabBoxHandlerImpl::TabBoxHandlerImpl(TabBox* tabBox) connect(vds, SIGNAL(countChanged(uint,uint)), m_desktopFocusChain, SLOT(resize(uint,uint))); connect(vds, SIGNAL(currentChanged(uint,uint)), m_desktopFocusChain, SLOT(addDesktop(uint,uint))); #ifdef KWIN_BUILD_ACTIVITIES - connect(Activities::self(), SIGNAL(currentChanged(QString)), m_desktopFocusChain, SLOT(useChain(QString))); + if (Activities::self()) { + connect(Activities::self(), SIGNAL(currentChanged(QString)), m_desktopFocusChain, SLOT(useChain(QString))); + } #endif } diff --git a/toplevel.cpp b/toplevel.cpp index 3b07a6658b..43a3b30967 100644 --- a/toplevel.cpp +++ b/toplevel.cpp @@ -391,6 +391,9 @@ bool Toplevel::isDeleted() const bool Toplevel::isOnCurrentActivity() const { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return true; + } return isOnActivity(Activities::self()->current()); #else return true; diff --git a/useractions.cpp b/useractions.cpp index a88075dd49..428d854665 100755 --- a/useractions.cpp +++ b/useractions.cpp @@ -437,6 +437,9 @@ void UserActionsMenu::menuAboutToShow() void UserActionsMenu::showHideActivityMenu() { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return; + } const QStringList &openActivities_ = Activities::self()->running(); qCDebug(KWIN_CORE) << "activities:" << openActivities_.size(); if (openActivities_.size() < 2) { @@ -671,6 +674,9 @@ void UserActionsMenu::activityPopupAboutToShow() return; #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return; + } m_activityMenu->clear(); m_activityMenu->setPalette(m_client.data()->palette()); QAction *action = m_activityMenu->addAction(i18n("&All Activities")); @@ -781,6 +787,9 @@ void UserActionsMenu::slotSendToScreen(QAction *action) void UserActionsMenu::slotToggleOnActivity(QAction *action) { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return; + } QString activity = action->data().toString(); if (m_client.isNull()) return; diff --git a/workspace.cpp b/workspace.cpp index 5322dae28b..9568b83b04 100644 --- a/workspace.cpp +++ b/workspace.cpp @@ -143,8 +143,18 @@ Workspace::Workspace(const QString &sessionKey) #endif #ifdef KWIN_BUILD_ACTIVITIES - Activities *activities = Activities::create(this); - connect(activities, SIGNAL(currentChanged(QString)), SLOT(updateCurrentActivity(QString))); + Activities *activities = nullptr; + // HACK: do not use Activities on Wayland as it blocks the startup +#if HAVE_WAYLAND + if (kwinApp()->operationMode() == Application::OperationModeX11) { + activities = Activities::create(this); + } +#else + activities = Activities::create(this); +#endif + if (activities) { + connect(activities, SIGNAL(currentChanged(QString)), SLOT(updateCurrentActivity(QString))); + } #endif // PluginMgr needs access to the config file, so we need to wait for it for finishing @@ -975,6 +985,9 @@ AbstractClient *Workspace::findClientToActivateOnDesktop(uint desktop) void Workspace::updateCurrentActivity(const QString &new_activity) { #ifdef KWIN_BUILD_ACTIVITIES + if (!Activities::self()) { + return; + } //closeActivePopup(); ++block_focus; // TODO: Q_ASSERT( block_stacking_updates == 0 ); // Make sure stacking_order is up to date