mirror of
https://github.com/gnif/LookingGlass.git
synced 2026-11-12 23:07:21 +00:00
[client/idd] input: reduce network latency
Route input through a dedicated high-priority stream, send pointer motion as cumulative datagrams, and recover suspected loss reliably. Reduce downstream input queuing with age-aware coalescing and input thread scheduling.
This commit is contained in:
@@ -27,9 +27,12 @@
|
||||
#include "CDebug.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <avrt.h>
|
||||
#include <stdint.h>
|
||||
#include <vector>
|
||||
|
||||
#pragma comment(lib, "avrt.lib")
|
||||
|
||||
const DWORD CPipeEndpoint::CLIENT_RETRY_INITIAL_MS = 100;
|
||||
const DWORD CPipeEndpoint::CLIENT_RETRY_MAX_MS = 2000;
|
||||
const DWORD CPipeEndpoint::SERVER_RETRY_MS = 1000;
|
||||
@@ -195,22 +198,24 @@ bool CPipeEndpoint::Start(
|
||||
size_t messageSize,
|
||||
const SECURITY_ATTRIBUTES * serverSecurity,
|
||||
DWORD serverOpenMode,
|
||||
DWORD serverPipeMode)
|
||||
DWORD serverPipeMode,
|
||||
ThreadScheduling threadScheduling)
|
||||
{
|
||||
Stop();
|
||||
|
||||
if (!pipeName || !*pipeName || !messageSize || messageSize > MAXDWORD)
|
||||
return false;
|
||||
|
||||
m_pipeName = pipeName;
|
||||
m_mode = mode;
|
||||
m_messageSize = messageSize;
|
||||
m_hasServerSecurity = serverSecurity != nullptr;
|
||||
m_serverSecurity = serverSecurity ? *serverSecurity :
|
||||
m_pipeName = pipeName;
|
||||
m_mode = mode;
|
||||
m_messageSize = messageSize;
|
||||
m_threadScheduling = threadScheduling;
|
||||
m_hasServerSecurity = serverSecurity != nullptr;
|
||||
m_serverSecurity = serverSecurity ? *serverSecurity :
|
||||
SECURITY_ATTRIBUTES {};
|
||||
m_serverOpenMode = serverOpenMode;
|
||||
m_serverPipeMode = serverPipeMode;
|
||||
m_stopEvent = CreateEventW(nullptr, TRUE, FALSE, nullptr);
|
||||
m_serverOpenMode = serverOpenMode;
|
||||
m_serverPipeMode = serverPipeMode;
|
||||
m_stopEvent = CreateEventW(nullptr, TRUE, FALSE, nullptr);
|
||||
if (!m_stopEvent)
|
||||
{
|
||||
const DWORD error = GetLastError();
|
||||
@@ -362,11 +367,30 @@ DWORD WINAPI CPipeEndpoint::ThreadProc(void * context)
|
||||
|
||||
void CPipeEndpoint::Thread()
|
||||
{
|
||||
HANDLE avTaskHandle = nullptr;
|
||||
if (m_threadScheduling == ThreadScheduling::Input)
|
||||
{
|
||||
DWORD avTask = 0;
|
||||
bool prioritySet = false;
|
||||
|
||||
avTaskHandle = AvSetMmThreadCharacteristicsW(L"Distribution", &avTask);
|
||||
if (avTaskHandle)
|
||||
prioritySet =
|
||||
AvSetMmThreadPriority(avTaskHandle, AVRT_PRIORITY_HIGH) != FALSE;
|
||||
if (!prioritySet && !SetThreadPriority(
|
||||
GetCurrentThread(), THREAD_PRIORITY_ABOVE_NORMAL))
|
||||
DEBUG_WARN_HR(GetLastError(),
|
||||
"Failed to raise input pipe thread priority");
|
||||
}
|
||||
|
||||
if (m_mode == Mode::Server)
|
||||
RunServer();
|
||||
else
|
||||
RunClient();
|
||||
|
||||
if (avTaskHandle)
|
||||
AvRevertMmThreadCharacteristics(avTaskHandle);
|
||||
|
||||
Atomic::Store(m_running, false);
|
||||
Atomic::Store(m_connected, false);
|
||||
}
|
||||
|
||||
@@ -80,6 +80,12 @@ public:
|
||||
Client,
|
||||
};
|
||||
|
||||
enum class ThreadScheduling
|
||||
{
|
||||
Normal,
|
||||
Input,
|
||||
};
|
||||
|
||||
CPipeEndpoint() = default;
|
||||
~CPipeEndpoint();
|
||||
|
||||
@@ -92,7 +98,8 @@ public:
|
||||
_In_ size_t messageSize,
|
||||
_In_opt_ const SECURITY_ATTRIBUTES * serverSecurity = nullptr,
|
||||
_In_ DWORD serverOpenMode = 0,
|
||||
_In_ DWORD serverPipeMode = 0);
|
||||
_In_ DWORD serverPipeMode = 0,
|
||||
_In_ ThreadScheduling threadScheduling = ThreadScheduling::Normal);
|
||||
void Stop();
|
||||
void DisconnectClient();
|
||||
|
||||
@@ -158,13 +165,14 @@ private:
|
||||
void ClosePipe(_In_ HANDLE pipe);
|
||||
|
||||
std::wstring m_pipeName;
|
||||
size_t m_messageSize = 0;
|
||||
Mode m_mode = Mode::Client;
|
||||
IPipeEndpointHandler * m_handler = nullptr;
|
||||
SECURITY_ATTRIBUTES m_serverSecurity = {};
|
||||
bool m_hasServerSecurity = false;
|
||||
DWORD m_serverOpenMode = 0;
|
||||
DWORD m_serverPipeMode = 0;
|
||||
size_t m_messageSize = 0;
|
||||
Mode m_mode = Mode::Client;
|
||||
ThreadScheduling m_threadScheduling = ThreadScheduling::Normal;
|
||||
IPipeEndpointHandler * m_handler = nullptr;
|
||||
SECURITY_ATTRIBUTES m_serverSecurity = {};
|
||||
bool m_hasServerSecurity = false;
|
||||
DWORD m_serverOpenMode = 0;
|
||||
DWORD m_serverPipeMode = 0;
|
||||
|
||||
std::atomic<bool> m_running { false };
|
||||
std::atomic<bool> m_connected { false };
|
||||
|
||||
Reference in New Issue
Block a user