Skip to content

Commit

Permalink
Multiplayer: Updated GPT_GAME_STATE packet
Browse files Browse the repository at this point in the history
Added map Uri and game identity key. Currently the Uri is not
used by the client (still relies on episode and map number), but
the game identity key is verified (although there is currently no
way it can be wrong on the client).
  • Loading branch information
skyjake committed Jan 7, 2012
1 parent 221ec06 commit dc1c121
Show file tree
Hide file tree
Showing 2 changed files with 69 additions and 50 deletions.
71 changes: 42 additions & 29 deletions doomsday/plugins/common/src/d_netcl.c
Expand Up @@ -64,53 +64,66 @@

void NetCl_UpdateGameState(Reader* msg)
{
byte gsGameMode = 0;
byte len;
byte gsFlags = 0;
char gsGameIdentity[256];
Uri* mapUri;
byte gsEpisode = 0;
byte gsMap = 0;
byte flags = 0;
byte configFlags = 0;
byte gsDeathmatch = 0;
byte gsMonsters = 0;
byte gsRespawn = 0;
byte gsJumping = 0;
byte gsSkill = 0;
float gsGravity = 0;

gsGameMode = Reader_ReadByte(msg);
gsFlags = Reader_ReadByte(msg);
gsEpisode = Reader_ReadByte(msg) - 1;
gsMap = Reader_ReadByte(msg) - 1;
flags = Reader_ReadByte(msg);
gsDeathmatch = flags & 0x3;
gsMonsters = (flags & 0x4? true : false);
gsRespawn = (flags & 0x8? true : false);
gsJumping = (flags & 0x10? true : false);

// Game identity key.
len = Reader_ReadByte(msg);
Reader_Read(msg, gsGameIdentity, len);
gsGameIdentity[len] = 0;

// Current map.
mapUri = Uri_NewFromReader(msg);

gsEpisode = Reader_ReadByte(msg);
gsMap = Reader_ReadByte(msg);

configFlags = Reader_ReadByte(msg);
gsDeathmatch = configFlags & 0x3;
gsMonsters = (configFlags & 0x4? true : false);
gsRespawn = (configFlags & 0x8? true : false);
gsJumping = (configFlags & 0x10? true : false);
gsSkill = Reader_ReadByte(msg);
gsGravity = Reader_ReadFloat(msg);

VERBOSE(
ddstring_t* str = Uri_ToString(mapUri);
Con_Message("NetCl_UpdateGameState: Flags=%x, Map uri=\"%s\"\n", gsFlags, Str_Text(str));
Str_Delete(str);
)

// Demo game state changes are only effective during demo playback.
if(gsFlags & GSF_DEMO && !Get(DD_PLAYBACK))
return;

#pragma message("!!!WARNING: NetCl_UpdateGameState presently overrides gameMode mismatches.")
/**
* \kludge
* djs: 2010-09-20 23:31 GMT
* Dedicated servers are presently built from the master branch and as such
* our gameMode will never match that returned by the server. However, this
* is now protected against at a much higher level during game initialization
* so we don't really need to be worrying about that here.
*
* For now we'll override it using our local gameMode value.
*/
gsGameMode = gameMode;
/*if(gsGameMode != gameMode)
{ // Wrong game mode! This is highly irregular!
Con_Message("NetCl_UpdateGameState: Game mode mismatch!\n");
// Stop the demo if one is being played.
DD_Execute(false, "stopdemo");
return;
} kludge end */
// Check for a game mode mismatch.
/// @todo Automatically load the server's game if it is available.
/// However, note that this can only occur if the server changes its game
/// while a netgame is running (which currently will end the netgame).
{
GameInfo gameInfo;
DD_GameInfo(&gameInfo);
if(strcmp(gameInfo.identityKey, gsGameIdentity))
{
Con_Message("NetCl_UpdateGameState: Server's game mode (%s) is different than yours (%s).\n",
gsGameIdentity, gameInfo.identityKey);
DD_Execute(false, "net disconnect");
return;
}
}

deathmatch = gsDeathmatch;
noMonstersParm = !gsMonsters;
Expand Down
48 changes: 27 additions & 21 deletions doomsday/plugins/common/src/d_netsv.c
Expand Up @@ -819,13 +819,21 @@ void NetSv_SendGameState(int flags, int to)
{
int i;
Writer* writer;
GameInfo gameInfo;
Uri* mapUri;
ddstring_t* str;

if(IS_CLIENT)
return;

DD_GameInfo(&gameInfo);
mapUri = G_ComposeMapUri(gameEpisode, gameMap);

// Print a short message that describes the game state.
Con_Message("NetSv_SendGameState: Game setup: ep%u map%u %s\n",
gameEpisode+1, gameMap+1, gameConfigString);
str = Uri_Resolved(mapUri);
Con_Message("NetSv_SendGameState: Game setup: %s %s %s\n",
gameInfo.identityKey, Str_Text(str), gameConfigString);
Str_Delete(str);

// Send an update to all the players in the game.
for(i = 0; i < MAXPLAYERS; ++i)
Expand All @@ -834,33 +842,29 @@ void NetSv_SendGameState(int flags, int to)
continue;

writer = D_NetWrite();

#if __JDOOM__ || __JDOOM64__
Writer_WriteByte(writer, gameMode);
#else
Writer_WriteByte(writer, 0);
#endif
Writer_WriteByte(writer, flags);
Writer_WriteByte(writer, gameEpisode + 1);
Writer_WriteByte(writer, gameMap + 1);

// Game identity key.
Writer_WriteByte(writer, strlen(gameInfo.identityKey));
Writer_Write(writer, gameInfo.identityKey, strlen(gameInfo.identityKey));

// The current map.
Uri_Write(mapUri, writer);

// Also include the episode and map numbers.
Writer_WriteByte(writer, gameEpisode);
Writer_WriteByte(writer, gameMap);

Writer_WriteByte(writer, (deathmatch & 0x3)
| (!noMonstersParm? 0x4 : 0)
#if !__JHEXEN__
| (respawnMonsters? 0x8 : 0)
#else
| 0
#endif
| (cfg.jumpEnabled? 0x10 : 0));
//#if __JDOOM__ || __JHERETIC__ || __JDOOM64__
// | (gameSkill << 5));
//#else
// );
//#endif
//#if __JDOOM__ || __JHERETIC__ || __JDOOM64__
// Writer_WriteByte(writer, 0);
//#else
| (cfg.jumpEnabled? 0x10 : 0));

Writer_WriteByte(writer, gameSkill & 0x7);
//#endif
Writer_WriteFloat(writer, P_GetGravity());

if(flags & GSF_CAMERA_INIT)
Expand All @@ -873,8 +877,10 @@ void NetSv_SendGameState(int flags, int to)
}

// Send the packet.
Net_SendPacket(i | DDSP_ORDERED, GPT_GAME_STATE, Writer_Data(writer), Writer_Size(writer));
Net_SendPacket(i, GPT_GAME_STATE, Writer_Data(writer), Writer_Size(writer));
}

Uri_Delete(mapUri);
}

/**
Expand Down

0 comments on commit dc1c121

Please sign in to comment.