Drop various types of packets if level/area doesn't match

This commit is contained in:
MysterD 2020-09-26 15:52:00 -07:00
parent e0bdaa1229
commit 168a41f0f6
22 changed files with 70 additions and 32 deletions

View file

@ -9,6 +9,9 @@
#include "packets/packet.h" #include "packets/packet.h"
#include "../cliopts.h" #include "../cliopts.h"
#define SET_BIT(val, num) ((((u8)(val)) & 0x01) << (num));
#define GET_BIT(val, num) (((val) >> (num)) & 0x01)
// Mario 64 specific externs // Mario 64 specific externs
extern struct MarioState gMarioStates[]; extern struct MarioState gMarioStates[];

View file

@ -11,6 +11,12 @@ void packet_receive(struct Packet* p) {
return; return;
} }
// send an ACK if requested
network_send_ack(p);
// check if we should drop packet
if (!packet_initial_read(p)) { return; }
switch (packetType) { switch (packetType) {
case PACKET_ACK: network_receive_ack(p); break; case PACKET_ACK: network_receive_ack(p); break;
case PACKET_PLAYER: network_receive_player(p); break; case PACKET_PLAYER: network_receive_player(p); break;
@ -35,7 +41,4 @@ void packet_receive(struct Packet* p) {
case PACKET_CUSTOM: network_receive_custom(p); break; case PACKET_CUSTOM: network_receive_custom(p); break;
default: LOG_ERROR("received unknown packet: %d", p->buffer[0]); default: LOG_ERROR("received unknown packet: %d", p->buffer[0]);
} }
// send an ACK if requested
network_send_ack(p);
} }

View file

