即使使用mysql_real_escape_string(),SQL注入仍然可能发生
尽管普遍认为mysql_real_escape_string()可以防止SQL注入,但在特定情况下,SQL注入仍然可能发生。以下解释了这种攻击是如何发生的:
-
字符集选择:
- 将服务器字符集设置为允许ASCII反斜杠(0x5c)和无效多字节字符的字符集(例如,gbk)。这可以通过SET NAMES语句实现。
-
有效载荷构建:
- 创建一个以0xbf27开头的有效载荷。在指定的字符集(例如,gbk)中,这表示一个无效的多字节字符,它在Latin1中将转换为0x27(撇号)。
-
mysql_real_escape_string()操作:
- mysql_real_escape_string()基于连接的字符集(GBK)操作,而不是客户端假定的字符集(Latin1)。
- 它将有效载荷转义为0x5c27,假设它是一个反斜杠后跟一个撇号。但是,由于客户端仍然认为它使用的是Latin1,所以反斜杠(0x5c)仍然未转义。
-
查询执行:
- 渲染后的查询在转义的内容中包含一个未转义的撇号,从而导致成功的注入攻击。
PDO和MySQLi中的漏洞:
- PDO默认使用模拟预处理语句,容易受到此攻击。
- MySQLi不受影响,因为它使用真正的预处理语句。
缓解措施:
- 使用非易受攻击的字符集进行连接编码(例如,utf8)。
- 使用mysql_set_charset() / PDO DSN字符集参数正确设置连接字符集。
- 禁用PDO中的模拟预处理语句。
通过验证以下条件:
- 使用具有正确字符集管理的现代MySQL版本
- 或使用非易受攻击的字符集
您可以减轻这种潜在的漏洞。
以上是即使使用`mysql_real_escape_string()`即使SQL注入仍然会发生?的详细内容。更多信息请关注PHP中文网其他相关文章!