Author Topic: Need help in stopping Cheaters  (Read 3342 times)

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Need help in stopping Cheaters
« on: May 24, 2008, 08:25:14 AM »
Hi,

I've been developing my EzRPG game, and learning PHP as I go.

I have made a few mods in my game, and everything is working pretty well.  One of the mods I've made is to give users access to new cities as they gain levels.   

I have a bus.php and this page displays links to new cities as you gain levels.   When you click on the link for a city it updates the city_ID in the players table.   

This all works great, but I found if a user manually just types in the city_ID it will update the field, regardless of what level they are.   

For example,  if a user is level 1.   They could have access to city id 1 or 2

but if they type in
bus.php?act=go&id=100

they just moved themselves to city_ID 100 (even tho that city doesn't even exist yet)

I've attached my bus.php,  how could I stop a player from doing that.
Would an IF statement somewhere that checks the level work?  Is there a better way?

I have a couple mods where I'm going to need to do similar checks, so I want to make sure I do this right and stop cheaters from ruining the game.

Thanks!

Offline leZourite

  • Level 12
  • *
  • Posts: 81
  • Reputation: +2/-0
    • View Profile
    • After doomsday
Re: Need help in stopping Cheaters
« Reply #1 on: May 24, 2008, 09:13:48 AM »
do you use oop, or procedural ?

Anyway here is an example in procedural.

example :
Code: [Select]
$userquery = mysql_query ("SELECT level FROM users WHERE userid=$playerid LIMIT 1");
$cityquery =  mysql_query ("SELECT citylevel FROM cities WHERE cityid=$id LIMIT 1"); // the $id being what is passed from the querystring, you should of course sanitize/check before executing the query

$userlevel = mysql_fetch_assoc($userquery); // retrieve level of user
$citylevel = mysql_fetch_assoc($cityquery); // retrieve level of city

// Edit you can even add more checks here like

if (empty($citylevel)) { die(" This city doesn't exist !!"); }

if ($userlevel['level'] >= $citylevel['citylevel']) {

// process code to move user
}

else {

// display error

}


The queries in sql should be tweaked to work with your database of course i used arbitrary field names. Also, i didn't check your file so if it comes from the eZrpg from zeggy the sql queries go through a class (and it's then shorter).

Anyway this is the basic idea of what you need to do :)
« Last Edit: May 24, 2008, 09:18:24 AM by leZourite »

Offline leZourite

  • Level 12
  • *
  • Posts: 81
  • Reputation: +2/-0
    • View Profile
    • After doomsday
Re: Need help in stopping Cheaters
« Reply #2 on: May 25, 2008, 02:09:19 AM »
Ok after looking at the source code it's easy to do, note that as i don't know the way your database is setup i am going to put some arbitrary value in there... this code will not work as is you have to mod it of course.

1) change $query = $db->execute("select `City_ID`, `City_Name`, `Cost` from `Cities` where `City_ID`=?", array($_GET['id']));

with $query = $db->execute("select `City_ID`, `City_Name`, `Cost`, `Level`  from `Cities` where `City_ID`=?", array($_GET['id']));

(check that there is a Field "Level" in the table Cities, and if it's another name, change the code accordingly)

2) add before this
Code: [Select]
If ($player->City_ID == $cityid) {
        include("templates/private_header.php");
        echo "Are you high?  You're already here moron<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;
    }

the following code :
Code: [Select]
If ($player->Level < $buscost1['Level']) { // Check that there is a method to retrieve the level before...
        include("templates/private_header.php");
        echo "You can't access this city<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;
    }

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #3 on: May 25, 2008, 08:18:35 AM »
Ok after looking at the source code it's easy to do, note that as i don't know the way your database is setup i am going to put some arbitrary value in there... this code will not work as is you have to mod it of course.

1) change $query = $db->execute("select `City_ID`, `City_Name`, `Cost` from `Cities` where `City_ID`=?", array($_GET['id']));

with $query = $db->execute("select `City_ID`, `City_Name`, `Cost`, `Level`  from `Cities` where `City_ID`=?", array($_GET['id']));

(check that there is a Field "Level" in the table Cities, and if it's another name, change the code accordingly)

2) add before this
Code: [Select]
If ($player->City_ID == $cityid) {
        include("templates/private_header.php");
        echo "Are you high?  You're already here moron<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;
    }

