diff options
author | Liang Qi <liang.qi@theqtcompany.com> | 2015-10-14 15:45:35 +0200 |
---|---|---|
committer | Liang Qi <liang.qi@theqtcompany.com> | 2015-10-14 15:45:35 +0200 |
commit | 4456984da780b14572e1ec0f079a4d349ab299bd (patch) | |
tree | f586a281a81c57c91c49e83a5d3ec6c7eece0578 /src/platformsupport | |
parent | e824abd987d77efaa085fe1f9fb514d270798d55 (diff) | |
parent | 281121697340084f7d385eab530f41916789b94d (diff) |
Merge remote-tracking branch 'origin/5.6' into dev
Conflicts:
tests/auto/corelib/io/qfile/tst_qfile.cpp
tests/auto/corelib/io/qprocess/tst_qprocess.cpp
tests/auto/corelib/tools/qversionnumber/qversionnumber.pro
Change-Id: Ia93ce500349d96a2fbf0b4a37b73f088cc505c6e
Diffstat (limited to 'src/platformsupport')
27 files changed, 327 insertions, 141 deletions
diff --git a/src/platformsupport/accessibility/qaccessiblebridgeutils_p.h b/src/platformsupport/accessibility/qaccessiblebridgeutils_p.h index fca3e16a68..4e52e4b6fc 100644 --- a/src/platformsupport/accessibility/qaccessiblebridgeutils_p.h +++ b/src/platformsupport/accessibility/qaccessiblebridgeutils_p.h @@ -34,6 +34,17 @@ #ifndef QACCESSIBLEBRIDGEUTILS_H #define QACCESSIBLEBRIDGEUTILS_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists for the convenience +// of other Qt classes. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #include <QtCore/qstringlist.h> #include <QtGui/qaccessible.h> diff --git a/src/platformsupport/cfsocketnotifier/qcfsocketnotifier.cpp b/src/platformsupport/cfsocketnotifier/qcfsocketnotifier.cpp index 2b5723d827..c58e0ea78d 100644 --- a/src/platformsupport/cfsocketnotifier/qcfsocketnotifier.cpp +++ b/src/platformsupport/cfsocketnotifier/qcfsocketnotifier.cpp @@ -55,11 +55,15 @@ void qt_mac_socket_callback(CFSocketRef s, CFSocketCallBackType callbackType, CF // notifier is now gone. The upshot is we have to check the notifier // every time. if (callbackType == kCFSocketReadCallBack) { - if (socketInfo->readNotifier) + if (socketInfo->readNotifier && socketInfo->readEnabled) { + socketInfo->readEnabled = false; QGuiApplication::sendEvent(socketInfo->readNotifier, ¬ifierEvent); + } } else if (callbackType == kCFSocketWriteCallBack) { - if (socketInfo->writeNotifier) + if (socketInfo->writeNotifier && socketInfo->writeEnabled) { + socketInfo->writeEnabled = false; QGuiApplication::sendEvent(socketInfo->writeNotifier, ¬ifierEvent); + } } if (cfSocketNotifier->maybeCancelWaitForMoreEvents) @@ -88,12 +92,12 @@ void qt_mac_remove_socket_from_runloop(const CFSocketRef socket, CFRunLoopSource CFRunLoopRemoveSource(CFRunLoopGetMain(), runloop, kCFRunLoopCommonModes); CFSocketDisableCallBacks(socket, kCFSocketReadCallBack); CFSocketDisableCallBacks(socket, kCFSocketWriteCallBack); - CFRunLoopSourceInvalidate(runloop); } QCFSocketNotifier::QCFSocketNotifier() -:eventDispatcher(0) -, maybeCancelWaitForMoreEvents(0) + : eventDispatcher(0) + , maybeCancelWaitForMoreEvents(0) + , enableNotifiersObserver(0) { } @@ -150,36 +154,34 @@ void QCFSocketNotifier::registerSocketNotifier(QSocketNotifier *notifier) } CFOptionFlags flags = CFSocketGetSocketFlags(socketInfo->socket); - flags |= kCFSocketAutomaticallyReenableWriteCallBack; //QSocketNotifier stays enabled after a write - flags &= ~kCFSocketCloseOnInvalidate; //QSocketNotifier doesn't close the socket upon destruction/invalidation + // QSocketNotifier doesn't close the socket upon destruction/invalidation + flags &= ~kCFSocketCloseOnInvalidate; + // Expicitly disable automatic re-enable, as we do that manually on each runloop pass + flags &= ~(kCFSocketAutomaticallyReenableWriteCallBack | kCFSocketAutomaticallyReenableReadCallBack); CFSocketSetSocketFlags(socketInfo->socket, flags); - // Add CFSocket to runloop. - if (!(socketInfo->runloop = qt_mac_add_socket_to_runloop(socketInfo->socket))) { - qWarning("QEventDispatcherMac::registerSocketNotifier: Failed to add CFSocket to runloop"); - CFSocketInvalidate(socketInfo->socket); - CFRelease(socketInfo->socket); - return; - } - - // Disable both callback types by default. This must be done after - // we add the CFSocket to the runloop, or else these calls will have - // no effect. - CFSocketDisableCallBacks(socketInfo->socket, kCFSocketReadCallBack); - CFSocketDisableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); - macSockets.insert(nativeSocket, socketInfo); } - // Increment read/write counters and select enable callbacks if necessary. if (type == QSocketNotifier::Read) { Q_ASSERT(socketInfo->readNotifier == 0); socketInfo->readNotifier = notifier; - CFSocketEnableCallBacks(socketInfo->socket, kCFSocketReadCallBack); + socketInfo->readEnabled = false; } else if (type == QSocketNotifier::Write) { Q_ASSERT(socketInfo->writeNotifier == 0); socketInfo->writeNotifier = notifier; - CFSocketEnableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); + socketInfo->writeEnabled = false; + } + + if (!enableNotifiersObserver) { + // Create a run loop observer which enables the socket notifiers on each + // pass of the run loop, before any sources are processed. + CFRunLoopObserverContext context = {}; + context.info = this; + enableNotifiersObserver = CFRunLoopObserverCreate(kCFAllocatorDefault, kCFRunLoopBeforeSources, + true, 0, enableSocketNotifiers, &context); + Q_ASSERT(enableNotifiersObserver); + CFRunLoopAddObserver(CFRunLoopGetMain(), enableNotifiersObserver, kCFRunLoopCommonModes); } } @@ -212,21 +214,18 @@ void QCFSocketNotifier::unregisterSocketNotifier(QSocketNotifier *notifier) if (type == QSocketNotifier::Read) { Q_ASSERT(notifier == socketInfo->readNotifier); socketInfo->readNotifier = 0; + socketInfo->readEnabled = false; CFSocketDisableCallBacks(socketInfo->socket, kCFSocketReadCallBack); } else if (type == QSocketNotifier::Write) { Q_ASSERT(notifier == socketInfo->writeNotifier); socketInfo->writeNotifier = 0; + socketInfo->writeEnabled = false; CFSocketDisableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); } // Remove CFSocket from runloop if this was the last QSocketNotifier. if (socketInfo->readNotifier == 0 && socketInfo->writeNotifier == 0) { - if (CFSocketIsValid(socketInfo->socket)) - qt_mac_remove_socket_from_runloop(socketInfo->socket, socketInfo->runloop); - CFRunLoopSourceInvalidate(socketInfo->runloop); - CFRelease(socketInfo->runloop); - CFSocketInvalidate(socketInfo->socket); - CFRelease(socketInfo->socket); + unregisterSocketInfo(socketInfo); delete socketInfo; macSockets.remove(nativeSocket); } @@ -235,14 +234,70 @@ void QCFSocketNotifier::unregisterSocketNotifier(QSocketNotifier *notifier) void QCFSocketNotifier::removeSocketNotifiers() { // Remove CFSockets from the runloop. - for (MacSocketHash::ConstIterator it = macSockets.constBegin(); it != macSockets.constEnd(); ++it) { - MacSocketInfo *socketInfo = (*it); - if (CFSocketIsValid(socketInfo->socket)) { + foreach (MacSocketInfo *socketInfo, macSockets) { + unregisterSocketInfo(socketInfo); + delete socketInfo; + } + + macSockets.clear(); + + destroyRunLoopObserver(); +} + +void QCFSocketNotifier::destroyRunLoopObserver() +{ + if (!enableNotifiersObserver) + return; + + CFRunLoopObserverInvalidate(enableNotifiersObserver); + CFRelease(enableNotifiersObserver); + enableNotifiersObserver = 0; +} + +void QCFSocketNotifier::unregisterSocketInfo(MacSocketInfo *socketInfo) +{ + if (socketInfo->runloop) { + if (CFSocketIsValid(socketInfo->socket)) qt_mac_remove_socket_from_runloop(socketInfo->socket, socketInfo->runloop); - CFRunLoopSourceInvalidate(socketInfo->runloop); - CFRelease(socketInfo->runloop); - CFSocketInvalidate(socketInfo->socket); - CFRelease(socketInfo->socket); + CFRunLoopSourceInvalidate(socketInfo->runloop); + CFRelease(socketInfo->runloop); + } + CFSocketInvalidate(socketInfo->socket); + CFRelease(socketInfo->socket); +} + +void QCFSocketNotifier::enableSocketNotifiers(CFRunLoopObserverRef ref, CFRunLoopActivity activity, void *info) +{ + Q_UNUSED(ref); + Q_UNUSED(activity); + + QCFSocketNotifier *that = static_cast<QCFSocketNotifier *>(info); + + foreach (MacSocketInfo *socketInfo, that->macSockets) { + if (!CFSocketIsValid(socketInfo->socket)) + continue; + + if (!socketInfo->runloop) { + // Add CFSocket to runloop. + if (!(socketInfo->runloop = qt_mac_add_socket_to_runloop(socketInfo->socket))) { + qWarning("QEventDispatcherMac::registerSocketNotifier: Failed to add CFSocket to runloop"); + CFSocketInvalidate(socketInfo->socket); + continue; + } + + if (!socketInfo->readNotifier) + CFSocketDisableCallBacks(socketInfo->socket, kCFSocketReadCallBack); + if (!socketInfo->writeNotifier) + CFSocketDisableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); + } + + if (socketInfo->readNotifier && !socketInfo->readEnabled) { + socketInfo->readEnabled = true; + CFSocketEnableCallBacks(socketInfo->socket, kCFSocketReadCallBack); + } + if (socketInfo->writeNotifier && !socketInfo->writeEnabled) { + socketInfo->writeEnabled = true; + CFSocketEnableCallBacks(socketInfo->socket, kCFSocketWriteCallBack); } } } diff --git a/src/platformsupport/cfsocketnotifier/qcfsocketnotifier_p.h b/src/platformsupport/cfsocketnotifier/qcfsocketnotifier_p.h index af8122f753..9bccc1bf98 100644 --- a/src/platformsupport/cfsocketnotifier/qcfsocketnotifier_p.h +++ b/src/platformsupport/cfsocketnotifier/qcfsocketnotifier_p.h @@ -53,11 +53,14 @@ QT_BEGIN_NAMESPACE struct MacSocketInfo { - MacSocketInfo() : socket(0), runloop(0), readNotifier(0), writeNotifier(0) {} + MacSocketInfo() : socket(0), runloop(0), readNotifier(0), writeNotifier(0), + readEnabled(false), writeEnabled(false) {} CFSocketRef socket; CFRunLoopSourceRef runloop; QObject *readNotifier; QObject *writeNotifier; + bool readEnabled; + bool writeEnabled; }; typedef QHash<int, MacSocketInfo *> MacSocketHash; @@ -83,9 +86,18 @@ public: void unregisterSocketNotifier(QSocketNotifier *notifier); void removeSocketNotifiers(); +private: + void destroyRunLoopObserver(); + + static void unregisterSocketInfo(MacSocketInfo *socketInfo); + static void enableSocketNotifiers(CFRunLoopObserverRef ref, CFRunLoopActivity activity, void *info); + MacSocketHash macSockets; QAbstractEventDispatcher *eventDispatcher; MaybeCancelWaitForMoreEventsFn maybeCancelWaitForMoreEvents; + CFRunLoopObserverRef enableNotifiersObserver; + + friend void qt_mac_socket_callback(CFSocketRef, CFSocketCallBackType, CFDataRef, const void *, void *); }; QT_END_NAMESPACE diff --git a/src/platformsupport/dbusmenu/qdbusmenuadaptor_p.h b/src/platformsupport/dbusmenu/qdbusmenuadaptor_p.h index 85b5bd8d49..41ab761f12 100644 --- a/src/platformsupport/dbusmenu/qdbusmenuadaptor_p.h +++ b/src/platformsupport/dbusmenu/qdbusmenuadaptor_p.h @@ -45,6 +45,17 @@ #ifndef DBUSMENUADAPTOR_H #define DBUSMENUADAPTOR_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #include <QtCore/QObject> #include <QtDBus/QtDBus> #include "qdbusmenutypes_p.h" diff --git a/src/platformsupport/dbusmenu/qdbusmenutypes.cpp b/src/platformsupport/dbusmenu/qdbusmenutypes.cpp index 94df0f53dd..8d5d96353c 100644 --- a/src/platformsupport/dbusmenu/qdbusmenutypes.cpp +++ b/src/platformsupport/dbusmenu/qdbusmenutypes.cpp @@ -247,7 +247,7 @@ QDebug operator<<(QDebug d, const QDBusMenuItem &item) { QDebugStateSaver saver(d); d.nospace(); - d << "QDBusMenuItem(id=" << item.m_id << ", properties=" << item.m_properties << ")"; + d << "QDBusMenuItem(id=" << item.m_id << ", properties=" << item.m_properties << ')'; return d; } diff --git a/src/platformsupport/dbusmenu/qdbusmenutypes_p.h b/src/platformsupport/dbusmenu/qdbusmenutypes_p.h index 8dae75281c..bc9f064f88 100644 --- a/src/platformsupport/dbusmenu/qdbusmenutypes_p.h +++ b/src/platformsupport/dbusmenu/qdbusmenutypes_p.h @@ -34,6 +34,17 @@ #ifndef QDBUSMENUTYPES_H #define QDBUSMENUTYPES_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists for the convenience +// of other Qt classes. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #include <QObject> #include <QString> #include <QDBusArgument> diff --git a/src/platformsupport/dbusmenu/qdbusplatformmenu.cpp b/src/platformsupport/dbusmenu/qdbusplatformmenu.cpp index a64e107e71..1dd2b462ed 100644 --- a/src/platformsupport/dbusmenu/qdbusplatformmenu.cpp +++ b/src/platformsupport/dbusmenu/qdbusplatformmenu.cpp @@ -59,6 +59,11 @@ QDBusPlatformMenuItem::QDBusPlatformMenuItem(quintptr tag) menuItemsByID.insert(m_dbusID, this); } +QDBusPlatformMenuItem::~QDBusPlatformMenuItem() +{ + menuItemsByID.remove(m_dbusID); +} + void QDBusPlatformMenuItem::setTag(quintptr tag) { m_tag = tag; @@ -155,6 +160,7 @@ QDBusPlatformMenu::QDBusPlatformMenu(quintptr tag) QDBusPlatformMenu::~QDBusPlatformMenu() { menusByID.remove(m_dbusID); + m_topLevelMenus.removeOne(this); } void QDBusPlatformMenu::insertMenuItem(QPlatformMenuItem *menuItem, QPlatformMenuItem *before) diff --git a/src/platformsupport/dbusmenu/qdbusplatformmenu_p.h b/src/platformsupport/dbusmenu/qdbusplatformmenu_p.h index 16bb4f195c..6d2d27463f 100644 --- a/src/platformsupport/dbusmenu/qdbusplatformmenu_p.h +++ b/src/platformsupport/dbusmenu/qdbusplatformmenu_p.h @@ -33,6 +33,17 @@ #ifndef QDBUSPLATFORMMENU_H #define QDBUSPLATFORMMENU_H + +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// // // W A R N I N G // ------------- @@ -57,6 +68,7 @@ class QDBusPlatformMenuItem : public QPlatformMenuItem public: QDBusPlatformMenuItem(quintptr tag = 0LL); + ~QDBusPlatformMenuItem(); quintptr tag()const Q_DECL_OVERRIDE { return m_tag; } void setTag(quintptr tag) Q_DECL_OVERRIDE; diff --git a/src/platformsupport/dbustray/qdbustraytypes_p.h b/src/platformsupport/dbustray/qdbustraytypes_p.h index e6f200362f..d8e52b932d 100644 --- a/src/platformsupport/dbustray/qdbustraytypes_p.h +++ b/src/platformsupport/dbustray/qdbustraytypes_p.h @@ -35,6 +35,17 @@ #ifndef QDBUSTRAYTYPES_P_H #define QDBUSTRAYTYPES_P_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists for the convenience +// of other Qt classes. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #ifndef QT_NO_SYSTEMTRAYICON #include <QObject> diff --git a/src/platformsupport/dbustray/qstatusnotifieritemadaptor_p.h b/src/platformsupport/dbustray/qstatusnotifieritemadaptor_p.h index 56fbb75d7a..c3849f0e03 100644 --- a/src/platformsupport/dbustray/qstatusnotifieritemadaptor_p.h +++ b/src/platformsupport/dbustray/qstatusnotifieritemadaptor_p.h @@ -45,6 +45,17 @@ #ifndef QSTATUSNOTIFIERITEMADAPTER_P_H #define QSTATUSNOTIFIERITEMADAPTER_P_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #ifndef QT_NO_SYSTEMTRAYICON #include <QtCore/QObject> diff --git a/src/platformsupport/dbustray/qxdgnotificationproxy_p.h b/src/platformsupport/dbustray/qxdgnotificationproxy_p.h index 3e573cb118..5c74405ae8 100644 --- a/src/platformsupport/dbustray/qxdgnotificationproxy_p.h +++ b/src/platformsupport/dbustray/qxdgnotificationproxy_p.h @@ -45,6 +45,17 @@ #ifndef QXDGNOTIFICATIONPROXY_P_H #define QXDGNOTIFICATIONPROXY_P_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists for the convenience +// of other Qt classes. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #include <QtCore/QObject> #include <QtCore/QByteArray> #include <QtCore/QList> diff --git a/src/platformsupport/devicediscovery/qdevicediscovery_static.cpp b/src/platformsupport/devicediscovery/qdevicediscovery_static.cpp index 1bc834b5ef..3aab785b34 100644 --- a/src/platformsupport/devicediscovery/qdevicediscovery_static.cpp +++ b/src/platformsupport/devicediscovery/qdevicediscovery_static.cpp @@ -90,7 +90,7 @@ QStringList QDeviceDiscoveryStatic::scanConnectedDevices() if (m_types & Device_InputMask) { dir.setPath(QString::fromLatin1(QT_EVDEV_DEVICE_PATH)); foreach (const QString &deviceFile, dir.entryList()) { - QString absoluteFilePath = dir.absolutePath() + QString::fromLatin1("/") + deviceFile; + QString absoluteFilePath = dir.absolutePath() + QLatin1Char('/') + deviceFile; if (checkDeviceType(absoluteFilePath)) devices << absoluteFilePath; } @@ -100,7 +100,7 @@ QStringList QDeviceDiscoveryStatic::scanConnectedDevices() if (m_types & Device_VideoMask) { dir.setPath(QString::fromLatin1(QT_DRM_DEVICE_PATH)); foreach (const QString &deviceFile, dir.entryList()) { - QString absoluteFilePath = dir.absolutePath() + QString::fromLatin1("/") + deviceFile; + QString absoluteFilePath = dir.absolutePath() + QLatin1Char('/') + deviceFile; if (checkDeviceType(absoluteFilePath)) devices << absoluteFilePath; } diff --git a/src/platformsupport/devicediscovery/qdevicediscovery_udev.cpp b/src/platformsupport/devicediscovery/qdevicediscovery_udev.cpp index 96fa058f78..334eb51a86 100644 --- a/src/platformsupport/devicediscovery/qdevicediscovery_udev.cpp +++ b/src/platformsupport/devicediscovery/qdevicediscovery_udev.cpp @@ -210,7 +210,7 @@ bool QDeviceDiscoveryUDev::checkDeviceType(udev_device *dev) if ((m_types & Device_Keyboard) && (qstrcmp(udev_device_get_property_value(dev, "ID_INPUT_KEYBOARD"), "1") == 0 )) { const char *capabilities_key = udev_device_get_sysattr_value(dev, "capabilities/key"); - QStringList val = QString::fromUtf8(capabilities_key).split(QString::fromUtf8(" "), QString::SkipEmptyParts); + QStringList val = QString::fromUtf8(capabilities_key).split(QLatin1Char(' '), QString::SkipEmptyParts); if (!val.isEmpty()) { bool ok; unsigned long long keys = val.last().toULongLong(&ok, 16); diff --git a/src/platformsupport/eglconvenience/qeglconvenience_p.h b/src/platformsupport/eglconvenience/qeglconvenience_p.h index 59441d8c9a..ec6f668cba 100644 --- a/src/platformsupport/eglconvenience/qeglconvenience_p.h +++ b/src/platformsupport/eglconvenience/qeglconvenience_p.h @@ -88,7 +88,6 @@ public: protected: virtual bool filterConfig(EGLConfig config) const; -private: QSurfaceFormat m_format; EGLDisplay m_display; EGLint m_surfaceType; diff --git a/src/platformsupport/eglconvenience/qeglpbuffer.cpp b/src/platformsupport/eglconvenience/qeglpbuffer.cpp index 756609a641..d1a31642b2 100644 --- a/src/platformsupport/eglconvenience/qeglpbuffer.cpp +++ b/src/platformsupport/eglconvenience/qeglpbuffer.cpp @@ -49,13 +49,15 @@ QT_BEGIN_NAMESPACE and return a new instance of this class. */ -QEGLPbuffer::QEGLPbuffer(EGLDisplay display, const QSurfaceFormat &format, QOffscreenSurface *offscreenSurface) +QEGLPbuffer::QEGLPbuffer(EGLDisplay display, const QSurfaceFormat &format, QOffscreenSurface *offscreenSurface, + QEGLPlatformContext::Flags flags) : QPlatformOffscreenSurface(offscreenSurface) , m_format(format) , m_display(display) , m_pbuffer(EGL_NO_SURFACE) { - bool hasSurfaceless = q_hasEglExtension(display, "EGL_KHR_surfaceless_context"); + bool hasSurfaceless = !flags.testFlag(QEGLPlatformContext::NoSurfaceless) + && q_hasEglExtension(display, "EGL_KHR_surfaceless_context"); // Disable surfaceless contexts on Mesa for now. As of 10.6.0 and Intel at least, some // operations (glReadPixels) are unable to work without a surface since they at some diff --git a/src/platformsupport/eglconvenience/qeglpbuffer_p.h b/src/platformsupport/eglconvenience/qeglpbuffer_p.h index 3372c0735d..81fdab8901 100644 --- a/src/platformsupport/eglconvenience/qeglpbuffer_p.h +++ b/src/platformsupport/eglconvenience/qeglpbuffer_p.h @@ -47,13 +47,15 @@ #include <EGL/egl.h> #include <qpa/qplatformoffscreensurface.h> +#include <QtPlatformSupport/private/qeglplatformcontext_p.h> QT_BEGIN_NAMESPACE class QEGLPbuffer : public QPlatformOffscreenSurface { public: - QEGLPbuffer(EGLDisplay display, const QSurfaceFormat &format, QOffscreenSurface *offscreenSurface); + QEGLPbuffer(EGLDisplay display, const QSurfaceFormat &format, QOffscreenSurface *offscreenSurface, + QEGLPlatformContext::Flags flags = 0); ~QEGLPbuffer(); QSurfaceFormat format() const Q_DECL_OVERRIDE { return m_format; } diff --git a/src/platformsupport/eglconvenience/qeglplatformcontext.cpp b/src/platformsupport/eglconvenience/qeglplatformcontext.cpp index 905f7695bb..acd6197ed5 100644 --- a/src/platformsupport/eglconvenience/qeglplatformcontext.cpp +++ b/src/platformsupport/eglconvenience/qeglplatformcontext.cpp @@ -39,6 +39,10 @@ #include <QtPlatformHeaders/QEGLNativeContext> #include <QDebug> +#ifdef Q_OS_ANDROID +#include <QtCore/private/qjnihelpers_p.h> +#endif + QT_BEGIN_NAMESPACE /*! @@ -102,11 +106,12 @@ QT_BEGIN_NAMESPACE #endif QEGLPlatformContext::QEGLPlatformContext(const QSurfaceFormat &format, QPlatformOpenGLContext *share, EGLDisplay display, - EGLConfig *config, const QVariant &nativeHandle) + EGLConfig *config, const QVariant &nativeHandle, Flags flags) : m_eglDisplay(display) , m_swapInterval(-1) , m_swapIntervalEnvChecked(false) , m_swapIntervalFromEnv(-1) + , m_flags(flags) { if (nativeHandle.isNull()) { m_eglConfig = config ? *config : q_configFromGLFormat(display, format); @@ -287,7 +292,7 @@ void QEGLPlatformContext::updateFormatFromGL() // drivers (Mesa) when certain attributes are present (multisampling). EGLSurface tempSurface = EGL_NO_SURFACE; EGLContext tempContext = EGL_NO_CONTEXT; - if (!q_hasEglExtension(m_eglDisplay, "EGL_KHR_surfaceless_context")) + if (m_flags.testFlag(NoSurfaceless) || !q_hasEglExtension(m_eglDisplay, "EGL_KHR_surfaceless_context")) tempSurface = createTemporaryOffscreenSurface(); EGLBoolean ok = eglMakeCurrent(m_eglDisplay, tempSurface, tempSurface, m_eglContext); @@ -305,6 +310,14 @@ void QEGLPlatformContext::updateFormatFromGL() QByteArray version = QByteArray(reinterpret_cast<const char *>(s)); int major, minor; if (QPlatformOpenGLContext::parseOpenGLVersion(version, major, minor)) { +#ifdef Q_OS_ANDROID + // Some Android 4.2.2 devices report OpenGL ES 3.0 without the functions being available. + static int apiLevel = QtAndroidPrivate::androidSdkVersion(); + if (apiLevel <= 17 && major >= 3) { + major = 2; + minor = 0; + } +#endif m_format.setMajorVersion(major); m_format.setMinorVersion(minor); } diff --git a/src/platformsupport/eglconvenience/qeglplatformcontext_p.h b/src/platformsupport/eglconvenience/qeglplatformcontext_p.h index 2ab7ad28d0..2fa465556b 100644 --- a/src/platformsupport/eglconvenience/qeglplatformcontext_p.h +++ b/src/platformsupport/eglconvenience/qeglplatformcontext_p.h @@ -56,8 +56,14 @@ QT_BEGIN_NAMESPACE class QEGLPlatformContext : public QPlatformOpenGLContext { public: + enum Flag { + NoSurfaceless = 0x01 + }; + Q_DECLARE_FLAGS(Flags, Flag) + QEGLPlatformContext(const QSurfaceFormat &format, QPlatformOpenGLContext *share, EGLDisplay display, - EGLConfig *config = 0, const QVariant &nativeHandle = QVariant()); + EGLConfig *config = 0, const QVariant &nativeHandle = QVariant(), + Flags flags = 0); ~QEGLPlatformContext(); void initialize() Q_DECL_OVERRIDE; @@ -93,10 +99,13 @@ private: int m_swapInterval; bool m_swapIntervalEnvChecked; int m_swapIntervalFromEnv; + Flags m_flags; bool m_ownsContext; QVector<EGLint> m_contextAttrs; }; +Q_DECLARE_OPERATORS_FOR_FLAGS(QEGLPlatformContext::Flags) + QT_END_NAMESPACE #endif //QEGLPLATFORMCONTEXT_H diff --git a/src/platformsupport/eventdispatchers/qeventdispatcher_cf.mm b/src/platformsupport/eventdispatchers/qeventdispatcher_cf.mm index 13b7dc4358..0273fe5ed4 100644 --- a/src/platformsupport/eventdispatchers/qeventdispatcher_cf.mm +++ b/src/platformsupport/eventdispatchers/qeventdispatcher_cf.mm @@ -41,8 +41,6 @@ #include <QtCore/private/qcore_mac_p.h> #include <QtCore/private/qthread_p.h> -#include <qpa/qwindowsysteminterface.h> - #include <limits> #include <UIKit/UIApplication.h> @@ -169,6 +167,7 @@ static const CFTimeInterval kCFTimeIntervalDistantFuture = std::numeric_limits<C QEventDispatcherCoreFoundation::QEventDispatcherCoreFoundation(QObject *parent) : QAbstractEventDispatcher(parent) + , m_processEvents(QEventLoop::EventLoopExec) , m_postedEventsRunLoopSource(this, &QEventDispatcherCoreFoundation::processPostedEvents) , m_runLoopActivityObserver(this, &QEventDispatcherCoreFoundation::handleRunLoopActivity, #if DEBUG_EVENT_DISPATCHER @@ -181,7 +180,6 @@ QEventDispatcherCoreFoundation::QEventDispatcherCoreFoundation(QObject *parent) , m_runLoopTimer(0) , m_blockedRunLoopTimer(0) , m_overdueTimerScheduled(false) - , m_processEvents(QEventLoop::EventLoopExec) { m_cfSocketNotifier.setHostEventDispatcher(this); @@ -371,11 +369,11 @@ bool QEventDispatcherCoreFoundation::processEvents(QEventLoop::ProcessEventsFlag return eventsProcessed; } -void QEventDispatcherCoreFoundation::processPostedEvents() +bool QEventDispatcherCoreFoundation::processPostedEvents() { if (m_processEvents.processedPostedEvents && !(m_processEvents.flags & QEventLoop::EventLoopExec)) { qEventDispatcherDebug() << "Already processed events this pass"; - return; + return false; } m_processEvents.processedPostedEvents = true; @@ -384,9 +382,7 @@ void QEventDispatcherCoreFoundation::processPostedEvents() QCoreApplication::sendPostedEvents(); qUnIndent(); - qEventDispatcherDebug() << "Sending window system events for " << m_processEvents.flags; qIndent(); - QWindowSystemInterface::sendWindowSystemEvents(m_processEvents.flags); - qUnIndent(); + return true; } void QEventDispatcherCoreFoundation::processTimers(CFRunLoopTimerRef timer) diff --git a/src/platformsupport/eventdispatchers/qeventdispatcher_cf_p.h b/src/platformsupport/eventdispatchers/qeventdispatcher_cf_p.h index 1cd9ae4ebf..2fe5dea3d8 100644 --- a/src/platformsupport/eventdispatchers/qeventdispatcher_cf_p.h +++ b/src/platformsupport/eventdispatchers/qeventdispatcher_cf_p.h @@ -101,7 +101,7 @@ template <class T = QEventDispatcherCoreFoundation> class RunLoopSource { public: - typedef void (T::*CallbackFunction) (); + typedef bool (T::*CallbackFunction)(); enum { kHighestPriority = 0 } RunLoopSourcePriority; @@ -221,18 +221,8 @@ public: void interrupt(); void flush(); -private: - RunLoopSource<> m_postedEventsRunLoopSource; - RunLoopObserver<> m_runLoopActivityObserver; - - RunLoopModeTracker *m_runLoopModeTracker; - - QTimerInfoList m_timerInfoList; - CFRunLoopTimerRef m_runLoopTimer; - CFRunLoopTimerRef m_blockedRunLoopTimer; - bool m_overdueTimerScheduled; - - QCFSocketNotifier m_cfSocketNotifier; +protected: + virtual bool processPostedEvents(); struct ProcessEventsState { @@ -251,7 +241,19 @@ private: ProcessEventsState m_processEvents; - void processPostedEvents(); +private: + RunLoopSource<> m_postedEventsRunLoopSource; + RunLoopObserver<> m_runLoopActivityObserver; + + RunLoopModeTracker *m_runLoopModeTracker; + + QTimerInfoList m_timerInfoList; + CFRunLoopTimerRef m_runLoopTimer; + CFRunLoopTimerRef m_blockedRunLoopTimer; + bool m_overdueTimerScheduled; + + QCFSocketNotifier m_cfSocketNotifier; + void processTimers(CFRunLoopTimerRef); void handleRunLoopActivity(CFRunLoopActivity activity); diff --git a/src/platformsupport/fbconvenience/qfbvthandler.cpp b/src/platformsupport/fbconvenience/qfbvthandler.cpp index c46e470c34..5e062b3f0a 100644 --- a/src/platformsupport/fbconvenience/qfbvthandler.cpp +++ b/src/platformsupport/fbconvenience/qfbvthandler.cpp @@ -79,87 +79,79 @@ static void setTTYCursor(bool enable) } #endif +#ifdef VTH_ENABLED +static QFbVtHandler *vth; + +void QFbVtHandler::signalHandler(int sigNo) +{ + char a = sigNo; + QT_WRITE(vth->m_sigFd[0], &a, sizeof(a)); +} +#endif + QFbVtHandler::QFbVtHandler(QObject *parent) : QObject(parent), m_tty(-1), - m_signalFd(-1), m_signalNotifier(0) { #ifdef VTH_ENABLED - setTTYCursor(false); - - if (isatty(0)) { + if (isatty(0)) m_tty = 0; - ioctl(m_tty, KDGKBMODE, &m_oldKbdMode); - if (!qEnvironmentVariableIntValue("QT_QPA_ENABLE_TERMINAL_KEYBOARD")) { - // Disable the tty keyboard. - ioctl(m_tty, KDSKBMUTE, 1); - ioctl(m_tty, KDSKBMODE, KBD_OFF_MODE); - } + if (::socketpair(AF_UNIX, SOCK_STREAM, 0, m_sigFd)) { + qErrnoWarning(errno, "QFbVtHandler: socketpair() failed"); + return; } - // SIGSEGV and such cannot safely be blocked. We cannot handle them in an - // async-safe manner either. Restoring the keyboard, video mode, etc. may - // all contain calls that cannot safely be made from a signal handler. - - // Other signals: block them and use signalfd. - sigset_t mask; - sigemptyset(&mask); - - // Catch Ctrl+C. - sigaddset(&mask, SIGINT); - - // Ctrl+Z. Up to the platform plugins to handle it in a meaningful way. - sigaddset(&mask, SIGTSTP); - sigaddset(&mask, SIGCONT); - - // Default signal used by kill. To overcome the common issue of no cleaning - // up when killing a locally started app via a remote session. - sigaddset(&mask, SIGTERM); - - m_signalFd = signalfd(-1, &mask, SFD_CLOEXEC); - if (m_signalFd < 0) { - qErrnoWarning(errno, "signalfd() failed"); - } else { - m_signalNotifier = new QSocketNotifier(m_signalFd, QSocketNotifier::Read, this); - connect(m_signalNotifier, &QSocketNotifier::activated, this, &QFbVtHandler::handleSignal); - - // Block the signals that are handled via signalfd. Applies only to the current - // thread, but new threads will inherit the creator's signal mask. - pthread_sigmask(SIG_BLOCK, &mask, 0); - } + vth = this; + setTTYCursor(false); + setKeyboardEnabled(false); + + m_signalNotifier = new QSocketNotifier(m_sigFd[1], QSocketNotifier::Read, this); + connect(m_signalNotifier, &QSocketNotifier::activated, this, &QFbVtHandler::handleSignal); + + struct sigaction sa; + sa.sa_flags = 0; + sa.sa_handler = signalHandler; + sigemptyset(&sa.sa_mask); + sigaction(SIGINT, &sa, 0); // Ctrl+C + sigaction(SIGTSTP, &sa, 0); // Ctrl+Z + sigaction(SIGCONT, &sa, 0); + sigaction(SIGTERM, &sa, 0); // default signal used by kill #endif } QFbVtHandler::~QFbVtHandler() { #ifdef VTH_ENABLED - restoreKeyboard(); + setKeyboardEnabled(true); setTTYCursor(true); - if (m_signalFd != -1) - close(m_signalFd); + if (m_signalNotifier) { + close(m_sigFd[0]); + close(m_sigFd[1]); + } #endif } -void QFbVtHandler::restoreKeyboard() +void QFbVtHandler::setKeyboardEnabled(bool enable) { #ifdef VTH_ENABLED if (m_tty == -1) return; - ioctl(m_tty, KDSKBMUTE, 0); - ioctl(m_tty, KDSKBMODE, m_oldKbdMode); -#endif -} - -// To be called from the slot connected to suspendRequested() in case the -// platform plugin does in fact allow suspending on Ctrl+Z. -void QFbVtHandler::suspend() -{ -#ifdef VTH_ENABLED - kill(getpid(), SIGSTOP); + if (enable) { + ::ioctl(m_tty, KDSKBMUTE, 0); + ::ioctl(m_tty, KDSKBMODE, m_oldKbdMode); + } else { + ::ioctl(m_tty, KDGKBMODE, &m_oldKbdMode); + if (!qEnvironmentVariableIntValue("QT_QPA_ENABLE_TERMINAL_KEYBOARD")) { + ::ioctl(m_tty, KDSKBMUTE, 1); + ::ioctl(m_tty, KDSKBMODE, KBD_OFF_MODE); + } + } +#else + Q_UNUSED(enable); #endif } @@ -168,17 +160,22 @@ void QFbVtHandler::handleSignal() #ifdef VTH_ENABLED m_signalNotifier->setEnabled(false); - signalfd_siginfo sig; - if (read(m_signalFd, &sig, sizeof(sig)) == sizeof(sig)) { - switch (sig.ssi_signo) { + char sigNo; + if (QT_READ(m_sigFd[1], &sigNo, sizeof(sigNo)) == sizeof(sigNo)) { + switch (sigNo) { case SIGINT: // fallthrough case SIGTERM: handleInt(); break; case SIGTSTP: - emit suspendRequested(); + emit aboutToSuspend(); + setKeyboardEnabled(true); + setTTYCursor(true); + ::kill(getpid(), SIGSTOP); break; case SIGCONT: + setTTYCursor(false); + setKeyboardEnabled(false); emit resumed(); break; default: @@ -194,7 +191,7 @@ void QFbVtHandler::handleInt() { #ifdef VTH_ENABLED emit interrupted(); - restoreKeyboard(); + setKeyboardEnabled(true); setTTYCursor(true); _exit(1); #endif diff --git a/src/platformsupport/fbconvenience/qfbvthandler_p.h b/src/platformsupport/fbconvenience/qfbvthandler_p.h index 3681def9f0..91eba248fe 100644 --- a/src/platformsupport/fbconvenience/qfbvthandler_p.h +++ b/src/platformsupport/fbconvenience/qfbvthandler_p.h @@ -59,23 +59,22 @@ public: QFbVtHandler(QObject *parent = 0); ~QFbVtHandler(); - void suspend(); - signals: void interrupted(); - void suspendRequested(); + void aboutToSuspend(); void resumed(); private slots: void handleSignal(); private: - void restoreKeyboard(); + void setKeyboardEnabled(bool enable); void handleInt(); + static void signalHandler(int sigNo); int m_tty; int m_oldKbdMode; - int m_signalFd; + int m_sigFd[2]; QSocketNotifier *m_signalNotifier; }; diff --git a/src/platformsupport/fontdatabases/basic/qbasicfontdatabase.cpp b/src/platformsupport/fontdatabases/basic/qbasicfontdatabase.cpp index b04ae8ee52..728b166b71 100644 --- a/src/platformsupport/fontdatabases/basic/qbasicfontdatabase.cpp +++ b/src/platformsupport/fontdatabases/basic/qbasicfontdatabase.cpp @@ -188,7 +188,7 @@ QStringList QBasicFontDatabase::addTTFile(const QByteArray &fontData, const QByt error = FT_New_Face(library, file.constData(), index, &face); } if (error != FT_Err_Ok) { - qDebug() << "FT_New_Face failed with index" << index << ":" << hex << error; + qDebug() << "FT_New_Face failed with index" << index << ':' << hex << error; break; } numFaces = face->num_faces; diff --git a/src/platformsupport/input/evdevmouse/qevdevmousehandler.cpp b/src/platformsupport/input/evdevmouse/qevdevmousehandler.cpp index 2e9723329e..c4ebc5c51d 100644 --- a/src/platformsupport/input/evdevmouse/qevdevmousehandler.cpp +++ b/src/platformsupport/input/evdevmouse/qevdevmousehandler.cpp @@ -148,7 +148,7 @@ bool QEvdevMouseHandler::getHardwareMaximum() qCDebug(qLcEvdevMouse) << "Absolute pointing device" << "hardware max x" << m_hardwareWidth << "hardware max y" << m_hardwareHeight - << "hardware scalers x" << m_hardwareScalerX << "y" << m_hardwareScalerY; + << "hardware scalers x" << m_hardwareScalerX << 'y' << m_hardwareScalerY; return true; } diff --git a/src/platformsupport/input/tslib/qtslib_p.h b/src/platformsupport/input/tslib/qtslib_p.h index c3ee6697fa..b6448c67d7 100644 --- a/src/platformsupport/input/tslib/qtslib_p.h +++ b/src/platformsupport/input/tslib/qtslib_p.h @@ -34,6 +34,17 @@ #ifndef QTSLIB_H #define QTSLIB_H +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists for the convenience +// of other Qt classes. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + #include <QObject> struct tsdev; diff --git a/src/platformsupport/linuxaccessibility/atspiadaptor.cpp b/src/platformsupport/linuxaccessibility/atspiadaptor.cpp index d155cecd89..0293c74fb9 100644 --- a/src/platformsupport/linuxaccessibility/atspiadaptor.cpp +++ b/src/platformsupport/linuxaccessibility/atspiadaptor.cpp @@ -2312,7 +2312,7 @@ bool AtSpiAdaptor::tableInterface(QAccessibleInterface *interface, const QString (column < 0) || (row >= interface->tableInterface()->rowCount()) || (column >= interface->tableInterface()->columnCount())) { - qAtspiDebug() << "WARNING: invalid index for tableInterface GetAccessibleAt (" << row << ", " << column << ")"; + qAtspiDebug() << "WARNING: invalid index for tableInterface GetAccessibleAt (" << row << ", " << column << ')'; return false; } @@ -2331,7 +2331,7 @@ bool AtSpiAdaptor::tableInterface(QAccessibleInterface *interface, const QString int column = message.arguments().at(1).toInt(); QAccessibleInterface *cell = interface->tableInterface()->cellAt(row, column); if (!cell) { - qAtspiDebug() << "WARNING: AtSpiAdaptor::GetIndexAt(" << row << "," << column << ") did not find a cell. " << interface; + qAtspiDebug() << "WARNING: AtSpiAdaptor::GetIndexAt(" << row << ',' << column << ") did not find a cell. " << interface; return false; } int index = interface->indexOfChild(cell); diff --git a/src/platformsupport/themes/genericunix/qgenericunixthemes.cpp b/src/platformsupport/themes/genericunix/qgenericunixthemes.cpp index fe03c7ac06..26d815d7ff 100644 --- a/src/platformsupport/themes/genericunix/qgenericunixthemes.cpp +++ b/src/platformsupport/themes/genericunix/qgenericunixthemes.cpp @@ -243,8 +243,13 @@ void QKdeThemePrivate::refresh() toolButtonStyle = Qt::ToolButtonTextBesideIcon; toolBarIconSize = 0; styleNames.clear(); + if (kdeVersion >= 5) + styleNames << QStringLiteral("breeze"); styleNames << QStringLiteral("Oxygen") << QStringLiteral("fusion") << QStringLiteral("windows"); - iconFallbackThemeName = iconThemeName = QStringLiteral("oxygen"); + if (kdeVersion >= 5) + iconFallbackThemeName = iconThemeName = QStringLiteral("breeze"); + else + iconFallbackThemeName = iconThemeName = QStringLiteral("oxygen"); QHash<QString, QSettings*> kdeSettings; |