ben_1uk Posted January 30, 2014 Share Posted January 30, 2014 (edited) Hi everyone, My SQL database has been the victim of numerous SQL injection attempts over a period of time now and i've reached a point where it's really starting to concern me and I want to try and resolve the issue. I've done a lot of research and reading via the Internet from numerous sources and I'm just getting more and more confused with the different things suggested and I'm going round in circles without getting any closer to a solution. I'm hoping that somebody can help with the latest attempt of SQL injection I've been notified of. This is the latest warning I have received: SELECT p.id as parentID, p.name as parentName, p.description, p.logo as parentLogo, p.parent, p.active FROM com_catalogue_category p LEFT JOIN com_catalogue_category c ON (c.id = p.parent) WHERE p.id = '711111111111111111111111111' UNION SELECT unhex(hex(CONCAT(CHAR(100,100,100),CHAR(91,67,79,76,85,77,78,95,78,65,77,69,93),COLUMN_NAME,CHAR(91,67,79,76,85,77,78,95,78,65,77,69,93),CHAR(91,84,65,66,76,69,95,78,65,77,69,93),TABLE_NAME,CHAR(91,84,65,66,76,69,95,78,65,77,69,93),CHAR(91,84,65,66,76,69,95,83,67,72,69,77,65,93),TABLE_SCHEMA,CHAR(91,84,65,66,76,69,95,83,67,72,69,77,65,93)))),13 FROM information_schema.COLUMNS WHERE (`COLUMN_NAME` LIKE char(37,109,97,105,108,37) or `COLUMN_NAME` LIKE char(37,108,111,103,105,110,37)) AND ( DATA_TYPE=char(99,104,97,114) OR DATA_TYPE=char(118,97,114,99,104,97,114) OR DATA_TYPE=char(116,101,120,116)) limit 12,1 -- /* order by 'as' The E-mail notfication points to a line of code in a dbFunctions php file, but I don't really know what it is I need to address . Can someone please help me? Thank you. Edited January 30, 2014 by ben_1uk Quote Link to comment Share on other sites More sharing options...
mac_gyver Posted January 30, 2014 Share Posted January 30, 2014 the issue is actually a straight forward one. all data that your script receives can be anything (i.e. you cannot assume that the data is even present at all or that integers will be just an integer, dates will be in the expected format, or strings will contain safe content...) each piece of data must first be validated/cast to insure it contains only a value/string of the expected type/format/content. for general/arbitrary string data, like a comment, blog, forum post..., using your database library's string escape function (or using prepared queries) will at least make it safe for inserting into a sql query statement (the data can still contain links/spam content or XSS/client-side issues, but that is a different subject from sql injection.) also, using your database libraries string escape function (or using prepared queries) on all string data will prevent sql errors if the expected string data happens to contain any special sql characters that would break the sql syntax of the query. apparently, your script is expecting an id, which would be an integer with a value greater than 0 (even though you have surrounded it with single-quotes in the query like it is a string.) your task would be to validate/cast it as an integer, then to test if the value is greater-than zero before using it in the sql statement. Quote Link to comment Share on other sites More sharing options...
ben_1uk Posted January 30, 2014 Author Share Posted January 30, 2014 the issue is actually a straight forward one. all data that your script receives can be anything (i.e. you cannot assume that the data is even present at all or that integers will be just an integer, dates will be in the expected format, or strings will contain safe content...) each piece of data must first be validated/cast to insure it contains only a value/string of the expected type/format/content. for general/arbitrary string data, like a comment, blog, forum post..., using your database library's string escape function (or using prepared queries) will at least make it safe for inserting into a sql query statement (the data can still contain links/spam content or XSS/client-side issues, but that is a different subject from sql injection.) also, using your database libraries string escape function (or using prepared queries) on all string data will prevent sql errors if the expected string data happens to contain any special sql characters that would break the sql syntax of the query. apparently, your script is expecting an id, which would be an integer with a value greater than 0 (even though you have surrounded it with single-quotes in the query like it is a string.) your task would be to validate/cast it as an integer, then to test if the value is greater-than zero before using it in the sql statement. Thanks for your reply mac_gyver, So, basically what you are saying, is that there must be a validation process to check whether what's being asked of the sql database is safe / expected, and not malicious. If I understand you correctly, the existing php script could handle the query better and safer than it is at the moment. Would it help if I were to add a sample of my code to show where I'm at at present? Thanks again for your help. Quote Link to comment Share on other sites More sharing options...
ben_1uk Posted February 4, 2014 Author Share Posted February 4, 2014 Hi there, I've looked into the above again having done more research and think the statement can be broken in two. I think the word UNION adds a second query to the statement. The second query looks like it is trying to retrieve information about my database, but I'm not 100% sure. I have found the below example of how to prevent database attack using the mysql_real_escape_string() function: <?php function check_input($value) { // Stripslashes if (get_magic_quotes_gpc()) { $value = stripslashes($value); } // Quote if not a number if (!is_numeric($value)) { $value = "'" . mysql_real_escape_string($value) . "'"; } return $value; } $con = mysql_connect("localhost", "peter", "abc123"); if (!$con) { die('Could not connect: ' . mysql_error()); } // Make a safe SQL $user = check_input($_POST['user']); $pwd = check_input($_POST['pwd']); $sql = "SELECT * FROM users WHERE user=$user AND password=$pwd"; mysql_query($sql); mysql_close($con); ?> However, because the above script is a generic one, I'm trying to figure out how to implement it with the existing PHP I've inherited from my predecessor. Again, any help would be really appreciated. Thank you. Quote Link to comment Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.