@ -39,6 +39,7 @@ struct Packet {
u16 cursor; u16 cursor;
bool error; bool error;
bool reliable; bool reliable;
bool levelAreaMustMatch;
u16 seqId; u16 seqId;
bool sent; bool sent;
u8 buffer[PACKET_LENGTH]; u8 buffer[PACKET_LENGTH];
@ -53,8 +54,9 @@ enum KickReasonType {
void packet_receive(struct Packet* packet); void packet_receive(struct Packet* packet);
// packet_read_write.c // packet_read_write.c
void packet_init(struct Packet* packet, enum PacketType packetType, bool reliable); void packet_init(struct Packet* packet, enum PacketType packetType, bool reliable, bool levelAreaMustMatch);
void packet_write(struct Packet* packet, void* data, u16 length); void packet_write(struct Packet* packet, void* data, u16 length);
u8 packet_initial_read(struct Packet* packet);
void packet_read(struct Packet* packet, void* data, u16 length); void packet_read(struct Packet* packet, void* data, u16 length);
u32 packet_hash(struct Packet* packet); u32 packet_hash(struct Packet* packet);
bool packet_check_hash(struct Packet* packet); bool packet_check_hash(struct Packet* packet);
@ -125,7 +127,7 @@ void network_receive_join(struct Packet* p);
// packet_custom.c // packet_custom.c
u8 network_register_custom_packet(void (*send_callback)(struct Packet* p, void* params), void (*receive_callback)(struct Packet* p)); u8 network_register_custom_packet(void (*send_callback)(struct Packet* p, void* params), void (*receive_callback)(struct Packet* p));
void network_send_custom(u8 customId, bool reliable, void* params); void network_send_custom(u8 customId, bool reliable, bool levelAreaMustMatch, void* params);
void network_receive_custom(struct Packet* p); void network_receive_custom(struct Packet* p);
// packet_chat.c // packet_chat.c

View file

@ -13,7 +13,7 @@ static u8 onRemoteChatId = 0;
void network_send_chat(char* message) { void network_send_chat(char* message) {
u16 messageLength = strlen(message); u16 messageLength = strlen(message);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_CHAT, true); packet_init(&p, PACKET_CHAT, true, false);
packet_write(&p, &localChatId, sizeof(u8)); packet_write(&p, &localChatId, sizeof(u8));
packet_write(&p, &messageLength, sizeof(u16)); packet_write(&p, &messageLength, sizeof(u16));
packet_write(&p, message, messageLength * sizeof(u8)); packet_write(&p, message, messageLength * sizeof(u8));

View file

@ -55,7 +55,7 @@ void network_send_collect_coin(struct Object* o) {
enum BehaviorId behaviorId = get_id_from_behavior(o->behavior); enum BehaviorId behaviorId = get_id_from_behavior(o->behavior);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_COLLECT_COIN, true); packet_init(&p, PACKET_COLLECT_COIN, true, true);
packet_write(&p, &localCoinId, sizeof(u8)); packet_write(&p, &localCoinId, sizeof(u8));
packet_write(&p, &behaviorId, sizeof(enum BehaviorId)); packet_write(&p, &behaviorId, sizeof(enum BehaviorId));
packet_write(&p, &o->oPosX, sizeof(f32) * 3); packet_write(&p, &o->oPosX, sizeof(f32) * 3);

View file

@ -52,7 +52,7 @@ void network_send_collect_item(struct Object* o) {
enum BehaviorId behaviorId = get_id_from_behavior(o->behavior); enum BehaviorId behaviorId = get_id_from_behavior(o->behavior);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_COLLECT_ITEM, true); packet_init(&p, PACKET_COLLECT_ITEM, true, true);
packet_write(&p, &localItemId, sizeof(u8)); packet_write(&p, &localItemId, sizeof(u8));
packet_write(&p, &behaviorId, sizeof(enum BehaviorId)); packet_write(&p, &behaviorId, sizeof(enum BehaviorId));
packet_write(&p, &o->oPosX, sizeof(f32) * 3); packet_write(&p, &o->oPosX, sizeof(f32) * 3);

View file

@ -47,7 +47,7 @@ void network_send_collect_star(struct Object* o, s16 coinScore, s16 starIndex) {
enum BehaviorId behaviorId = get_id_from_behavior(o->behavior); enum BehaviorId behaviorId = get_id_from_behavior(o->behavior);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_COLLECT_STAR, true); packet_init(&p, PACKET_COLLECT_STAR, true, false);
packet_write(&p, &gCurrSaveFileNum, sizeof(s16)); packet_write(&p, &gCurrSaveFileNum, sizeof(s16));
packet_write(&p, &gCurrCourseNum, sizeof(s16)); packet_write(&p, &gCurrCourseNum, sizeof(s16));

View file

@ -22,11 +22,11 @@ u8 network_register_custom_packet(void (*send_callback)(struct Packet* p, void*
return i; return i;
} }
void network_send_custom(u8 customId, bool reliable, void* params) { void network_send_custom(u8 customId, bool reliable, bool levelAreaMustMatch, void* params) {
if (customPackets[customId].send_callback == NULL) { return; } if (customPackets[customId].send_callback == NULL) { return; }
struct Packet p; struct Packet p;
packet_init(&p, PACKET_CUSTOM, reliable); packet_init(&p, PACKET_CUSTOM, reliable, levelAreaMustMatch);
packet_write(&p, &customId, sizeof(u8)); packet_write(&p, &customId, sizeof(u8));
customPackets[customId].send_callback(&p, params); customPackets[customId].send_callback(&p, params);
network_send(&p); network_send(&p);

View file

@ -35,7 +35,7 @@ void network_send_inside_painting(void) {
populate_packet_data(&data); populate_packet_data(&data);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_INSIDE_PAINTING, true); packet_init(&p, PACKET_INSIDE_PAINTING, true, false);
packet_write(&p, &data, sizeof(struct PacketInsidePaintingData)); packet_write(&p, &data, sizeof(struct PacketInsidePaintingData));
network_send(&p); network_send(&p);
seqId++; seqId++;

View file

@ -22,7 +22,7 @@ void network_send_join_request(void) {
gOverrideEeprom = eeprom; gOverrideEeprom = eeprom;
struct Packet p; struct Packet p;
packet_init(&p, PACKET_JOIN_REQUEST, true); packet_init(&p, PACKET_JOIN_REQUEST, true, false);
network_send_to(0, &p); network_send_to(0, &p);
LOG_INFO("sending join request"); LOG_INFO("sending join request");
} }
@ -52,7 +52,7 @@ void network_send_join(struct Packet* joinRequestPacket) {
char hash[HASH_LENGTH] = GIT_HASH; char hash[HASH_LENGTH] = GIT_HASH;
struct Packet p; struct Packet p;
packet_init(&p, PACKET_JOIN, true); packet_init(&p, PACKET_JOIN, true, false);
packet_write(&p, &hash, sizeof(u8) * HASH_LENGTH); packet_write(&p, &hash, sizeof(u8) * HASH_LENGTH);
packet_write(&p, &joinRequestPacket->localIndex, sizeof(u8)); packet_write(&p, &joinRequestPacket->localIndex, sizeof(u8));
packet_write(&p, &gCurrSaveFileNum, sizeof(s16)); packet_write(&p, &gCurrSaveFileNum, sizeof(s16));

View file

@ -4,7 +4,7 @@
void network_send_keep_alive(void) { void network_send_keep_alive(void) {
struct Packet p; struct Packet p;
packet_init(&p, PACKET_KEEP_ALIVE, FALSE); packet_init(&p, PACKET_KEEP_ALIVE, false, false);
network_send(&p); network_send(&p);
gLastNetworkSend = clock(); gLastNetworkSend = clock();
LOG_INFO("sending keep alive"); LOG_INFO("sending keep alive");

View file

@ -5,7 +5,7 @@
void network_send_kick(enum KickReasonType kickReason) { void network_send_kick(enum KickReasonType kickReason) {
struct Packet p; struct Packet p;
packet_init(&p, PACKET_KICK, FALSE); packet_init(&p, PACKET_KICK, false, false);
packet_write(&p, &kickReason, sizeof(enum KickReasonType)); packet_write(&p, &kickReason, sizeof(enum KickReasonType));
network_send_to(0, &p); network_send_to(0, &p);
} }

View file

@ -19,7 +19,7 @@ void network_send_leaving(u8 globalIndex) {
} }
struct Packet p; struct Packet p;
packet_init(&p, PACKET_LEAVING, TRUE); packet_init(&p, PACKET_LEAVING, true, false);
packet_write(&p, &globalIndex, sizeof(u8)); packet_write(&p, &globalIndex, sizeof(u8));
if (gNetworkType == NT_SERVER) { if (gNetworkType == NT_SERVER) {
network_send(&p); network_send(&p);

View file

@ -70,7 +70,7 @@ void network_send_level_warp_begin(void) {
populate_packet_data(&data, false, eventId); populate_packet_data(&data, false, eventId);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_LEVEL_WARP, true); packet_init(&p, PACKET_LEVEL_WARP, true, false);
packet_write(&p, &data, sizeof(struct PacketLevelWarpData)); packet_write(&p, &data, sizeof(struct PacketLevelWarpData));
network_send(&p); network_send(&p);
@ -88,7 +88,7 @@ void network_send_level_warp_repeat(void) {
populate_packet_data(&data, false, eventId); populate_packet_data(&data, false, eventId);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_LEVEL_WARP, false); packet_init(&p, PACKET_LEVEL_WARP, false, false);
packet_write(&p, &data, sizeof(struct PacketLevelWarpData)); packet_write(&p, &data, sizeof(struct PacketLevelWarpData));
network_send(&p); network_send(&p);
@ -103,7 +103,7 @@ static void network_send_level_warp_done(u8 remoteEventId) {
populate_packet_data(&data, true, remoteEventId); populate_packet_data(&data, true, remoteEventId);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_LEVEL_WARP, true); packet_init(&p, PACKET_LEVEL_WARP, true, false);
packet_write(&p, &data, sizeof(struct PacketLevelWarpData)); packet_write(&p, &data, sizeof(struct PacketLevelWarpData));
network_send(&p); network_send(&p);

View file

@ -356,7 +356,7 @@ void network_send_object_reliability(struct Object* o, bool reliable) {
// write the packet data // write the packet data
struct Packet p; struct Packet p;
packet_init(&p, PACKET_OBJECT, reliable); packet_init(&p, PACKET_OBJECT, reliable, true);
packet_write_object_header(&p, o); packet_write_object_header(&p, o);
packet_write_object_full_sync(&p, o); packet_write_object_full_sync(&p, o);
packet_write_object_standard_fields(&p, o); packet_write_object_standard_fields(&p, o);

View file

@ -8,9 +8,6 @@
#include "game/area.h" #include "game/area.h"
#include "audio/external.h" #include "audio/external.h"
#define SET_BIT(val, num) ((((u8)(val)) & 0x01) << (num));
#define GET_BIT(val, num) (((val) >> (num)) & 0x01)
#pragma pack(1) #pragma pack(1)
struct PacketPlayerData { struct PacketPlayerData {
u32 rawData[80]; u32 rawData[80];
@ -147,7 +144,7 @@ void network_send_player(void) {
read_packet_data(&data, &gMarioStates[0]); read_packet_data(&data, &gMarioStates[0]);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_PLAYER, false); packet_init(&p, PACKET_PLAYER, false, false);
packet_write(&p, &data, sizeof(struct PacketPlayerData)); packet_write(&p, &data, sizeof(struct PacketPlayerData));
network_send(&p); network_send(&p);
} }

View file

@ -1,7 +1,8 @@
#include "../network.h" #include "../network.h"
#include "game/area.h"
static u16 nextSeqNum = 1; static u16 nextSeqNum = 1;
void packet_init(struct Packet* packet, enum PacketType packetType, bool reliable) { void packet_init(struct Packet* packet, enum PacketType packetType, bool reliable, bool levelAreaMustMatch) {
memset(packet->buffer, 0, PACKET_LENGTH); memset(packet->buffer, 0, PACKET_LENGTH);
packet->buffer[0] = (char)packetType; packet->buffer[0] = (char)packetType;
if (reliable) { if (reliable) {
@ -14,7 +15,18 @@ void packet_init(struct Packet* packet, enum PacketType packetType, bool reliabl
packet->cursor = 3; packet->cursor = 3;
packet->error = false; packet->error = false;
packet->reliable = reliable; packet->reliable = reliable;
packet->levelAreaMustMatch = levelAreaMustMatch;
packet->sent = false; packet->sent = false;
// write packet flags
u8 flags;
flags |= SET_BIT(packet->levelAreaMustMatch, 0);
packet_write(packet, &flags, sizeof(u8));
if (levelAreaMustMatch) {
packet_write(packet, &gCurrLevelNum, sizeof(s16));
packet_write(packet, &gCurrAreaIndex, sizeof(s16));
}
} }
void packet_write(struct Packet* packet, void* data, u16 length) { void packet_write(struct Packet* packet, void* data, u16 length) {
@ -24,6 +36,27 @@ void packet_write(struct Packet* packet, void* data, u16 length) {
packet->cursor += length; packet->cursor += length;
} }
u8 packet_initial_read(struct Packet* packet) {
// read packet flags
u8 flags = 0;
packet_read(packet, &flags, sizeof(u8));
packet->levelAreaMustMatch = GET_BIT(flags, 0);
if (packet->levelAreaMustMatch) {
s16 currLevelNum;
s16 currAreaIndex;
packet_read(packet, &currLevelNum, sizeof(s16));
packet_read(packet, &currAreaIndex, sizeof(s16));
if (currLevelNum != gCurrLevelNum || currAreaIndex != gCurrAreaIndex) {
// drop packet
return FALSE;
}
}
// don't drop packet
return TRUE;
}
void packet_read(struct Packet* packet, void* data, u16 length) { void packet_read(struct Packet* packet, void* data, u16 length) {
if (data == NULL) { packet->error = true; return; } if (data == NULL) { packet->error = true; return; }
u16 cursor = packet->cursor; u16 cursor = packet->cursor;

View file

@ -41,7 +41,7 @@ void network_send_ack(struct Packet* p) {
// send back the ACK // send back the ACK
struct Packet ack = { 0 }; struct Packet ack = { 0 };
packet_init(&ack, PACKET_ACK, false); packet_init(&ack, PACKET_ACK, false, false);
packet_write(&ack, &seqId, sizeof(u16)); packet_write(&ack, &seqId, sizeof(u16));
network_send_to(0, &ack); network_send_to(0, &ack);
} }

View file

@ -13,7 +13,7 @@ void network_send_reservation_request(void) {
assert(gNetworkType == NT_CLIENT); assert(gNetworkType == NT_CLIENT);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_RESERVATION_REQUEST, true); packet_init(&p, PACKET_RESERVATION_REQUEST, true, false);
network_send(&p); network_send(&p);
} }
@ -48,7 +48,7 @@ void network_send_reservation(void) {
} }
struct Packet p; struct Packet p;
packet_init(&p, PACKET_RESERVATION, true); packet_init(&p, PACKET_RESERVATION, true, false);
packet_write(&p, reservedObjs, sizeof(u8) * RESERVATION_COUNT); packet_write(&p, reservedObjs, sizeof(u8) * RESERVATION_COUNT);
network_send(&p); network_send(&p);
} }

View file

@ -5,7 +5,7 @@
void network_send_save_file(s32 fileIndex) { void network_send_save_file(s32 fileIndex) {
assert(gNetworkType == NT_CLIENT); assert(gNetworkType == NT_CLIENT);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_SAVE_FILE, true); packet_init(&p, PACKET_SAVE_FILE, true, false);
packet_write(&p, &fileIndex, sizeof(s32)); packet_write(&p, &fileIndex, sizeof(s32));
network_send_to(gNetworkPlayerServer->localIndex, &p); network_send_to(gNetworkPlayerServer->localIndex, &p);
} }

View file

@ -46,7 +46,7 @@ void network_send_spawn_objects(struct Object* objects[], u32 models[], u8 objec
assert(objectCount < MAX_SPAWN_OBJECTS_PER_PACKET); assert(objectCount < MAX_SPAWN_OBJECTS_PER_PACKET);
struct Packet p; struct Packet p;
packet_init(&p, PACKET_SPAWN_OBJECTS, true); packet_init(&p, PACKET_SPAWN_OBJECTS, true, true);
packet_write(&p, &localSpawnId, sizeof(u8)); packet_write(&p, &localSpawnId, sizeof(u8));
packet_write(&p, &objectCount, sizeof(u8)); packet_write(&p, &objectCount, sizeof(u8));

View file

@ -7,7 +7,7 @@ extern struct Object* gCurrentObject;
void network_send_spawn_star(struct Object* o, u8 starType, f32 x, f32 y, f32 z, u32 behParams) { void network_send_spawn_star(struct Object* o, u8 starType, f32 x, f32 y, f32 z, u32 behParams) {
struct Packet p; struct Packet p;
packet_init(&p, PACKET_SPAWN_STAR, true); packet_init(&p, PACKET_SPAWN_STAR, true, true);
packet_write(&p, &starType, sizeof(u8)); packet_write(&p, &starType, sizeof(u8));
packet_write(&p, &x, sizeof(f32)); packet_write(&p, &x, sizeof(f32));
packet_write(&p, &y, sizeof(f32)); packet_write(&p, &y, sizeof(f32));