Merge lp:~gerboland/qtmir/frameSwapped-crash-fix into lp:qtmir

Proposed by Gerry Boland
Status: Merged
Approved by: Daniel d'Andrada
Approved revision: no longer in the source branch.
Merged at revision: 419
Proposed branch: lp:~gerboland/qtmir/frameSwapped-crash-fix
Merge into: lp:qtmir
Prerequisite: lp:~dandrader/qtmir/surfaceCursor
Diff against target: 91 lines (+25/-10)
2 files modified
src/modules/Unity/Application/mirsurfaceitem.cpp (+21/-10)
src/modules/Unity/Application/mirsurfaceitem.h (+4/-0)
To merge this branch: bzr merge lp:~gerboland/qtmir/frameSwapped-crash-fix
Reviewer Review Type Date Requested Status
Daniel d'Andrada (community) Approve
PS Jenkins bot continuous-integration Pending
Review via email: mp+278467@code.launchpad.net

This proposal supersedes a proposal from 2015-11-20.

Commit message

Manage frameSwapped signal/slot connection with MirSurface more strictly to avoid crash.

Direct Signal/slot connections across thread boundaries incur the same risks as any cross-thread calls. While connect/disconnect are thread safe methods, it is possible for a slot to be called while the slot owner is being deconstructed - and so not yet disconnected.

So watch for the Item's window change signal and disconnect signal immediately. Also move slot ownership to MirSurfaceItem to auto-disconnect more aggressively.

To post a comment you must log in.
Revision history for this message
Gerry Boland (gerboland) wrote : Posted in a previous version of this proposal

To test, run the entire UITK AP suite and verify unity8 doesn't crash.

Revision history for this message
PS Jenkins bot (ps-jenkins) wrote : Posted in a previous version of this proposal
review: Needs Fixing (continuous-integration)
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote : Posted in a previous version of this proposal
review: Needs Fixing (continuous-integration)
Revision history for this message
Daniel d'Andrada (dandrader) wrote : Posted in a previous version of this proposal

I think this code in setSurface() is now redundant:

"""
        if (m_window) {
            connect(m_window, &QQuickWindow::frameSwapped, this, &MirSurfaceItem::onCompositorSwappedBuffers,
                (Qt::ConnectionType) (Qt::DirectConnection | Qt::UniqueConnection));
        }
"""

review: Needs Fixing
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote : Posted in a previous version of this proposal
review: Needs Fixing (continuous-integration)
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote : Posted in a previous version of this proposal
review: Needs Fixing (continuous-integration)
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote : Posted in a previous version of this proposal
review: Needs Fixing (continuous-integration)
Revision history for this message
Daniel d'Andrada (dandrader) wrote : Posted in a previous version of this proposal

Code looks ok. Need to test still.

review: Approve
Revision history for this message
Daniel d'Andrada (dandrader) : Posted in a previous version of this proposal
review: Approve (code)
Revision history for this message
PS Jenkins bot (ps-jenkins) wrote : Posted in a previous version of this proposal
review: Needs Fixing (continuous-integration)
Revision history for this message
Daniel d'Andrada (dandrader) wrote : Posted in a previous version of this proposal

Run ubuntuuitoolkit autopilot3 test suite and there were no crashes (although 30 of them failed)

review: Approve
Revision history for this message
Daniel d'Andrada (dandrader) wrote :

same code, same verdict.

review: Approve
413. By Gerry Boland

Manage frameSwapped signal/slot connection with MirSurface more strictly to avoid crash.

Direct Signal/slot connections across thread boundaries incur the same risks as any cross-thread calls. While connect/disconnect are thread safe methods, it is possible for a slot to be called while the slot owner is being deconstructed - and so not yet disconnected.