the following code :
Code: [Select]
If ($player->Level < $buscost1['Level']) { // Check that there is a method to retrieve the level before...
        include("templates/private_header.php");
        echo "You can't access this city<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;
    }

wow thank you!!
I was going to give what you posted yesterday a try and post back, but I decided to try and put up sheetrock in my garage yesterday, and let's just say that's is taking way longer then I thought (lol)

Hopefully I get some time today, to give this a try.   Thank You, I really really appreciate your help!

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #4 on: May 26, 2008, 10:03:41 AM »
Hi,

I just gave your suggestion a try, but it doesn't seem to be working. 
I can still type in any city ID into the address bar, and it takes me there.

I think I did everything right, here is my updated page.

Offline leZourite

  • Level 12
  • *
  • Posts: 81
  • Reputation: +2/-0
    • View Profile
    • After doomsday
Re: Need help in stopping Cheaters
« Reply #5 on: May 26, 2008, 01:31:05 PM »
Ok i know what's up, but first i need to know something :

does $player->Level exist ? that would trigger an error if it's not the case

Change the beginning of your code with the following (starting form the line with $query):

Code: [Select]
$query = $db->execute("select `City_ID`, `City_Name`, `Cost`, `Minimum_Level`  from `Cities` where `City_ID`=?", array($_GET['id']));

while ($buscost1 = $query->fetchrow()) {
$buscost2 = $buscost1['Cost'];
$citylvl = $buscost1['Minimum_Level'];
$cityID = $buscost1['City_ID'];
}

if ($_GET['act'] == "go") {

    if (empty($cityID) ) {
        include("templates/private_header.php");
        echo "This city doesn't exist duh duh duh !!<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;

   }
   
    if ($player->Level < $citylvl) { // Check that there is a method to retrieve the level before...
        include("templates/private_header.php");
        echo "You can't access this city<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;
    }

    if ($player->gold < $buscost2) {
        include("templates/private_header.php");
        echo "Hey everyone look, this wanna be gansta thinks this bus is free!<p>";
        echo "<a href=\"home.php\">Home</a>\n";
        include("templates/private_footer.php");
        exit;
    }

// continue process here
       

I changed the While loop so it takes other parameters than the bus cost (because other value would be 0), also added a check that the City_ID retrieved by the query is not null or = 0 (in this case it would mean the city doesn't exist), then changed the order to check the city level (as well as affecting a correct variable for it.

if $player->Level is a correct method the code above should work a treat.
« Last Edit: May 26, 2008, 01:40:15 PM by leZourite »

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #6 on: May 26, 2008, 10:37:32 PM »
Yes, there is a field labeled 'level' in the players table.

I just gave this a try, and it's getting closer.   
It wont' allow me to enter in any ID into the browser now, it comes up with the error that the city doesn't exist.

and if I try and enter a city that I shouldn't have access too, I get the warning too.

But, it also won't allow me to go to the cities that I should have access too.
I get the same error,  for example a level 1 should be able to enter city ID 1 and 2,  but the modification to the code is saying the player doesn't have access.


Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #7 on: May 26, 2008, 10:39:24 PM »
Nevermind!

I got it working !

the field is' level'  not' Level' :)

I made the change and it appears to be working now

thank you again for your help

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #8 on: June 09, 2008, 08:02:18 PM »
Hello Again!

I'm trying to do something similar to what we did earlier with my bus page,  to my shop page.

Basically what I have is, different shops per city.   Some cities have more then 1 shop, others only have 1 shop.

What I want to do is make it so users can't manually type in the URL to buy the items from the shops if they are in the wrong city (or even the wrong shop).   Since better weapons are available in the higher level cities.

I thought it would be similar to the bus page, but I'm having problems with this.   Here is my current shop.php, everything works fine if you just click on the links like you should.  But a cheater can just type in the URL to a shop in another city and buy anything they want.

Currently in my players table I have a field named City_ID (what city the player is currently in), 
In the shops table I have a field named Shop_City_ID (this determines what city this shop will appear)
I also have a cities table with the primary key field named City_ID


This was my first mod to ezRPG and my first crack at coding something like this.  I took the original shop.php and modified it to work like I wanted.  I have a feeling a ton can be changed to make it work better,  any suggestions are welcomed!

Offline hobotown

  • Level 4
  • *
  • Posts: 13
  • Reputation: +0/-0
    • View Profile
    • HoboTown
Re: Need help in stopping Cheaters
« Reply #9 on: June 09, 2008, 08:46:37 PM »
quick question, when they change city is there a variable update to say so

ie. update Players where city=1
$5 signup bonus @ www.hobotown.co.uk

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #10 on: June 09, 2008, 08:50:13 PM »
Yes, when they move from city to city, the city_ID field in the players table is updated to reflect this.

Is this what you meant?



Offline hobotown

  • Level 4
  • *
  • Posts: 13
  • Reputation: +0/-0
    • View Profile
    • HoboTown
Re: Need help in stopping Cheaters
« Reply #11 on: June 09, 2008, 09:00:32 PM »
well i dont know the script but roughly your after.

      <?php
if ($stat[city] != thecity) {
   print "You're not in right city.";
   exit;
}
?>
$5 signup bonus @ www.hobotown.co.uk

Offline hobotown

  • Level 4
  • *
  • Posts: 13
  • Reputation: +0/-0
    • View Profile
    • HoboTown
Re: Need help in stopping Cheaters
« Reply #12 on: June 09, 2008, 09:02:53 PM »
or changing the example above

<?

If ($player->City_ID != $cityid) {
        include("templates/private_header.php");
        echo "Are you high?  you cant buy that here<p>"; ?>
$5 signup bonus @ www.hobotown.co.uk

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #13 on: June 09, 2008, 10:04:39 PM »
That's almost exactly what I had, but it's not working.

I think I need to do 2 things,  the first is to check to make sure they are in the correct city.
Then also make sure they are in the correct shop???   To check for the correct shop, I'm almost thinking I'll need to add another field to my players table to keep this info? 

I don't want players to be able to even see what items are in the stores they can't buy from yet.   

I have a feeling I'm just over thinking this, and there has to be a better way to make this all work.

So I need to stop them from manually typing in the URL to a city
ex.  http://www.caraudiocentral.net/CAC_Mafia_Life/shop3.php?act=go&id=10

And I also need to stop them from being able to manually type in an item from any city
ex. http://www.caraudiocentral.net/CAC_Mafia_Life/shop3.php?act=buy&id=6   

Offline leZourite

  • Level 12
  • *
  • Posts: 81
  • Reputation: +2/-0
    • View Profile
    • After doomsday
Re: Need help in stopping Cheaters
« Reply #14 on: June 09, 2008, 10:29:36 PM »
whatever you do post or query string people will still be able to hijack your forms to change location and whatnot.

What you need to do is that you check that the item belongs to the right shop, and to do so a fast query to check that the  ID of the item is in the right table for the right shop id and you are set, if the result is null/empty then the guy tries to cheat :).

Tell me are you using this on a production game or just a test game ?

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #15 on: June 10, 2008, 04:51:39 PM »
The game hasn't been released to anyone yet, besides testers.
I have it here if you want to take a look at it.

http://www.caraudiocentral.net/CAC_Mafia_Life/home.php

So how should I go and stop people from cheating?

I want to get as many loopholes plugged before I go any further with the game.

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #16 on: June 12, 2008, 09:15:53 PM »
whatever you do post or query string people will still be able to hijack your forms to change location and whatnot.

What you need to do is that you check that the item belongs to the right shop, and to do so a fast query to check that the  ID of the item is in the right table for the right shop id and you are set, if the result is null/empty then the guy tries to cheat :).

Tell me are you using this on a production game or just a test game ?

I'm not really sure what your saying,  what do you mean to do a fast query and check that the item is in the right table?



Offline leZourite

  • Level 12
  • *
  • Posts: 81
  • Reputation: +2/-0
    • View Profile
    • After doomsday
Re: Need help in stopping Cheaters
« Reply #17 on: June 13, 2008, 05:17:14 AM »
ok, when buying something i suppose that you are sending the item's ID right ?

say the url is shop.php?shopid=5, if you do a post (from a form) with "itemid", you should get by querystring shopid = 5 and itemid=10 (say for the sake of the example the item id is 10).

what you have to do is a query like this :

SELECT shops.name FROM shops INNER JOIN shopsitems ON shops.id = shopsitems.shopid WHERE shops.id =5 AND shopitems.itemid = 10

This of course works if you have your tables setup like this :

