From e711753b9d584845e385ada29780b9ed216c4f55 Mon Sep 17 00:00:00 2001 From: Haru Date: Sun, 6 Dec 2015 15:42:56 +0100 Subject: Fixed a validation issue in the NPC Sell List Signed-off-by: Haru --- src/map/npc.c | 18 +++++++++++++----- 1 file changed, 13 insertions(+), 5 deletions(-) (limited to 'src') diff --git a/src/map/npc.c b/src/map/npc.c index 8a7998931..3bd14bf41 100644 --- a/src/map/npc.c +++ b/src/map/npc.c @@ -2076,6 +2076,7 @@ int npc_selllist(struct map_session_data* sd, int n, unsigned short* item_list) double z; int i,skill_t, skill_idx = skill->get_index(MC_OVERCHARGE); struct npc_data *nd; + bool duplicates[MAX_INVENTORY] = { 0 }; nullpo_retr(1, sd); nullpo_retr(1, item_list); @@ -2092,29 +2093,36 @@ int npc_selllist(struct map_session_data* sd, int n, unsigned short* item_list) z = 0; // verify the sell list - for( i = 0; i < n; i++ ) { + for (i = 0; i < n; i++) { int nameid, amount, idx, value; idx = item_list[i*2]-2; amount = item_list[i*2+1]; - if( idx >= MAX_INVENTORY || idx < 0 || amount < 0 ) { + if (idx >= MAX_INVENTORY || idx < 0 || amount < 0) { + return 1; + } + + if (duplicates[idx]) { + // Sanity check. The client sends each inventory index at most once [Haru] return 1; } + duplicates[idx] = true; nameid = sd->status.inventory[idx].nameid; - if( !nameid || !sd->inventory_data[idx] || sd->status.inventory[idx].amount < amount ) { + if (!nameid || !sd->inventory_data[idx] || sd->status.inventory[idx].amount < amount) { return 1; } - if( nd->master_nd ) {// Script-controlled shops decide by themselves, what can be sold and at what price. + if (nd->master_nd) { + // Script-controlled shops decide by themselves, what can be sold and at what price. continue; } value = pc->modifysellvalue(sd, sd->inventory_data[idx]->value_sell); - z+= (double)value*amount; + z += (double)value*amount; } if( nd->master_nd ) { // Script-controlled shops -- cgit v1.2.3-70-g09d2