summaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorStanislaw Halik <sthalik@misaki.pl>2015-11-29 11:58:20 +0100
committerStanislaw Halik <sthalik@misaki.pl>2015-11-29 11:58:48 +0100
commitedb0e01947f67142c00c3f75a62df7af708cdf11 (patch)
tree5ac50202796be1964662a278186b92992868c06a
parent044b799a15ec8b47094d6086b13ec77f991b6054 (diff)
api/joystick: reduce mutex contention
Don't look for changes in hotplug joysticks by freezing up polling for joysticks' axis and button. Issue: #267
-rw-r--r--opentrack/win32-joystick.cpp21
-rw-r--r--opentrack/win32-joystick.hpp4
2 files changed, 18 insertions, 7 deletions
diff --git a/opentrack/win32-joystick.cpp b/opentrack/win32-joystick.cpp
index 29a51a43..0bd6bfda 100644
--- a/opentrack/win32-joystick.cpp
+++ b/opentrack/win32-joystick.cpp
@@ -33,9 +33,10 @@ win32_joy_ctx& win32_joy_ctx::make()
void win32_joy_ctx::poll(fn f)
{
+ refresh(false);
+
QMutexLocker l(&mtx);
- refresh(false);
for (auto& j : joys())
{
j.second->poll(f);
@@ -44,10 +45,10 @@ void win32_joy_ctx::poll(fn f)
bool win32_joy_ctx::poll_axis(const QString &guid, int axes[])
{
- QMutexLocker l(&mtx);
-
refresh(false);
+ QMutexLocker l(&mtx);
+
auto iter = joys().find(guid);
if (iter == joys().end() || iter->second->joy_handle == nullptr)
@@ -134,12 +135,14 @@ void win32_joy_ctx::refresh(bool first)
{
if (!first)
{
+ QMutexLocker l(&mtx);
+
if (timer_joylist.elapsed_ms() < joylist_refresh_ms)
return;
timer_joylist.start();
}
- enum_state st(joys(), first);
+ enum_state st(joys(), first, mtx);
}
QString win32_joy_ctx::guid_to_string(const GUID guid)
@@ -210,11 +213,16 @@ bool win32_joy_ctx::joy::poll(fn f)
return true;
}
-win32_joy_ctx::enum_state::enum_state(std::unordered_map<QString, std::shared_ptr<joy> > &joys, bool first) : joys(joys), first(first)
+win32_joy_ctx::enum_state::enum_state(std::unordered_map<QString, std::shared_ptr<joy> > &joys, bool first, QMutex& mtx) : first(first)
{
HRESULT hr;
LPDIRECTINPUT8 di = dinput_handle();
+ {
+ QMutexLocker l(&mtx);
+ this->joys = joys;
+ }
+
if(FAILED(hr = di->EnumDevices(DI8DEVCLASS_GAMECTRL,
EnumJoysticksCallback,
this,
@@ -231,6 +239,9 @@ win32_joy_ctx::enum_state::enum_state(std::unordered_map<QString, std::shared_pt
else
it++;
}
+
+ QMutexLocker l(&mtx);
+ joys = this->joys;
}
win32_joy_ctx::enum_state::EnumJoysticksCallback(const DIDEVICEINSTANCE *pdidInstance, void *pContext)
diff --git a/opentrack/win32-joystick.hpp b/opentrack/win32-joystick.hpp
index 334b617a..3f47d170 100644
--- a/opentrack/win32-joystick.hpp
+++ b/opentrack/win32-joystick.hpp
@@ -100,14 +100,14 @@ private:
class enum_state
{
- std::unordered_map<QString, std::shared_ptr<joy>>& joys;
+ std::unordered_map<QString, std::shared_ptr<joy>> joys;
bool first;
std::vector<QString> all;
static BOOL CALLBACK EnumJoysticksCallback(const DIDEVICEINSTANCE* pdidInstance, VOID* pContext);
static BOOL CALLBACK EnumObjectsCallback(const DIDEVICEOBJECTINSTANCE* pdidoi, VOID* ctx);
public:
- enum_state(std::unordered_map<QString, std::shared_ptr<joy>>& joys, bool first);
+ enum_state(std::unordered_map<QString, std::shared_ptr<joy>>& joys, bool first, QMutex &mtx);
};
};