So watch for the Item's window change signal and disconnect signal immediately. Also move slot ownership to MirSurfaceItem to auto-disconnect more agressively.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'src/modules/Unity/Application/mirsurfaceitem.cpp'
2--- src/modules/Unity/Application/mirsurfaceitem.cpp 2015-11-24 16:01:06 +0000
3+++ src/modules/Unity/Application/mirsurfaceitem.cpp 2015-11-24 16:01:06 +0000
4@@ -84,6 +84,7 @@
5 MirSurfaceItem::MirSurfaceItem(QQuickItem *parent)
6 : MirSurfaceItemInterface(parent)
7 , m_surface(nullptr)
8+ , m_window(nullptr)
9 , m_textureProvider(nullptr)
10 , m_lastTouchEvent(nullptr)
11 , m_lastFrameNumberRendered(nullptr)
12@@ -107,6 +108,7 @@
13
14 connect(this, &QQuickItem::activeFocusChanged, this, &MirSurfaceItem::updateMirSurfaceFocus);
15 connect(this, &QQuickItem::visibleChanged, this, &MirSurfaceItem::updateMirSurfaceVisibility);
16+ connect(this, &QQuickItem::windowChanged, this, &MirSurfaceItem::onWindowChanged);
17 }
18
19 MirSurfaceItem::~MirSurfaceItem()
20@@ -614,11 +616,6 @@
21 }
22
23 m_surface->unregisterView((qintptr)this);
24-
25- if (!m_surface->isBeingDisplayed() && window()) {
26- disconnect(window(), nullptr, m_surface, nullptr);
27- }
28-
29 unsetCursor();
30 }
31
32@@ -636,11 +633,6 @@
33 connect(m_surface, &MirSurfaceInterface::sizeChanged, this, &MirSurfaceItem::onActualSurfaceSizeChanged);
34 connect(m_surface, &MirSurfaceInterface::cursorChanged, this, &MirSurfaceItem::setCursor);
35
36- if (window()) {
37- connect(window(), &QQuickWindow::frameSwapped, m_surface, &MirSurfaceInterface::onCompositorSwappedBuffers,
38- (Qt::ConnectionType) (Qt::DirectConnection | Qt::UniqueConnection));
39- }
40-
41 Q_EMIT typeChanged(m_surface->type());
42 Q_EMIT liveChanged(true);
43 Q_EMIT surfaceStateChanged(m_surface->state());
44@@ -674,6 +666,25 @@
45 Q_EMIT surfaceChanged(m_surface);
46 }
47
48+void MirSurfaceItem::onCompositorSwappedBuffers()
49+{
50+ if (Q_LIKELY(m_surface)) {
51+ m_surface->onCompositorSwappedBuffers();
52+ }
53+}
54+
55+void MirSurfaceItem::onWindowChanged(QQuickWindow *window)
56+{
57+ if (m_window) {
58+ disconnect(m_window, nullptr, this, nullptr);
59+ }
60+ m_window = window;
61+ if (m_window) {
62+ connect(m_window, &QQuickWindow::frameSwapped, this, &MirSurfaceItem::onCompositorSwappedBuffers,
63+ Qt::DirectConnection);
64+ }
65+}
66+
67 void MirSurfaceItem::releaseResources()
68 {
69 if (m_textureProvider) {
70
71=== modified file 'src/modules/Unity/Application/mirsurfaceitem.h'
72--- src/modules/Unity/Application/mirsurfaceitem.h 2015-11-19 12:55:57 +0000
73+++ src/modules/Unity/Application/mirsurfaceitem.h 2015-11-24 16:01:06 +0000
74@@ -115,6 +115,9 @@
75 void updateMirSurfaceVisibility();
76
77 void onActualSurfaceSizeChanged(const QSize &size);
78+ void onCompositorSwappedBuffers();
79+
80+ void onWindowChanged(QQuickWindow *window);
81
82 private:
83 void ensureTextureProvider();
84@@ -131,6 +134,7 @@
85 Qt::TouchPointStates touchPointStates);
86
87 MirSurfaceInterface* m_surface;
88+ QQuickWindow* m_window;
89
90 QMutex m_mutex;
91 MirTextureProvider *m_textureProvider;

Subscribers

People subscribed via source and target branches