From 3b98467ebe0e447d8343457310827e18706e9550 Mon Sep 17 00:00:00 2001 From: Maurice Kalinowski Date: Fri, 8 Apr 2016 07:39:41 +0200 Subject: winrt: Try to acquire CoreDispatcher from multiple sources When the system launches the application via different activation mode (eg. app registered for sharing) no main window will be created. Hence accessing the core window will return null and event dispatcher initialization will fail. In that case iterate through all available views and try to get access to their dispatcher to be able to invoke code on the xaml thread. Task-number: QTBUG-49276 Change-Id: I8c78baa27747a0465ff7a1b2ead6c9e03f0e05a8 Reviewed-by: Oliver Wolff --- src/corelib/kernel/qeventdispatcher_winrt.cpp | 31 +++++++++++++++++++++++++-- 1 file changed, 29 insertions(+), 2 deletions(-) (limited to 'src/corelib/kernel') diff --git a/src/corelib/kernel/qeventdispatcher_winrt.cpp b/src/corelib/kernel/qeventdispatcher_winrt.cpp index ca4ba72b66..d115a3db2a 100644 --- a/src/corelib/kernel/qeventdispatcher_winrt.cpp +++ b/src/corelib/kernel/qeventdispatcher_winrt.cpp @@ -50,6 +50,7 @@ using namespace Microsoft::WRL; using namespace Microsoft::WRL::Wrappers; using namespace ABI::Windows::System::Threading; using namespace ABI::Windows::Foundation; +using namespace ABI::Windows::Foundation::Collections; using namespace ABI::Windows::UI::Core; using namespace ABI::Windows::ApplicationModel::Core; @@ -179,8 +180,34 @@ HRESULT QEventDispatcherWinRT::runOnXamlThread(const std::function & ComPtr window; hr = view->get_CoreWindow(&window); Q_ASSERT_SUCCEEDED(hr); - hr = window->get_Dispatcher(&dispatcher); - Q_ASSERT_SUCCEEDED(hr); + if (!window) { + // In case the application is launched via activation + // there might not be a main view (eg ShareTarget). + // Hence iterate through the available views and try to find + // a dispatcher in there + ComPtr> appViews; + hr = application->get_Views(&appViews); + Q_ASSERT_SUCCEEDED(hr); + quint32 count; + hr = appViews->get_Size(&count); + Q_ASSERT_SUCCEEDED(hr); + for (quint32 i = 0; i < count; ++i) { + hr = appViews->GetAt(i, &view); + Q_ASSERT_SUCCEEDED(hr); + hr = view->get_CoreWindow(&window); + Q_ASSERT_SUCCEEDED(hr); + if (window) { + hr = window->get_Dispatcher(&dispatcher); + Q_ASSERT_SUCCEEDED(hr); + if (dispatcher) + break; + } + } + Q_ASSERT(dispatcher); + } else { + hr = window->get_Dispatcher(&dispatcher); + Q_ASSERT_SUCCEEDED(hr); + } } HRESULT hr; -- cgit v1.2.3 From dbe9a8c9696428529cacb9dd4e004db99914b56e Mon Sep 17 00:00:00 2001 From: Olivier Goffart Date: Tue, 12 Apr 2016 16:05:10 +0200 Subject: Don't copy the functor object for each signal emission The behavior was different in the variadic template code and in the C++98 code. The code without variadic template support was not copying the functor object (e.g. a lambda) before calling it. However, in the variadic template section, QtPrivate::FunctorCall::call took the functor by value instead of by reference resulting in a copy. QtPrivate::FunctorCall::call is a helper function for QtPrivate::FunctionPointer::call which is only needed for variadic template expension. [ChangeLog][QtCore][QObject] If the compiler supports variadic templates, no longer copy functor connected to a signal each time the signal is emitted. Restoring the C++98 behavior. Task-number: QTBUG-52542 Change-Id: I3ca20ef6910893b8a288e70af7de4c7b69502173 Reviewed-by: Thiago Macieira --- src/corelib/kernel/qobjectdefs_impl.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib/kernel') diff --git a/src/corelib/kernel/qobjectdefs_impl.h b/src/corelib/kernel/qobjectdefs_impl.h index d5574a4dd1..922b6bbb42 100644 --- a/src/corelib/kernel/qobjectdefs_impl.h +++ b/src/corelib/kernel/qobjectdefs_impl.h @@ -491,7 +491,7 @@ namespace QtPrivate { template struct FunctorCall; template struct FunctorCall, List, R, Function> { - static void call(Function f, void **arg) { + static void call(Function &f, void **arg) { f((*reinterpret_cast::Type *>(arg[II+1]))...), ApplyReturnValue(arg[0]); } }; -- cgit v1.2.3 From 17ad6e2a93f93aaa948c1286b3cad785e7f38808 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tor=20Arne=20Vestb=C3=B8?= Date: Wed, 13 Apr 2016 14:09:35 +0200 Subject: Fix build when Qt is used in an automatic reference-counted environment When automatic reference-counting (ARC) is enabled on Darwin platforms the NSAutoReleasePool class should not be used directly, which caused a build error if qglobal.h was included after the Foundation.h in client code. The preferred alternative for ARC is the scoped @autoreleasepool construct, which allows the compiler to reason about needing to insert _objc_autoreleasePoolPush and _objc_autoreleasePoolPop calls. Note that ARC translation units can be combined with non-ARC translation units, so Qt and the QMacAutoReleasePool class can still be used in ARC client code even if Qt is not built with ARC. Task-number: QTBUG-51332 Change-Id: I7ef1c3146aa416a9d6a1dc299ce7b17f22f889e5 Reviewed-by: Simon Hausmann Reviewed-by: Richard Moe Gustavsen --- src/corelib/kernel/qcore_mac_objc.mm | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/corelib/kernel') diff --git a/src/corelib/kernel/qcore_mac_objc.mm b/src/corelib/kernel/qcore_mac_objc.mm index 1a2b047041..e1480a36d5 100644 --- a/src/corelib/kernel/qcore_mac_objc.mm +++ b/src/corelib/kernel/qcore_mac_objc.mm @@ -150,7 +150,7 @@ QMacAutoReleasePool::~QMacAutoReleasePool() // Drain behaves the same as release, with the advantage that // if we're ever used in a garbage-collected environment, the // drain acts as a hint to the garbage collector to collect. - [pool drain]; + [static_cast(pool) drain]; } // ------------------------------------------------------------------------- -- cgit v1.2.3 From 62ad5abe0637abc742f10cc31a3faf0a2353ab2f Mon Sep 17 00:00:00 2001 From: Marc Mutz Date: Thu, 14 Apr 2016 10:00:24 +0200 Subject: QWinEventNotifier: compile with -Wzero-as-null-pointer-constant Seems to be the last 5.6 QtBase public header that didn't, paving the way to add the warning to the headersclean check. Change-Id: Ib2655782e34ec58e5d9b1b9c0ec31a965a38f9b7 Reviewed-by: Friedemann Kleint --- src/corelib/kernel/qwineventnotifier.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/corelib/kernel') diff --git a/src/corelib/kernel/qwineventnotifier.h b/src/corelib/kernel/qwineventnotifier.h index 95fdff07ce..f59754de6f 100644 --- a/src/corelib/kernel/qwineventnotifier.h +++ b/src/corelib/kernel/qwineventnotifier.h @@ -48,8 +48,8 @@ class Q_CORE_EXPORT QWinEventNotifier : public QObject typedef Qt::HANDLE HANDLE; public: - explicit QWinEventNotifier(QObject *parent = 0); - explicit QWinEventNotifier(HANDLE hEvent, QObject *parent = 0); + explicit QWinEventNotifier(QObject *parent = Q_NULLPTR); + explicit QWinEventNotifier(HANDLE hEvent, QObject *parent = Q_NULLPTR); ~QWinEventNotifier(); void setHandle(HANDLE hEvent); -- cgit v1.2.3 From cc7cd61909ad0931ea702178274b7138dd5bdf52 Mon Sep 17 00:00:00 2001 From: Alex Trotsenko Date: Sat, 9 Apr 2016 18:17:52 +0300 Subject: Improve performance of socket notifications on WinCE QEventDispatcherWin32 on WinCE uses a separate low-priority thread to monitor sockets activity, so changing the state of notifiers occurs asynchronously to the main thread. This makes a message-based socket activation mechanism ineffective. To avoid timeouts in the helper thread, update the thread's pool directly from the (un)registerSocketNotifier() functions. Change-Id: I702c32d69dce09323ca5f65dc2ee1407842e41ef Reviewed-by: Tobias Koenig Reviewed-by: Friedemann Kleint --- src/corelib/kernel/qeventdispatcher_win.cpp | 25 ++++++++++++++++++++++++- src/corelib/kernel/qeventdispatcher_win_p.h | 4 +++- 2 files changed, 27 insertions(+), 2 deletions(-) (limited to 'src/corelib/kernel') diff --git a/src/corelib/kernel/qeventdispatcher_win.cpp b/src/corelib/kernel/qeventdispatcher_win.cpp index b3df139743..31c6530e80 100644 --- a/src/corelib/kernel/qeventdispatcher_win.cpp +++ b/src/corelib/kernel/qeventdispatcher_win.cpp @@ -309,7 +309,10 @@ static void resolveTimerAPI() QEventDispatcherWin32Private::QEventDispatcherWin32Private() : threadId(GetCurrentThreadId()), interrupt(false), closingDown(false), internalHwnd(0), getMessageHook(0), serialNumber(0), lastSerialNumber(0), sendPostedEventsWindowsTimerId(0), - wakeUps(0), activateNotifiersPosted(false) + wakeUps(0) +#ifndef Q_OS_WINCE + , activateNotifiersPosted(false) +#endif { resolveTimerAPI(); } @@ -391,9 +394,11 @@ LRESULT QT_WIN_CALLBACK qt_internal_proc(HWND hwnd, UINT message, WPARAM wp, LPA QSockNot *sn = dict ? dict->value(wp) : 0; if (sn) { +#ifndef Q_OS_WINCE d->doWsaAsyncSelect(sn->fd, 0); d->active_fd[sn->fd].selected = false; d->postActivateSocketNotifiers(); +#endif if (type < 3) { QEvent event(QEvent::SockAct); QCoreApplication::sendEvent(sn->obj, &event); @@ -404,6 +409,7 @@ LRESULT QT_WIN_CALLBACK qt_internal_proc(HWND hwnd, UINT message, WPARAM wp, LPA } } return 0; +#ifndef Q_OS_WINCE } else if (message == WM_QT_ACTIVATENOTIFIERS) { Q_ASSERT(d != 0); @@ -418,6 +424,7 @@ LRESULT QT_WIN_CALLBACK qt_internal_proc(HWND hwnd, UINT message, WPARAM wp, LPA } d->activateNotifiersPosted = false; return 0; +#endif // !Q_OS_WINCE } else if (message == WM_QT_SENDPOSTEDEVENTS // we also use a Windows timer to send posted events when the message queue is full || (message == WM_TIMER @@ -658,11 +665,13 @@ void QEventDispatcherWin32Private::doWsaAsyncSelect(int socket, long event) WSAAsyncSelect(socket, internalHwnd, event ? int(WM_QT_SOCKETNOTIFIER) : 0, event); } +#ifndef Q_OS_WINCE void QEventDispatcherWin32Private::postActivateSocketNotifiers() { if (!activateNotifiersPosted) activateNotifiersPosted = PostMessage(internalHwnd, WM_QT_ACTIVATENOTIFIERS, 0, 0); } +#endif // !Q_OS_WINCE void QEventDispatcherWin32::createInternalHwnd() { @@ -920,16 +929,22 @@ void QEventDispatcherWin32::registerSocketNotifier(QSocketNotifier *notifier) QSFDict::iterator it = d->active_fd.find(sockfd); if (it != d->active_fd.end()) { QSockFd &sd = it.value(); +#ifndef Q_OS_WINCE if (sd.selected) { d->doWsaAsyncSelect(sockfd, 0); sd.selected = false; } +#endif // !Q_OS_WINCE sd.event |= event; } else { d->active_fd.insert(sockfd, QSockFd(event)); } +#ifndef Q_OS_WINCE d->postActivateSocketNotifiers(); +#else + d->doWsaAsyncSelect(sockfd, event); +#endif } void QEventDispatcherWin32::unregisterSocketNotifier(QSocketNotifier *notifier) @@ -958,6 +973,7 @@ void QEventDispatcherWin32::doUnregisterSocketNotifier(QSocketNotifier *notifier QSFDict::iterator it = d->active_fd.find(sockfd); if (it != d->active_fd.end()) { QSockFd &sd = it.value(); +#ifndef Q_OS_WINCE if (sd.selected) d->doWsaAsyncSelect(sockfd, 0); const long event[3] = { FD_READ | FD_CLOSE | FD_ACCEPT, FD_WRITE | FD_CONNECT, FD_OOB }; @@ -968,6 +984,13 @@ void QEventDispatcherWin32::doUnregisterSocketNotifier(QSocketNotifier *notifier sd.selected = false; d->postActivateSocketNotifiers(); } +#else + const long event[3] = { FD_READ | FD_CLOSE | FD_ACCEPT, FD_WRITE | FD_CONNECT, FD_OOB }; + sd.event ^= event[type]; + d->doWsaAsyncSelect(sockfd, sd.event); + if (sd.event == 0) + d->active_fd.erase(it); +#endif // !Q_OS_WINCE } QSNDict *sn_vec[3] = { &d->sn_read, &d->sn_write, &d->sn_except }; diff --git a/src/corelib/kernel/qeventdispatcher_win_p.h b/src/corelib/kernel/qeventdispatcher_win_p.h index 222562dfce..989bac3904 100644 --- a/src/corelib/kernel/qeventdispatcher_win_p.h +++ b/src/corelib/kernel/qeventdispatcher_win_p.h @@ -179,9 +179,11 @@ public: QSNDict sn_write; QSNDict sn_except; QSFDict active_fd; +#ifndef Q_OS_WINCE bool activateNotifiersPosted; - void doWsaAsyncSelect(int socket, long event); void postActivateSocketNotifiers(); +#endif + void doWsaAsyncSelect(int socket, long event); QList winEventNotifierList; void activateEventNotifier(QWinEventNotifier * wen); -- cgit v1.2.3