views:

354

answers:

4

Dear stackoverflowers

I am using mysql and trying to block unwanted queries injection of people who will try to use my single query to run several ones. ie, for example when i have the parameter "?id=3", people can try to run it with ="id=3;drop table users"

Now, i know that the best way to avoid this is by parsing and checking the parameter, but is there a way to change the concatenated queries delimiter from ";" to something like "%^#$%@#$^$"?

+6  A: 

Security through obscurity is useless. Take the time to write the proper code to protect against the SQL injection attacks. Doing it up front will cost you a lot less than doing it after you've had a successful attack run against your code!

scwagner
yes ma'am. i guess you are right, yet, i need a temporary patch.
+4  A: 

The best way to defend against injection attacks is to use Prepared Statements.

By using Prepared Statements, you are immune to most injection attacks (which of course aren't the only security vulnerability you need to think about, but they're a pretty major one.)

RichieHindle
+1 Yes it is the best single thing you can do, but it's not 100% proof.
Bill Karwin
+2  A: 

When you call mysql_query or mysql_real_query, it won't run multiple statements anyway, so the statement delimiter doesn't really matter. You can enable multiple statements per query when you connect, but since you're trying to avoid that ability, simply don't enable it.

An even better option for avoid SQL injection is to use prepared statements. Start with mysql_stmt_init and mysql_stmt_prepare with placeholders for your statement's parameters, and then fill in the parameters with mysql_stmt_bind_param before mysql_stmt_execute. If you're not calling the API directly, then whatever wrapper library you have should also provide support for prepared statements. (If it doesn't support them, then consider switching to a better wrapper.)

Rob Kennedy
+2  A: 

The statement DELIMITER configuration is a built-in command only in the mysql client tool. You can't change the delimiter for multi-statements. It's always semicolon.

Also, the MySQL API allows execution of only one statement at a time, by default. The example you're talking about doesn't work unless you explicitly enable multi-statements.

Furthermore, multi-statements isn't the only vector for SQL injection. Even if you could change the statement delimiter, it wouldn't do anything to protect against SQL injection that modifies a single given statement.

UPDATE Accounts SET PASSWORD = '...' WHERE account_id = $id

In this example, if $id has a value of "1234 OR 1=1" then the attacker has changed the password for all accounts, including probably a privileged user. And yet no multi-statements were involved.

You still need to be mindful of security issues when you write code. There's no silver bullet to protect against SQL injection.

Even query parameters aren't a cure-all for SQL injection. Parameters take the place only of values in SQL expressions. There are many common cases where it's still necessary to interpolate application variables into an SQL string. For example, when parameterizing an IN() predicate, or when choosing ORDER BY expressions. Don't listen to people who say prepared queries are 100% proof against security flaws.

Bill Karwin
+1 - Very nice as usual, Bill.
duffymo