CRC validity checking. Ignore CRCs if they don't work.

This commit is contained in:
Gregor Richards 2016-12-15 12:43:29 -05:00
parent a6cd8c3aa1
commit 6658826759
3 changed files with 19 additions and 8 deletions

View File

@ -429,6 +429,8 @@ netplay_t *netplay_new(void *direct_host, const char *server, uint16_t port,
netplay->nat_traversal = netplay->is_server ? nat_traversal : false; netplay->nat_traversal = netplay->is_server ? nat_traversal : false;
netplay->delay_frames = delay_frames; netplay->delay_frames = delay_frames;
netplay->check_frames = check_frames; netplay->check_frames = check_frames;
netplay->crc_validity_checked = false;
netplay->crcs_valid = true;
netplay->quirks = quirks; netplay->quirks = quirks;
netplay->self_mode = netplay->is_server ? netplay->self_mode = netplay->is_server ?
NETPLAY_CONNECTION_PLAYING : NETPLAY_CONNECTION_PLAYING :

View File

@ -430,6 +430,12 @@ struct netplay
/* Frequency with which to check CRCs */ /* Frequency with which to check CRCs */
uint32_t check_frames; uint32_t check_frames;
/* Have we checked whether CRCs are valid at all? */
bool crc_validity_checked;
/* Are they valid? */
bool crcs_valid;
}; };

View File

@ -131,34 +131,37 @@ void netplay_simulate_input(netplay_t *netplay, size_t sim_ptr, bool resim)
static void netplay_handle_frame_hash(netplay_t *netplay, struct delta_frame *delta) static void netplay_handle_frame_hash(netplay_t *netplay, struct delta_frame *delta)
{ {
static bool crcs_valid = true;
if (netplay->is_server) if (netplay->is_server)
{ {
if (netplay->check_frames && if (netplay->check_frames &&
(delta->frame % netplay->check_frames == 0 || delta->frame == 1)) delta->frame % netplay->check_frames == 0)
{ {
delta->crc = netplay_delta_frame_crc(netplay, delta); delta->crc = netplay_delta_frame_crc(netplay, delta);
netplay_cmd_crc(netplay, delta); netplay_cmd_crc(netplay, delta);
} }
} }
else if (delta->crc && crcs_valid) else if (delta->crc && netplay->crcs_valid)
{ {
/* We have a remote CRC, so check it */ /* We have a remote CRC, so check it */
uint32_t local_crc = netplay_delta_frame_crc(netplay, delta); uint32_t local_crc = netplay_delta_frame_crc(netplay, delta);
if (local_crc != delta->crc) if (local_crc != delta->crc)
{ {
if (delta->frame == 1) if (!netplay->crc_validity_checked)
{ {
/* We check frame 1 just to make sure the CRCs make sense at all. /* If the very first check frame is wrong, they probably just don't
* If we've diverged at frame 1, we assume CRCs are not useful. */ * work */
crcs_valid = false; netplay->crcs_valid = false;
} }
else if (crcs_valid) else if (netplay->crcs_valid)
{ {
/* Fix this! */ /* Fix this! */
netplay_cmd_request_savestate(netplay); netplay_cmd_request_savestate(netplay);
} }
} }
else if (!netplay->crc_validity_checked)
{
netplay->crc_validity_checked = true;
}
} }
} }