From a310c7fa20119bfa3c92997820ed66f233787cf1 Mon Sep 17 00:00:00 2001 From: Ethin Probst Date: Thu, 14 Nov 2019 14:37:07 -0600 Subject: [PATCH] Overlay, winhooks: add screen reader detection to prevent the setting of winhooks if a screen reader was found to be running at app startup --- src/mumble/GlobalShortcut_win.cpp | 28 +++++++++++++++++++++++++++- src/mumble/GlobalShortcut_win.h | 3 +++ 2 files changed, 30 insertions(+), 1 deletion(-) diff --git a/src/mumble/GlobalShortcut_win.cpp b/src/mumble/GlobalShortcut_win.cpp index c09069ae843..acfd3778321 100644 --- a/src/mumble/GlobalShortcut_win.cpp +++ b/src/mumble/GlobalShortcut_win.cpp @@ -21,6 +21,9 @@ // 3rdparty/xinputcheck-src. #include +// Used to detect screen readers +#include + // We define a global macro called 'g'. This can lead to issues when included code uses 'g' as a type or parameter name (like protobuf 3.7 does). As such, for now, we have to make this our last include. #include "Global.h" @@ -129,7 +132,8 @@ GlobalShortcutWin::GlobalShortcutWin() #endif { // Hidden setting to disable hooking - bHook = g.qs->value(QLatin1String("winhooks"), true).toBool(); + // Also disable hooking if a screen reader is running + bHook = g.qs->value(QLatin1String("winhooks"), true).toBool() && !areScreenReadersActive(); moveToThread(this); start(QThread::LowestPriority); @@ -899,3 +903,25 @@ QString GlobalShortcutWin::buttonName(const QVariant &v) { bool GlobalShortcutWin::canSuppress() { return bHook; } + +bool GlobalShortcutWin::areScreenReadersActive() { + // This list contains valid executables we consider to be 'screen readers'. + // Todo: perhaps make this a configuration option in mumble to let users dynamically add executables. + const QStringList executables = { QLatin1String("nvda.exe"), QLatin1String("jfw.exe") }; + + const auto snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); + if (snapshot != INVALID_HANDLE_VALUE) { + PROCESSENTRY32 p; + p.dwSize = sizeof(p); + auto ok = Process32First(snapshot, &p); + while (ok) { + if (executables.contains(QString::fromWCharArray(p.szExeFile))) { + CloseHandle(snapshot); + return true; + } + ok = Process32Next(snapshot, &p); + } + CloseHandle(snapshot); + } + return false; +} diff --git a/src/mumble/GlobalShortcut_win.h b/src/mumble/GlobalShortcut_win.h index 9226ced649a..876f120c81f 100644 --- a/src/mumble/GlobalShortcut_win.h +++ b/src/mumble/GlobalShortcut_win.h @@ -129,6 +129,9 @@ class GlobalShortcutWin : public GlobalShortcutEngine { /// @return Returns true if the GlobalShortcut engine signalled that /// the button should be suppressed. Returns false otherwise. bool injectMouseMessage(MSG *msg); + + private: + bool areScreenReadersActive(); }; uint qHash(const GUID &);