table shops               table shopsitems                             table items
**id                          **id                                                  **id
name                        *shopid                                            itemname
type                         *itemid                                             etc....
level                          etc...                   

I didn't check ezrpg but i think it "may" use something along the line. ** means primarykey *means index (or if you are using innodb a foreignkey)

What it means is that your table "shopsitems" stores both IDs from the table "shops" and the table "items" to keep track of what item goes to what shop. So usually a query like the one i built should work : if in the table shops "inner join" (linked to) table shopsitems there is no shop, and no item (ie the querystring/form is being manipulated) then you won't have any results and it will show that the person tried to access a resource he shouldn't have.

The query can be much more complex as well, like checking that the item exists in the item table as well.

Please note : I didn't use a very correct notation for tables' fields, tables shouldn't have fields with the same name (because of ambiguity that may arises) . But looking at your database will give you all the clues anyway.

Also contrary to last time i don't give you the whole solution because as you are learning to code it's best you search how to make it properly.

Good luck !

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #18 on: June 15, 2008, 09:58:35 AM »
Thanks,
I've been trying to get back to this sooner.

My table structure is like this.
Table:blueprint_items
**ID
BP_Shop_ID
item_name
etc

Table: Shops
Shop_ID
Shop_City_ID
Shop_Name

Table: Cities
City_ID
City_Name
etc.

So how it works right now is, depending on what city they are in.  It will display a list of shops in the city, they click on the shop and it displays the items.

To display the shops, it uses this.
Code: [Select]
$queryshop = $db->execute("SELECT * FROM Shops Where $player->City_ID = Shop_City_ID");
echo "Here are the shopping areas available here.<p>";
echo "<table width=\"100%\" border=\"1\">\n";
echo "<th width=\"199\" class=\"cellheader\">Shop</th>";
echo "<th width=\"217\" class=\"cellheader\">Description</th>";
while ($getshops = $queryshop->fetchrow())
{
echo "";


echo "<tr>";

echo "<td width=\"199\"><a href='shop3.php?act=go&id={$getshops['Shop_ID']}'>{$getshops['Shop_Name']}</a></td>\n";
echo "<td width=\"217\">";
echo "{$getshops['Shop_Description']}";
echo "</td>\n";
echo "</tr>\n";
}
echo "</table>\n";


When the users clicks on the name of the shop it, displays the shop items.
Code: [Select]
if ($_GET['act'] == go)
{
$shopid = $_GET['id'];
$getstuff = $db->execute("SELECT * FROM blueprint_items Where $shopid = BP_Shop_ID");




while ($item = $getstuff->fetchrow())

{

echo "<fieldset>\n";
echo "<legend><b>" . $item['name'] . "</b></legend>\n";
echo "<table width=\"100%\">\n";
echo "<tr><td width=\"17%\"><image src='$item[Item_Image]' alt='item' /></td>\n";
echo "<td width=\"59%\">";
echo $item['description'] . "\n<br /><br />";
echo "<b>Effectiveness:</b> " . $item['effectiveness'] . "\n";
echo "</td><td width=\"24%\">";
echo "<b>Price:</b> " . $item['price'] . "<br />";
echo "<a href=\"shop3.php?act=buy&id=" . $item['id'] . "\">Buy</a><br />";
echo "</td></tr>\n";
echo "</table>";
echo "</fieldset>\n<br />";
}

}

So looking at your table structure example, I need to modify how my structure is?
Since I don't have a table that stores both ShopID and ItemID's?

Or is there a way to stop cheaters using my table structure that I have?






Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #19 on: June 17, 2008, 09:22:50 AM »
OK,
I'm going to try and work on this tonight.

So it looks like the only way to stop cheaters from buying/viewing items from shops they aren't suppose too, is to change my table structure?

Or is there a way to stop them with what I have already?

I was hoping there was a way without having to create another table, since it will get difficult trying to remember all the ID's  when creating new city/shops/items etc.

Offline leZourite

  • Level 12
  • *
  • Posts: 81
  • Reputation: +2/-0
    • View Profile
    • After doomsday
Re: Need help in stopping Cheaters
« Reply #20 on: June 17, 2008, 12:59:11 PM »
from what i can see you have a shopID in your blue prints table right ? so it means that items are bound to one shop at a time. you have everything you need to work i think :)

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #21 on: June 17, 2008, 01:48:30 PM »
OK,
I guess it's confusing me a little since you have a shop/items table of it's own, plus an items table and also a shops table.

