Issue Information
-
#004057
-
5 - Critical
-
Fixed
Issue Confirmations
-
Yes (0)No (0)


eAAC coin banker missing item check zeny exploit
Posted by Hercules Bot on 13 February 2010 - 07:49 PM
Originally posted by theultramage
http://www.eathena.w...er&showbug=4057
I received a report about an exploit with the custom eAAC coin banker npc, with a video that demonstrated how the issue could be reproduced easily.
Below is the offending code. Notice how the countitem() check is only done at the beginning, followed by a chain of 'next' statements before the actual processing is done (beginner scripter's mistake, I wonder how the reviewers missed this). Also, due to how the actual processing steps are ordered (first get zeny, then delete item), even the recent delitem() script halting system is not able to trap this issue before it's too late.
http://www.eathena.w...er&showbug=4057
I received a report about an exploit with the custom eAAC coin banker npc, with a video that demonstrated how the issue could be reproduced easily.
Below is the offending code. Notice how the countitem() check is only done at the beginning, followed by a chain of 'next' statements before the actual processing is done (beginner scripter's mistake, I wonder how the reviewers missed this). Also, due to how the actual processing steps are ordered (first get zeny, then delete item), even the recent delitem() script halting system is not able to trap this issue before it's too late.
CODE
L_Inputing:
input @coinamount;
if (@coinamount <= 0) {
mes @npcname$;
mes "You didn't input any amount, please retry";
next;
goto L_Inputing;
} else if (countitem(getarg(0)) < @coinamount) {
mes @npcname$;
mes "You don't have enough coins, please get some";
next;
goto L_Menu;
} else if (@coinamount*getarg(1) > @MAX_ZENY) {
mes @npcname$;
mes "I'm sorry, the quantity you inputted gives a bigger zeny amount than the max allowed. I can't allow this.";
next;
goto L_Menu;
}
next;
mes @npcname$;
mes "So, you want to exchange "+@coinamount+" "+@coinname$+" ?";
menu "Yes, I want to exchange this much",-,"No, I want to exchange something else",L_CoinZeny,"No, I want to input another number",L_Inputing,"No, I dont want to exchange anything",L_Menu;
next;
set @price,getarg(1)*@coinamount;
set Zeny,Zeny+@price;
delitem getarg(0),@coinamount;
input @coinamount;
if (@coinamount <= 0) {
mes @npcname$;
mes "You didn't input any amount, please retry";
next;
goto L_Inputing;
} else if (countitem(getarg(0)) < @coinamount) {
mes @npcname$;
mes "You don't have enough coins, please get some";
next;
goto L_Menu;
} else if (@coinamount*getarg(1) > @MAX_ZENY) {
mes @npcname$;
mes "I'm sorry, the quantity you inputted gives a bigger zeny amount than the max allowed. I can't allow this.";
next;
goto L_Menu;
}
next;
mes @npcname$;
mes "So, you want to exchange "+@coinamount+" "+@coinname$+" ?";
menu "Yes, I want to exchange this much",-,"No, I want to exchange something else",L_CoinZeny,"No, I want to input another number",L_Inputing,"No, I dont want to exchange anything",L_Menu;
next;
set @price,getarg(1)*@coinamount;
set Zeny,Zeny+@price;
delitem getarg(0),@coinamount;