- A+
所属分类:Seay信息安全博客
显示不全请点击全屏阅读
首先查看以下代码
$pdo->query(‘SET NAMES GBK’);
$var = chr(0xbf) . chr(0x27) . ” OR 1=1 /*”;
$query = “SELECT * FROM test WHERE name = ? LIMIT 1”;
$stmt = $pdo->prepare($query);
$stmt->execute(array($var));
1.设置字符集
SET names x等同于以下内容:
SET character_set_client = x
SET character_set_results = x
SET character_set_connection = x
2.设置payload www.2cto.com
3.深入分析
mysql的prepare其实是本地PHP客户端模拟的,并没有根据你mysql的设置做字符集的调整。应该交与mysql server端做prepare,同时得调用mysql_set_character_set去操作,server才会按照字符集去做转义。
php本地模拟的prepare底层就是mysql_real_escape_string,所以必须得用mysql_set_character_set去设置mysql->charset,否则就存在字符集问题。
也就是说在php本地调用pdo prepare中的mysql_real_escape_string来操作query,使用的是本地单字节字符集,即编码为\xbf\x5c\x27,并带入到mysql中查询,由于使用set names设置了连接字符集,mysql使用内部操作字符集gbk来进行操作,即执行
“SELECT * FROM test WHERE name = ‘xxx’ or 1=1 /* LIMIT 1”;从而注入成功
解决方案:使用mysql_set_character_set函数来设置字符集。
作者:maoniu
Tags:
如果您喜欢我的博客,欢迎点击图片定订阅到邮箱 也可以点击链接【订阅到鲜果】
如果我的想法或工具帮助到了你,也可微信扫下方二维码打赏本人一杯咖啡