ggpo: make chat thread-safe. Deadlock on early rollback
Make ggpo_send_message() thread-safe Deadlock UI/emu threads if rollback happens before first render Disable rollback wait in single-thread mode
This commit is contained in:
parent
6d8e1794a0
commit
808a161d39
|
@ -286,14 +286,17 @@ UdpProtocol::SendMsg(UdpMsg *msg)
|
||||||
{
|
{
|
||||||
LogMsg("send", msg);
|
LogMsg("send", msg);
|
||||||
|
|
||||||
_packets_sent++;
|
{
|
||||||
_last_send_time = Platform::GetCurrentTimeMS();
|
std::lock_guard<std::mutex> lock(_send_mutex);
|
||||||
_bytes_sent += msg->PacketSize();
|
_packets_sent++;
|
||||||
|
_last_send_time = Platform::GetCurrentTimeMS();
|
||||||
|
_bytes_sent += msg->PacketSize();
|
||||||
|
|
||||||
msg->hdr.magic = _magic_number;
|
msg->hdr.magic = _magic_number;
|
||||||
msg->hdr.sequence_number = _next_send_seq++;
|
msg->hdr.sequence_number = _next_send_seq++;
|
||||||
|
|
||||||
_send_queue.push(QueueEntry(Platform::GetCurrentTimeMS(), _peer_addr, msg));
|
_send_queue.push(QueueEntry(Platform::GetCurrentTimeMS(), _peer_addr, msg));
|
||||||
|
}
|
||||||
PumpSendQueue();
|
PumpSendQueue();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -753,6 +756,7 @@ UdpProtocol::SetDisconnectNotifyStart(int timeout)
|
||||||
void
|
void
|
||||||
UdpProtocol::PumpSendQueue()
|
UdpProtocol::PumpSendQueue()
|
||||||
{
|
{
|
||||||
|
std::lock_guard<std::mutex> lock(_send_mutex);
|
||||||
while (!_send_queue.empty()) {
|
while (!_send_queue.empty()) {
|
||||||
QueueEntry &entry = _send_queue.front();
|
QueueEntry &entry = _send_queue.front();
|
||||||
|
|
||||||
|
@ -793,6 +797,7 @@ UdpProtocol::PumpSendQueue()
|
||||||
void
|
void
|
||||||
UdpProtocol::ClearSendQueue()
|
UdpProtocol::ClearSendQueue()
|
||||||
{
|
{
|
||||||
|
std::lock_guard<std::mutex> lock(_send_mutex);
|
||||||
while (!_send_queue.empty()) {
|
while (!_send_queue.empty()) {
|
||||||
delete _send_queue.front().msg;
|
delete _send_queue.front().msg;
|
||||||
_send_queue.pop();
|
_send_queue.pop();
|
||||||
|
|
|
@ -16,6 +16,7 @@
|
||||||
#include "ggponet.h"
|
#include "ggponet.h"
|
||||||
#include "ring_buffer.h"
|
#include "ring_buffer.h"
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
#include <mutex>
|
||||||
|
|
||||||
class UdpProtocol : public IPollSink
|
class UdpProtocol : public IPollSink
|
||||||
{
|
{
|
||||||
|
@ -153,6 +154,7 @@ protected:
|
||||||
UdpMsg* msg;
|
UdpMsg* msg;
|
||||||
} _oo_packet;
|
} _oo_packet;
|
||||||
RingBuffer<QueueEntry, 64> _send_queue;
|
RingBuffer<QueueEntry, 64> _send_queue;
|
||||||
|
std::mutex _send_mutex;
|
||||||
|
|
||||||
std::vector<uint8> verification;
|
std::vector<uint8> verification;
|
||||||
|
|
||||||
|
|
|
@ -466,7 +466,8 @@ void rend_allow_rollback()
|
||||||
|
|
||||||
void rend_start_rollback()
|
void rend_start_rollback()
|
||||||
{
|
{
|
||||||
vramRollback.Wait();
|
if (config::ThreadedRendering)
|
||||||
|
vramRollback.Wait();
|
||||||
}
|
}
|
||||||
|
|
||||||
void rend_serialize(void **data, unsigned int *total_size)
|
void rend_serialize(void **data, unsigned int *total_size)
|
||||||
|
|
|
@ -159,6 +159,7 @@ struct Inputs
|
||||||
u8 keys[6];
|
u8 keys[6];
|
||||||
} u;
|
} u;
|
||||||
};
|
};
|
||||||
|
static_assert(sizeof(Inputs) == 10, "wrong Inputs size");
|
||||||
|
|
||||||
struct GameEvent
|
struct GameEvent
|
||||||
{
|
{
|
||||||
|
@ -183,6 +184,7 @@ struct GameEvent
|
||||||
static bool begin_game(const char *)
|
static bool begin_game(const char *)
|
||||||
{
|
{
|
||||||
DEBUG_LOG(NETWORK, "Game begin");
|
DEBUG_LOG(NETWORK, "Game begin");
|
||||||
|
rend_allow_rollback();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue