mirror of
https://github.com/KartKrewDev/RingRacers.git
synced 2025-10-30 08:01:28 +00:00
XD_REQMAPQUEUE --> PT_REQMAPQUEUE
It was technically possible for custom clients to spoil future rounds of a tournament queued while they are connected to a server. Making it a PT direct packet to the servernode both solves this problem AND reduces irrelevant NetXCmd traffic for clients.
This commit is contained in:
parent
8bd50ddb65
commit
512ec6c2eb
5 changed files with 106 additions and 74 deletions
|
|
@ -4772,6 +4772,86 @@ static void PT_Say(int node)
|
||||||
DoSayCommand(say.message, say.target, say.flags, say.source);
|
DoSayCommand(say.message, say.target, say.flags, say.source);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void PT_ReqMapQueue(int node)
|
||||||
|
{
|
||||||
|
if (client)
|
||||||
|
return; // Only sent to servers, why are we receiving this?
|
||||||
|
|
||||||
|
reqmapqueue_pak reqmapqueue = netbuffer->u.reqmapqueue;
|
||||||
|
|
||||||
|
// Check for a spoofed source.
|
||||||
|
if (reqmapqueue.source == serverplayer)
|
||||||
|
{
|
||||||
|
// Servers aren't guaranteed to have a playernode, dedis exist.
|
||||||
|
if (node != servernode)
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (playernode[reqmapqueue.source] != node)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!IsPlayerAdmin(reqmapqueue.source))
|
||||||
|
{
|
||||||
|
CONS_Debug(DBG_NETPLAY,"Received illegal request map queue cmd from Player %d (%s).\n", reqmapqueue.source+1, player_names[reqmapqueue.source]);
|
||||||
|
SendKick(reqmapqueue.source, KICK_MSG_CON_FAIL);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const boolean doclear = (reqmapqueue.newgametype == ROUNDQUEUE_CLEAR);
|
||||||
|
|
||||||
|
// The following prints will only appear when multiple clients
|
||||||
|
// attempt to affect the round queue at similar time increments
|
||||||
|
if (doclear == true)
|
||||||
|
{
|
||||||
|
if (roundqueue.size == 0)
|
||||||
|
{
|
||||||
|
// therefore this one doesn't really need a error print
|
||||||
|
// because what both players wanted was done anyways
|
||||||
|
//CONS_Alert(CONS_ERROR, "queuemap: Queue is already empty!\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (roundqueue.size >= ROUNDQUEUE_MAX)
|
||||||
|
{
|
||||||
|
CONS_Alert(CONS_ERROR, "Recieved REQMAPQUEUE, but unable to add map beyond %u\n", roundqueue.size);
|
||||||
|
|
||||||
|
// But this one does, because otherwise it's silent failure!
|
||||||
|
// Todo print the map's name, maybe?
|
||||||
|
char rejectmsg[256];
|
||||||
|
strlcpy(rejectmsg, "The server couldn't queue your chosen map.", 256);
|
||||||
|
SendServerNotice(reqmapqueue.source, rejectmsg);
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
UINT8 buf[1+2+1];
|
||||||
|
UINT8 *buf_p = buf;
|
||||||
|
|
||||||
|
WRITEUINT8(buf_p, reqmapqueue.flags);
|
||||||
|
WRITEUINT16(buf_p, reqmapqueue.newgametype);
|
||||||
|
|
||||||
|
WRITEUINT8(buf_p, roundqueue.size);
|
||||||
|
|
||||||
|
// Match Got_MapQueuecmd, but with the addition of reqmapqueue.newmapnum available to us
|
||||||
|
if (doclear == true)
|
||||||
|
{
|
||||||
|
memset(&roundqueue, 0, sizeof(struct roundqueue));
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
G_MapIntoRoundQueue(
|
||||||
|
reqmapqueue.newmapnum,
|
||||||
|
reqmapqueue.newgametype,
|
||||||
|
((reqmapqueue.flags & 1) != 0),
|
||||||
|
false
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
SendNetXCmd(XD_MAPQUEUE, buf, buf_p - buf);
|
||||||
|
}
|
||||||
|
|
||||||
static char NodeToSplitPlayer(int node, int split)
|
static char NodeToSplitPlayer(int node, int split)
|
||||||
{
|
{
|
||||||
if (split == 0)
|
if (split == 0)
|
||||||
|
|
@ -5117,6 +5197,9 @@ static void HandlePacketFromPlayer(SINT8 node)
|
||||||
case PT_SAY:
|
case PT_SAY:
|
||||||
PT_Say(node);
|
PT_Say(node);
|
||||||
break;
|
break;
|
||||||
|
case PT_REQMAPQUEUE:
|
||||||
|
PT_ReqMapQueue(node);
|
||||||
|
break;
|
||||||
case PT_LOGIN:
|
case PT_LOGIN:
|
||||||
if (client)
|
if (client)
|
||||||
break;
|
break;
|
||||||
|
|
|
||||||
|
|
@ -135,6 +135,8 @@ typedef enum
|
||||||
|
|
||||||
PT_SAY, // "Hey server, please send this chat message to everyone via XD_SAY"
|
PT_SAY, // "Hey server, please send this chat message to everyone via XD_SAY"
|
||||||
|
|
||||||
|
PT_REQMAPQUEUE, // Client requesting a roundqueue operation
|
||||||
|
|
||||||
NUMPACKETTYPE
|
NUMPACKETTYPE
|
||||||
} packettype_t;
|
} packettype_t;
|
||||||
|
|
||||||
|
|
@ -401,6 +403,14 @@ struct say_pak
|
||||||
UINT8 source;
|
UINT8 source;
|
||||||
} ATTRPACK;
|
} ATTRPACK;
|
||||||
|
|
||||||
|
struct reqmapqueue_pak
|
||||||
|
{
|
||||||
|
UINT16 newmapnum;
|
||||||
|
UINT16 newgametype;
|
||||||
|
UINT8 flags;
|
||||||
|
UINT8 source;
|
||||||
|
} ATTRPACK;
|
||||||
|
|
||||||
struct netinfo_pak
|
struct netinfo_pak
|
||||||
{
|
{
|
||||||
UINT32 pingtable[MAXPLAYERS+1];
|
UINT32 pingtable[MAXPLAYERS+1];
|
||||||
|
|
@ -451,6 +461,7 @@ struct doomdata_t
|
||||||
responseall_pak responseall; // 256 bytes
|
responseall_pak responseall; // 256 bytes
|
||||||
resultsall_pak resultsall; // 1024 bytes. Also, you really shouldn't trust anything here.
|
resultsall_pak resultsall; // 1024 bytes. Also, you really shouldn't trust anything here.
|
||||||
say_pak say; // I don't care anymore.
|
say_pak say; // I don't care anymore.
|
||||||
|
reqmapqueue_pak reqmapqueue; // Formerly XD_REQMAPQUEUE
|
||||||
} u; // This is needed to pack diff packet types data together
|
} u; // This is needed to pack diff packet types data together
|
||||||
} ATTRPACK;
|
} ATTRPACK;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -109,7 +109,6 @@ static void Got_DiscordInfo(const UINT8 **cp, INT32 playernum);
|
||||||
static void Got_ScheduleTaskcmd(const UINT8 **cp, INT32 playernum);
|
static void Got_ScheduleTaskcmd(const UINT8 **cp, INT32 playernum);
|
||||||
static void Got_ScheduleClearcmd(const UINT8 **cp, INT32 playernum);
|
static void Got_ScheduleClearcmd(const UINT8 **cp, INT32 playernum);
|
||||||
static void Got_Automatecmd(const UINT8 **cp, INT32 playernum);
|
static void Got_Automatecmd(const UINT8 **cp, INT32 playernum);
|
||||||
static void Got_RequestMapQueuecmd(const UINT8 **cp, INT32 playernum);
|
|
||||||
static void Got_MapQueuecmd(const UINT8 **cp, INT32 playernum);
|
static void Got_MapQueuecmd(const UINT8 **cp, INT32 playernum);
|
||||||
static void Got_Cheat(const UINT8 **cp, INT32 playernum);
|
static void Got_Cheat(const UINT8 **cp, INT32 playernum);
|
||||||
|
|
||||||
|
|
@ -317,7 +316,7 @@ const char *netxcmdnames[MAXNETXCMD - 1] =
|
||||||
"SCHEDULETASK", // XD_SCHEDULETASK
|
"SCHEDULETASK", // XD_SCHEDULETASK
|
||||||
"SCHEDULECLEAR", // XD_SCHEDULECLEAR
|
"SCHEDULECLEAR", // XD_SCHEDULECLEAR
|
||||||
"AUTOMATE", // XD_AUTOMATE
|
"AUTOMATE", // XD_AUTOMATE
|
||||||
"REQMAPQUEUE", // XD_REQMAPQUEUE
|
"",
|
||||||
"MAPQUEUE", // XD_MAPQUEUE
|
"MAPQUEUE", // XD_MAPQUEUE
|
||||||
"CALLZVOTE", // XD_CALLZVOTE
|
"CALLZVOTE", // XD_CALLZVOTE
|
||||||
"SETZVOTE", // XD_SETZVOTE
|
"SETZVOTE", // XD_SETZVOTE
|
||||||
|
|
@ -369,7 +368,6 @@ void D_RegisterServerCommands(void)
|
||||||
RegisterNetXCmd(XD_SCHEDULETASK, Got_ScheduleTaskcmd);
|
RegisterNetXCmd(XD_SCHEDULETASK, Got_ScheduleTaskcmd);
|
||||||
RegisterNetXCmd(XD_SCHEDULECLEAR, Got_ScheduleClearcmd);
|
RegisterNetXCmd(XD_SCHEDULECLEAR, Got_ScheduleClearcmd);
|
||||||
RegisterNetXCmd(XD_AUTOMATE, Got_Automatecmd);
|
RegisterNetXCmd(XD_AUTOMATE, Got_Automatecmd);
|
||||||
RegisterNetXCmd(XD_REQMAPQUEUE, Got_RequestMapQueuecmd);
|
|
||||||
RegisterNetXCmd(XD_MAPQUEUE, Got_MapQueuecmd);
|
RegisterNetXCmd(XD_MAPQUEUE, Got_MapQueuecmd);
|
||||||
|
|
||||||
RegisterNetXCmd(XD_CHEAT, Got_Cheat);
|
RegisterNetXCmd(XD_CHEAT, Got_Cheat);
|
||||||
|
|
@ -2937,42 +2935,26 @@ static void Command_RestartLevel(void)
|
||||||
|
|
||||||
static void Handle_MapQueueSend(UINT16 newmapnum, UINT16 newgametype, boolean newencoremode)
|
static void Handle_MapQueueSend(UINT16 newmapnum, UINT16 newgametype, boolean newencoremode)
|
||||||
{
|
{
|
||||||
static char buf[1+2+2];
|
|
||||||
static char *buf_p = buf;
|
|
||||||
|
|
||||||
UINT8 flags = 0;
|
UINT8 flags = 0;
|
||||||
boolean doclear = (newgametype == ROUNDQUEUE_CLEAR);
|
|
||||||
|
|
||||||
CONS_Debug(DBG_GAMELOGIC, "Map queue: mapnum=%d newgametype=%d newencoremode=%d\n",
|
CONS_Debug(DBG_GAMELOGIC, "Map queue: mapnum=%d newgametype=%d newencoremode=%d\n",
|
||||||
newmapnum, newgametype, newencoremode);
|
newmapnum, newgametype, newencoremode);
|
||||||
|
|
||||||
buf_p = buf;
|
|
||||||
|
|
||||||
if (newencoremode)
|
if (newencoremode)
|
||||||
flags |= 1;
|
flags |= 1;
|
||||||
|
|
||||||
WRITEUINT8(buf_p, flags);
|
netbuffer->packettype = PT_REQMAPQUEUE;
|
||||||
WRITEUINT16(buf_p, newgametype);
|
|
||||||
|
|
||||||
if (client)
|
reqmapqueue_pak *reqmapqueue = &netbuffer->u.reqmapqueue;
|
||||||
{
|
|
||||||
WRITEUINT16(buf_p, newmapnum);
|
|
||||||
SendNetXCmd(XD_REQMAPQUEUE, buf, buf_p - buf);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
WRITEUINT8(buf_p, roundqueue.size);
|
reqmapqueue->newmapnum = newmapnum;
|
||||||
|
reqmapqueue->flags = flags;
|
||||||
|
reqmapqueue->newgametype = newgametype;
|
||||||
|
reqmapqueue->source = consoleplayer;
|
||||||
|
|
||||||
if (doclear == true)
|
HSendPacket(servernode, false, 0, sizeof(reqmapqueue_pak));
|
||||||
{
|
|
||||||
memset(&roundqueue, 0, sizeof(struct roundqueue));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
G_MapIntoRoundQueue(newmapnum, newgametype, newencoremode, false);
|
|
||||||
}
|
|
||||||
|
|
||||||
SendNetXCmd(XD_MAPQUEUE, buf, buf_p - buf);
|
// See PT_ReqMapQueue and Got_MapQueuecmd for the next stages
|
||||||
}
|
}
|
||||||
|
|
||||||
static void Command_QueueMap_f(void)
|
static void Command_QueueMap_f(void)
|
||||||
|
|
@ -3129,51 +3111,6 @@ static void Command_QueueMap_f(void)
|
||||||
Z_Free(mapname);
|
Z_Free(mapname);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void Got_RequestMapQueuecmd(const UINT8 **cp, INT32 playernum)
|
|
||||||
{
|
|
||||||
UINT8 flags;
|
|
||||||
boolean setencore;
|
|
||||||
UINT16 mapnumber, setgametype;
|
|
||||||
boolean doclear = false;
|
|
||||||
|
|
||||||
flags = READUINT8(*cp);
|
|
||||||
|
|
||||||
setencore = ((flags & 1) != 0);
|
|
||||||
|
|
||||||
setgametype = READUINT16(*cp);
|
|
||||||
|
|
||||||
mapnumber = READUINT16(*cp);
|
|
||||||
|
|
||||||
if (!IsPlayerAdmin(playernum))
|
|
||||||
{
|
|
||||||
CONS_Alert(CONS_WARNING, M_GetText("Illegal request map queue command received from %s\n"), player_names[playernum]);
|
|
||||||
if (server && playernum != serverplayer)
|
|
||||||
SendKick(playernum, KICK_MSG_CON_FAIL);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
doclear = (setgametype == ROUNDQUEUE_CLEAR);
|
|
||||||
|
|
||||||
if (doclear == true)
|
|
||||||
{
|
|
||||||
if (roundqueue.size == 0)
|
|
||||||
{
|
|
||||||
CONS_Alert(CONS_ERROR, "queuemap: Queue is already empty!\n");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (roundqueue.size >= ROUNDQUEUE_MAX)
|
|
||||||
{
|
|
||||||
CONS_Alert(CONS_ERROR, "queuemap: Unable to add map beyond %u\n", roundqueue.size);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (client)
|
|
||||||
return;
|
|
||||||
|
|
||||||
Handle_MapQueueSend(mapnumber, setgametype, setencore);
|
|
||||||
}
|
|
||||||
|
|
||||||
static void Got_MapQueuecmd(const UINT8 **cp, INT32 playernum)
|
static void Got_MapQueuecmd(const UINT8 **cp, INT32 playernum)
|
||||||
{
|
{
|
||||||
UINT8 flags, queueposition, i;
|
UINT8 flags, queueposition, i;
|
||||||
|
|
|
||||||
|
|
@ -180,8 +180,8 @@ typedef enum
|
||||||
XD_SCHEDULETASK, // 34
|
XD_SCHEDULETASK, // 34
|
||||||
XD_SCHEDULECLEAR, // 35
|
XD_SCHEDULECLEAR, // 35
|
||||||
XD_AUTOMATE, // 36
|
XD_AUTOMATE, // 36
|
||||||
XD_REQMAPQUEUE, // 37
|
// 37 is free
|
||||||
XD_MAPQUEUE, // 38
|
XD_MAPQUEUE = XD_AUTOMATE+2, // 38
|
||||||
XD_CALLZVOTE, // 39
|
XD_CALLZVOTE, // 39
|
||||||
XD_SETZVOTE, // 40
|
XD_SETZVOTE, // 40
|
||||||
XD_TEAMCHANGE, // 41
|
XD_TEAMCHANGE, // 41
|
||||||
|
|
|
||||||
|
|
@ -83,6 +83,7 @@ TYPEDEF (challengeall_pak);
|
||||||
TYPEDEF (responseall_pak);
|
TYPEDEF (responseall_pak);
|
||||||
TYPEDEF (resultsall_pak);
|
TYPEDEF (resultsall_pak);
|
||||||
TYPEDEF (say_pak);
|
TYPEDEF (say_pak);
|
||||||
|
TYPEDEF (reqmapqueue_pak);
|
||||||
TYPEDEF (netinfo_pak);
|
TYPEDEF (netinfo_pak);
|
||||||
|
|
||||||
// d_event.h
|
// d_event.h
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue