Properly handle destroying a Pointer resource
Summary: On client side the newer wl_pointer_release is used which is a destructor call. On server side the shared destroy callback is used and it's ensured that KWayland doesn't crash if called into the PointerInterface between unbound and destroyed. Test Plan: Test case extended to cover the condition of an unbound PointerInterface. Reviewers: #plasma_on_wayland Subscribers: plasma-devel Tags: #plasma_on_wayland Differential Revision: https://phabricator.kde.org/D2037
This commit is contained in:
parent
0b208fcd63
commit
89a4c2f0e1
3 changed files with 47 additions and 10 deletions
|
@ -466,11 +466,56 @@ void TestWaylandSeat::testPointer()
|
|||
QCOMPARE(p->enteredSurface(), s);
|
||||
QCOMPARE(cp.enteredSurface(), s);
|
||||
|
||||
// destroy the focused pointer
|
||||
QSignalSpy unboundSpy(serverPointer, &Resource::unbound);
|
||||
QVERIFY(unboundSpy.isValid());
|
||||
QSignalSpy destroyedSpy(serverPointer, &Resource::destroyed);
|
||||
QVERIFY(destroyedSpy.isValid());
|
||||
delete p;
|
||||
QVERIFY(unboundSpy.wait());
|
||||
QCOMPARE(unboundSpy.count(), 1);
|
||||
QCOMPARE(destroyedSpy.count(), 0);
|
||||
// now test that calling into the methods in Seat does not crash
|
||||
QCOMPARE(m_seatInterface->focusedPointer(), serverPointer);
|
||||
QCOMPARE(m_seatInterface->focusedPointerSurface(), serverSurface);
|
||||
m_seatInterface->setTimestamp(8);
|
||||
m_seatInterface->setPointerPos(QPoint(10, 15));
|
||||
m_seatInterface->setTimestamp(9);
|
||||
m_seatInterface->pointerButtonPressed(1);
|
||||
m_seatInterface->setTimestamp(10);
|
||||
m_seatInterface->pointerButtonReleased(1);
|
||||
m_seatInterface->setTimestamp(11);
|
||||
m_seatInterface->pointerAxis(Qt::Horizontal, 10);
|
||||
m_seatInterface->setTimestamp(12);
|
||||
m_seatInterface->pointerAxis(Qt::Vertical, 20);
|
||||
m_seatInterface->setFocusedPointerSurface(nullptr);
|
||||
QCOMPARE(focusedPointerChangedSpy.count(), 7);
|
||||
m_seatInterface->setFocusedPointerSurface(serverSurface);
|
||||
QCOMPARE(focusedPointerChangedSpy.count(), 8);
|
||||
QCOMPARE(m_seatInterface->focusedPointerSurface(), serverSurface);
|
||||
QVERIFY(!m_seatInterface->focusedPointer());
|
||||
|
||||
// and now destroy
|
||||
QVERIFY(destroyedSpy.wait());
|
||||
QCOMPARE(unboundSpy.count(), 1);
|
||||
QCOMPARE(destroyedSpy.count(), 1);
|
||||
QCOMPARE(m_seatInterface->focusedPointerSurface(), serverSurface);
|
||||
QVERIFY(!m_seatInterface->focusedPointer());
|
||||
|
||||
// create a pointer again
|
||||
p = m_seat->createPointer(m_seat);
|
||||
QVERIFY(focusedPointerChangedSpy.wait());
|
||||
QCOMPARE(focusedPointerChangedSpy.count(), 9);
|
||||
QCOMPARE(m_seatInterface->focusedPointerSurface(), serverSurface);
|
||||
serverPointer = m_seatInterface->focusedPointer();
|
||||
QVERIFY(serverPointer);
|
||||
|
||||
delete s;
|
||||
wl_display_flush(m_connection->display());
|
||||
QVERIFY(focusedPointerChangedSpy.wait());
|
||||
QCOMPARE(focusedPointerChangedSpy.count(), 7);
|
||||
QCOMPARE(focusedPointerChangedSpy.count(), 10);
|
||||
QVERIFY(!m_seatInterface->focusedPointerSurface());
|
||||
QVERIFY(!m_seatInterface->focusedPointer());
|
||||
}
|
||||
|
||||
void TestWaylandSeat::testPointerTransformation_data()
|
||||
|
|
|
@ -100,7 +100,7 @@ void PointerInterface::Private::sendEnter(SurfaceInterface *surface, const QPoin
|
|||
#ifndef DOXYGEN_SHOULD_SKIP_THIS
|
||||
const struct wl_pointer_interface PointerInterface::Private::s_interface = {
|
||||
setCursorCallback,
|
||||
releaseCallback
|
||||
resourceDestroyedCallback
|
||||
};
|
||||
#endif
|
||||
|
||||
|
@ -205,12 +205,6 @@ void PointerInterface::Private::setCursorCallback(wl_client *client, wl_resource
|
|||
p->setCursor(serial, SurfaceInterface::get(surface), QPoint(hotspot_x, hotspot_y));
|
||||
}
|
||||
|
||||
void PointerInterface::Private::releaseCallback(wl_client *client, wl_resource *resource)
|
||||
{
|
||||
Q_UNUSED(client)
|
||||
unbind(resource);
|
||||
}
|
||||
|
||||
Cursor *PointerInterface::cursor() const
|
||||
{
|
||||
Q_D();
|
||||
|
|
|
@ -51,8 +51,6 @@ private:
|
|||
// interface
|
||||
static void setCursorCallback(wl_client *client, wl_resource *resource, uint32_t serial,
|
||||
wl_resource *surface, int32_t hotspot_x, int32_t hotspot_y);
|
||||
// since version 3
|
||||
static void releaseCallback(wl_client *client, wl_resource *resource);
|
||||
|
||||
static const struct wl_pointer_interface s_interface;
|
||||
};
|
||||
|
|
Loading…
Reference in a new issue