Хук WSARecv: как игнорировать данные? - PullRequest
0 голосов
/ 26 февраля 2020

Добро пожаловать.

Существует игра, в которой необходимо временно приостановить прием данных без приостановки отправки.

То есть игра должна временно прекратить видеть входящие пакеты с информацией, не разрывая соединение , как будто ничего не получено.

Мне удалось получить желаемый эффект, установив хук на функцию выбора и очистив readfds с помощью FD_ZERO, но это работает очень неправильно.

int (WSAAPI * realSelect) (int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, const timeval *timeout) = select;
int WSAAPI mySelect(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, const timeval *timeout)
{
    if (GetAsyncKeyState(VK_SHIFT))
    {
        FD_ZERO(readfds);
    }
    return realSelect(nfds, readfds, writefds, exceptfds, timeout);
}

Если Вы смотрите на моего персонажа со стороны, вы можете видеть, как он двигается «рывками», как будто что-то происходит с отправкой данных. Более того, когда я отпускаю клавишу SHIFT, игра оживает только через 2-4 секунды, это очень странно и не должно быть так.

Также по совету одного человека я пытался сделать следующее.

int (WSAAPI * realRecv) (SOCKET s, LPWSABUF lpBuffers, DWORD dwBufferCount, LPDWORD lpNumberOfBytesRecvd, LPDWORD lpFlags, LPWSAOVERLAPPED lpOverlapped, LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine) = WSARecv;
int WSAAPI myRecv(SOCKET s, LPWSABUF lpBuffers, DWORD dwBufferCount, LPDWORD lpNumberOfBytesRecvd, LPDWORD lpFlags, LPWSAOVERLAPPED lpOverlapped, LPWSAOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine)
{
    if (GetAsyncKeyState(VK_SHIFT))
    {
        *lpNumberOfBytesRecvd = 0;
        return WSA_IO_PENDING;
    }

    return realRecv(s, lpBuffers, dwBufferCount, lpNumberOfBytesRecvd, lpFlags, lpOverlapped, lpCompletionRoutine);
}

Однако это не сработало, и я был отключен от сервера.

У меня была идея использовать SuspendThread, но WSASend и WSARecv находятся в одном потоке, поэтому если я приостановлю поток, и получение, и отправка будут приостановлены. Уловка приостановки потока работает, но она также приостанавливает WSASend, и это разрушает саму суть идеи.

Если это важно, вот вызовы WinAPI, которые игра использует для работы с сетью. : WSASend , WSARecv , select , ioctlsocket

Я уверен, что есть способ сделать что-то с данные в хуке WSARecv.

Я очень надеюсь, что вы поможете мне с этой задачей. Пожалуйста, если вы что-то объясняете, даже если это кажется вам слишком простым, объясните это очень подробно, я новичок в C ++ и не очень понимаю.

...