From 76de85b44953512957c273b29760de5c299504fd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Martin=20Gr=C3=A4=C3=9Flin?= Date: Fri, 3 Jun 2016 15:27:36 +0200 Subject: [PATCH] Don't setup PlasmaWindowManagement integration for lock screen windows Summary: We don't want external processes to know anything about the lock screen windows. Especially we don't want them to be able to request close on them. Thus better never show thus windows to them. Reviewers: #plasma Subscribers: plasma-devel Tags: #plasma Differential Revision: https://phabricator.kde.org/D1760 --- autotests/wayland/plasmawindow_test.cpp | 62 +++++++++++++++++++++++++ shell_client.cpp | 3 ++ 2 files changed, 65 insertions(+) diff --git a/autotests/wayland/plasmawindow_test.cpp b/autotests/wayland/plasmawindow_test.cpp index 25568ce0b2..d1a9f7e176 100644 --- a/autotests/wayland/plasmawindow_test.cpp +++ b/autotests/wayland/plasmawindow_test.cpp @@ -36,6 +36,8 @@ along with this program. If not, see . #include #include #include +//screenlocker +#include #include #include @@ -60,6 +62,7 @@ private Q_SLOTS: void testCreateDestroyX11PlasmaWindow(); void testInternalWindowNoPlasmaWindow(); void testPopupWindowNoPlasmaWindow(); + void testLockScreenNoPlasmaWindow(); private: ConnectionThread *m_connection = nullptr; @@ -87,6 +90,7 @@ void PlasmaWindowTest::initTestCase() QCOMPARE(screens()->geometry(0), QRect(0, 0, 1280, 1024)); QCOMPARE(screens()->geometry(1), QRect(1280, 0, 1280, 1024)); setenv("QT_QPA_PLATFORM", "wayland", true); + setenv("QMLSCENE_DEVICE", "softwarecontext", true); waylandServer()->initWorkspace(); } @@ -323,6 +327,64 @@ void PlasmaWindowTest::testPopupWindowNoPlasmaWindow() // this should not create a plasma window QEXPECT_FAIL("", "The call to setTransient comes to late the window is already mapped then", Continue); QVERIFY(!plasmaWindowCreatedSpy.wait()); + + // let's destroy the windows + QCOMPARE(waylandServer()->clients().count(), 3); + QSignalSpy destroyed1Spy(waylandServer()->clients().last(), &QObject::destroyed); + QVERIFY(destroyed1Spy.isValid()); + popup2Surface->attachBuffer(Buffer::Ptr()); + popup2Surface->commit(Surface::CommitFlag::None); + popup2ShellSurface.reset(); + popup2Surface.reset(); + QVERIFY(destroyed1Spy.wait()); + QCOMPARE(waylandServer()->clients().count(), 2); + QSignalSpy destroyed2Spy(waylandServer()->clients().last(), &QObject::destroyed); + QVERIFY(destroyed2Spy.isValid()); + popupSurface->attachBuffer(Buffer::Ptr()); + popupSurface->commit(Surface::CommitFlag::None); + popupShellSurface.reset(); + popupSurface.reset(); + QVERIFY(destroyed2Spy.wait()); + QCOMPARE(waylandServer()->clients().count(), 1); + QSignalSpy destroyed3Spy(waylandServer()->clients().last(), &QObject::destroyed); + QVERIFY(destroyed3Spy.isValid()); + parentSurface->attachBuffer(Buffer::Ptr()); + parentSurface->commit(Surface::CommitFlag::None); + parentShellSurface.reset(); + parentSurface.reset(); + QVERIFY(destroyed3Spy.wait()); +} + +void PlasmaWindowTest::testLockScreenNoPlasmaWindow() +{ + // this test verifies that lock screen windows are not exposed to PlasmaWindow + QSignalSpy plasmaWindowCreatedSpy(m_windowManagement, &PlasmaWindowManagement::windowCreated); + QVERIFY(plasmaWindowCreatedSpy.isValid()); + + // this time we use a QSignalSpy on ShellClient as it'a a little bit more complex setup + QSignalSpy clientAddedSpy(waylandServer(), &WaylandServer::shellClientAdded); + QVERIFY(clientAddedSpy.isValid()); + // lock + ScreenLocker::KSldApp::self()->lock(ScreenLocker::EstablishLock::Immediate); + QVERIFY(clientAddedSpy.wait()); + QVERIFY(clientAddedSpy.first().first().value()->isLockScreen()); + // should not be sent to the client + QVERIFY(plasmaWindowCreatedSpy.isEmpty()); + QVERIFY(!plasmaWindowCreatedSpy.wait()); + + // fake unlock + QSignalSpy lockStateChangedSpy(ScreenLocker::KSldApp::self(), &ScreenLocker::KSldApp::lockStateChanged); + QVERIFY(lockStateChangedSpy.isValid()); + const auto children = ScreenLocker::KSldApp::self()->children(); + for (auto it = children.begin(); it != children.end(); ++it) { + if (qstrcmp((*it)->metaObject()->className(), "LogindIntegration") != 0) { + continue; + } + QMetaObject::invokeMethod(*it, "requestUnlock"); + break; + } + QVERIFY(lockStateChangedSpy.wait()); + QVERIFY(!waylandServer()->isScreenLocked()); } } diff --git a/shell_client.cpp b/shell_client.cpp index 4eed1b6d36..6d7d24126b 100644 --- a/shell_client.cpp +++ b/shell_client.cpp @@ -1018,6 +1018,9 @@ bool ShellClient::shouldExposeToWindowManagement() if (isInternal()) { return false; } + if (isLockScreen()) { + return false; + } if (m_shellSurface) { if (m_shellSurface->isTransient() && !m_shellSurface->acceptsKeyboardFocus()) { return false;