diff --git a/src/CommandFormats.hh b/src/CommandFormats.hh index 2aa8b908..93a4ed9a 100644 --- a/src/CommandFormats.hh +++ b/src/CommandFormats.hh @@ -5959,6 +5959,11 @@ struct G_SyncCardTradeServerState_Ep3_6xBB { // 6xBB: BB bank request (handled by the server) +struct G_RequestBankContents_BB_6xBB { + G_UnusedHeader header; + le_uint32_t checksum; // crc32 of the bank contents in memory +} __packed_ws__(G_RequestBankContents_BB_6xBB, 0x08); + // 6xBC: Card counts (Episode 3) // This is sent by the client in response to a 6xB5x38 command. This is used // along with 6xB5x38 so clients can see each other's card counts. Curiously, @@ -5980,6 +5985,9 @@ struct G_CardCounts_Ep3_6xBC { } __packed_ws__(G_CardCounts_Ep3_6xBC, 0x2FC); // 6xBC: BB bank contents (server->client only) +// This is sent in response to a 6xBB command. If the checksum in this command +// doesn't match the checksum the client sent in its 6xBB command, the client +// overwrites its bank data with the data sent in this command. struct G_BankContentsHeader_BB_6xBC { G_ExtendedHeaderT header; diff --git a/src/PlayerInventory.hh b/src/PlayerInventory.hh index 87d2fe67..774b6196 100644 --- a/src/PlayerInventory.hh +++ b/src/PlayerInventory.hh @@ -305,6 +305,10 @@ struct PlayerBankT { /* 0008 */ parray, SlotCount> items; /* 05A8 for 60 items (v1/v2), 12C8 for 200 items (v3/v4) */ + uint32_t checksum() const { + return phosg::crc32(this, 2 * sizeof(U32T) + sizeof(PlayerBankItemT) * min(SlotCount, this->num_items)); + } + void add_item(const ItemData& item, const ItemData::StackLimits& limits) { uint32_t primary_identifier = item.primary_identifier(); diff --git a/src/SendCommands.cc b/src/SendCommands.cc index 0c22bada..ea54c8fb 100644 --- a/src/SendCommands.cc +++ b/src/SendCommands.cc @@ -3045,9 +3045,7 @@ void send_bank(shared_ptr c) { G_BankContentsHeader_BB_6xBC cmd = { {{0xBC, 0, 0}, sizeof(G_BankContentsHeader_BB_6xBC) + items.size() * sizeof(PlayerBankItem)}, - phosg::random_object(), - bank.num_items, - bank.meseta}; + bank.checksum(), bank.num_items, bank.meseta}; send_command_t_vt(c, 0x6C, 0x00, cmd, items); }