So the next part I'm not really sure of is,  do I make an extra IF statement to my buy action, that uses a query similar to the one you posted earlier? 



Code: [Select]
if ($get('act') == buy {


I also need to stop them from even viewing the shops, if they are in the wrong city too.

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #22 on: June 17, 2008, 05:50:38 PM »
I'm sorry, I'm looking at that query, and just not understanding where I need to put it?

I think I need to have 2 checks.
1 is to stop a users from trying to view a shop they don't have access too, for example a shop in a different city.
/shop3.php?act=go&id=2
I need to stop them from just changing the number.

Then I need to stop them from buying any items in any shop they don't have access too.
/shop3.php?act=buy&id=10
again stopping them from changing that number.

I'm trying to figure out how the query you posted works, where does it need to go? 

SELECT shops.name FROM shops INNER JOIN shopsitems ON shops.id = shopsitems.shopid WHERE shops.id =5 AND shopitems.itemid = 10

in my page, I already use this to display the list of shops for the current city.
Code: [Select]
$queryshop = $db->execute("SELECT * FROM Shops Where $player->City_ID = Shop_City_ID");

Is there anyway to use this query results elsewhere in my page as a check?

Then when the users clicks on a shop, I use this query to gather the items.
Code: [Select]
$query = $db->execute("select `id`, `name`, `price`, `Item_Image` from `blueprint_items` where `id`=?", array($_GET['id']));

I just want to make sure I'm not doubling the work in my pages.

I've also attached my shop3.php.   

This was my first mod, and used the original ezRPG shop page, and it appears to all work (except for the fact that you can just update the URL and get anything you want).  I'm really wondering if what I did is correct, is there a better way to accomplish what I want to do.

Offline mobeamer

  • Level 13
  • *
  • Posts: 93
  • Reputation: +0/-0
    • View Profile
    • Untouchable Games
Re: Need help in stopping Cheaters
« Reply #23 on: June 18, 2008, 10:45:26 AM »
I hesitate to suggest it but it seems so simple....why not add the shop id to your second statement. Then you don't need the first one...something like the following:

$query = $db->execute("select `id`, `name`, `price`, `Item_Image` from `blueprint_items` inner join Shops on Shops.shop_id = blueprint_items.shop_id where Shops.Shop_city_id = $player->Shop_City_ID and `id`=?", array($_GET['id']));

alternatively:
select id, name, price, Item_Image
from blueprint_items
inner join Shops on Shops.shop_id = blueprint_items.shop_id
where Shops.shop_city_id = $player->City_ID
and id = $_GET['id'];

My 2 cents...hope it helps.

I build games
My Blog

Offline cdoyle

  • Level 11
  • *
  • Posts: 67
  • Reputation: +1/-0
    • View Profile
Re: Need help in stopping Cheaters
« Reply #24 on: June 18, 2008, 09:00:54 PM »
I hesitate to suggest it but it seems so simple....why not add the shop id to your second statement. Then you don't need the first one...something like the following:

$query = $db->execute("select `id`, `name`, `price`, `Item_Image` from `blueprint_items` inner join Shops on Shops.shop_id = blueprint_items.shop_id where Shops.Shop_city_id = $player->Shop_City_ID and `id`=?", array($_GET['id']));

alternatively:
select id, name, price, Item_Image
from blueprint_items
inner join Shops on Shops.shop_id = blueprint_items.shop_id
where Shops.shop_city_id = $player->City_ID
and id = $_GET['id'];

My 2 cents...hope it helps.

Hi,
thanks for replying.

Just to make sure I understand what you're saying. 
On my page shop3.php,  I should remove the $queryshop query.
and then update the other query to

$query = $db->execute("select `id`, `name`, `price`, `Item_Image` from `blueprint_items` inner join Shops on Shops.shop_id = blueprint_items.shop_id where Shops.Shop_city_id = $player->Shop_City_ID and `id`=?", array($_GET['id']));

How my page works right now, it was using $queryshop to display the shops available for this city.
The user clicks on the shops, and then it brings up the items from that shop.

If I remove it the first query, how will it display the shops?  Since the second query doesn't run until they click on the shop name?




 


SimplePortal 2.3.3 © 2008-2010, SimplePortal