From d44de3a9dcb7645a6442b2b51bcde7684b319861 Mon Sep 17 00:00:00 2001 From: Connor McLaughlin Date: Thu, 14 Jan 2021 00:40:25 +1000 Subject: [PATCH] System: Use SetWaitableTimer() for throttling on Windows --- src/core/system.cpp | 26 +++++++++++++++++++++++++- 1 file changed, 25 insertions(+), 1 deletion(-) diff --git a/src/core/system.cpp b/src/core/system.cpp index afa9b5f23..693e41069 100644 --- a/src/core/system.cpp +++ b/src/core/system.cpp @@ -1299,7 +1299,31 @@ void Throttle() else if (sleep_time >= MINIMUM_SLEEP_TIME) { #ifdef WIN32 - Sleep(static_cast(sleep_time / 1000000)); + static HANDLE throttle_timer; + static bool throttle_timer_created = false; + if (!throttle_timer_created) + { + throttle_timer_created = true; + throttle_timer = CreateWaitableTimer(nullptr, TRUE, nullptr); + if (throttle_timer) + std::atexit([]() { CloseHandle(throttle_timer); }); + else + Log_ErrorPrintf("CreateWaitableTimer() failed, falling back to Sleep()"); + } + + if (throttle_timer) + { + LARGE_INTEGER due_time; + due_time.QuadPart = -static_cast(static_cast(sleep_time) / 100u); + if (SetWaitableTimer(throttle_timer, &due_time, 0, nullptr, nullptr, FALSE)) + WaitForSingleObject(throttle_timer, INFINITE); + else + Log_ErrorPrintf("SetWaitableTimer() failed: %08X", GetLastError()); + } + else + { + Sleep(static_cast(sleep_time / 1000000)); + } #else const struct timespec ts = {0, static_cast(sleep_time)}; nanosleep(&ts, nullptr);