mysql_real_escape_string 的缺点? [英] Shortcomings of mysql_real_escape_string?

查看:26
本文介绍了mysql_real_escape_string 的缺点?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在这里看到一些人说使用 mysql_real_escape_string 连接查询不会保护您(完全)免受 SQL 注入攻击.

I have seen a few people on here state that concatenating queries using mysql_real_escape_string will not protect you (entirely) from SQL injection attacks.

但是,我还没有看到一个输入示例来说明mysql_real_escape_string 无法保护您免受攻击.大多数示例忘记了 mysql_query 仅限于一个查询,并且错误地使用了 mysql_real_escape_string.

However, I am yet to see an example of input that illustrates an attack that mysql_real_escape_string would not protect you from. The majority of examples forget that mysql_query is limited to one query and use mysql_real_escape_string incorrectly.

我能想到的唯一例子如下:

The only example I can think of is the following:

mysql_query('DELETE FROM users WHERE user_id = '.mysql_real_escape_string($input));

这不会保护您免受以下输入的影响:

This would not protect you from the following input:

5 OR 1=1

我认为这是对 mysql_real_escape_string 的错误使用而不是缺点,它是为字符串而不是数字值设计的.您应该转换为数字类型,或者如果您要在清理时将输入视为字符串,您应该在查询中执行相同的操作并用引号将其括起来.

I would see this as incorrect usage of mysql_real_escape_string rather than a shortcoming, it is designed for strings not numeric values. You should either cast to a numeric type or if you are going to treat the input as a string when sanitising you should do the same in your query and wrap quotation marks around it.

谁能提供一个输入示例,该示例可以绕过 mysql_real_escape_string 而不依赖于对数值的错误处理或忘记 mysql_query 只能执行一个查询?

Can anyone provide an example of input that can get around mysql_real_escape_string that does not rely on incorrect handling of numeric values or forget that mysql_query can only execute one query?

我对 mysql_real_escape_string 的局限性很感兴趣,并没有将其与替代方案进行比较,我意识到新项目有更好的选择,对此我没有异议.

I am interested in the limitations of mysql_real_escape_string and not comparing it to alternatives, I realise there are better options for new projects and am not disputing that.

推荐答案

mysql_real_escape_string 或 mysql_ 扩展的主要缺点是它比其他的更难正确应用,更多现代 API,尤其是准备好的语句.mysql_real_escape_string 应该仅用于一种情况:转义用作 SQL 语句中引号之间的值的文本内容.例如:

The main shortcoming of mysql_real_escape_string, or of the mysql_ extension in general, is that it is harder to apply correctly than other, more modern APIs, especially prepared statements. mysql_real_escape_string is supposed to be used in exactly one case: escaping text content that is used as a value in an SQL statement between quotes. E.g.:

$value = mysql_real_escape_string($value, $link);
$sql = "... `foo` = '$value' ...";
                     ^^^^^^

mysql_real_escape_string 确保上述上下文中的 $value 不会混淆 SQL 语法.它不像您在这里想的那样工作:

mysql_real_escape_string makes sure that the $value in the above context does not mess up the SQL syntax. It does not work as you may think here:

$sql = "... `foo` = $value ...";

或在这里:

$sql = "... `$value` ...";

或在这里:

$sql = mysql_real_escape_string("... `foo` = '$value' ...");

如果应用于 SQL 语句中引用字符串以外的任何上下文中使用的值,则它被误用并且可能会或可能不会弄乱结果语法和/或允许某人提交可能启用 SQL 注入攻击的值.mysql_real_escape_string 的用例非常狭窄,但很少被正确理解.

If applied to values which are used in any context other than a quoted string in an SQL statement, it is misapplied and may or may not mess up the resulting syntax and/or allow somebody to submit values which may enable SQL injection attacks. The use case of mysql_real_escape_string is very narrow, but is seldom correctly understood.

另一种使用mysql_real_escape_string让自己陷入困境的方法是使用错误的方法设置数据库连接编码.你应该这样做:

Another way to get yourself into hot water using mysql_real_escape_string is when you set the database connection encoding using the wrong method. You should do this:

mysql_set_charset('utf8', $link);

也可以这样做:

mysql_query("SET NAMES 'utf8'", $link);

问题是后者绕过了 mysql_ API,它仍然认为您正在使用 latin1(或其他东西)与数据库对话.现在使用 mysql_real_escape_string 时,它会假设错误的字符编码和转义字符串,与数据库稍后解释它们的方式不同.通过运行 SET NAMES 查询,您在 mysql_ 客户端 API 如何处理字符串和数据库如何解释这些字符串之间产生了裂痕.这可用于某些多字节字符串情况下的注入攻击.

The problem is that the latter bypasses the mysql_ API, which still thinks you're talking to the database using latin1 (or something else). When using mysql_real_escape_string now, it will assume the wrong character encoding and escape strings differently than the database will interpret them later. By running the SET NAMES query, you have created a rift between how the mysql_ client API is treating strings and how the database will interpret these strings. This can be used for injection attacks in certain multibyte string situations.

mysql_real_escape_string 中没有基本的注入漏洞,我知道如果应用正确. 不过,主要问题是它非常容易应用它错误地打开了漏洞.

There are no fundamental injection vulnerabilities in mysql_real_escape_string that I am aware of if it is applied correctly. Again though, the main problem is that it is terrifyingly easy to apply it incorrectly, which opens up vulnerabilities.

这篇关于mysql_real_escape_string 的缺点?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