我之前和我的一位程序员谈过,他向我展示了他正在考虑的一段代码:
foreach($_REQUEST as $var=>$val) {
$$var = addslashes($val);
}
他希望能够使用$varName
而不必撰写$_REQUEST['varName']
我建议他使用mysql_real_escape_string
代替addSlashes
并且不要将$_REQUEST
变量放到本地堆栈上,因为这会给黑客一个附加向量。对我来说,这似乎与旧的REGISTER_GLOBALS
指令具有相同的问题。
他说没有相同的安全风险,因为这些变量都是在本地堆栈上创建的。所以我不确定,我检查了PHP变量变量页面:http://www.php.net/manual/en/language.variables.variable.php但是没有看到超级全局和安全性,而是警告框。
黑客可以轻松利用该构造吗?
答案 0 :(得分:2)
我多年没有编写php,但是有没有这样做的函数?也许叫extract?
关于在用户输入的数据中使用该功能有一些警告..这些警告也适用于您的代码段。
答案 1 :(得分:2)
这就像回归6年的PHP安全性增强......基本上,register_globals
和magic_quotes
放在一起!这两个在最近的PHP版本中被标记为已弃用,并且将从未来的版本中删除,原因非常充分。
想象一下以下代码:
if ($is_admin) {
do_administrative_task();
}
现在有人发出以下请求:
http://www.example.com/script.php?is_admin=1
就这样,你是管理员!
同样,addslashes()
并没有真正提供任何针对SQL注入攻击的保护,因为它不了解现代字符集。制作一些可以绕过addslashes()
和pwn你的数据库的东西是非常容易的。
答案 2 :(得分:1)
“本地堆栈”与它无关。它仍然允许任何人在代码的某些部分中创建一个新的变量,程序员可能没有这个变量。
如果他真的想要从$_REQUEST
中取出请求参数并将其全部变为变量,那么他应该只传输 代码所在的去寻找而不是更多。
沟渠addslashes()
。这不仅是逃避传入数据的错误位置,也是错误的功能。
答案 3 :(得分:0)
是。如果请求URL包含...&GLOBALS[var]=1
,则它将覆盖相应的全局变量。
他至少应该考虑遵循构造的安全性:
extract($_REQUEST, EXTR_PREFIX_ALL, "var_"); // or EXTR_SKIP
这将为本地化变量提供至少一个前缀并防止覆盖全局变量。为了更好的衡量,还可以使用array_map("addslashes", $_REQUEST)
或更合适的转义函数。但实际上,这只是另一个名字的magic_quotes。 (Offtopic:尝试放开mysql_query并使用PDO和预处理语句,这样更简单,更安全。)
答案 4 :(得分:0)
是的! 作为程序员,这里实际上有三个不同的问题。
$_REQUEST
并不比$_GET
或$_POST
更不安全,因为默认情况下,PHP $_COOKIES
优先于$_GET
和$_POST
。 让我们从顶部开始。
$_POST
和$_GET
并不比$_REQUEST
更安全。从表单收到的所有信息都很脏。期。而不管。如果我可以发送伪造的cookie,我知道如何伪造POST
变量。这个论点没有实际意义。 $var.
创建一个局部变量。此变量的范围仅在函数/方法中。将超全局的内容设置为用户提供的数据的值比在清除函数/方法堆栈时擦除的局部变量更安全吗?我想知道......
function some_function() {
foreach($_POST as $var=>$val) {
$$var = $val;
}
}
现在,如果$_POST
包含名为_POST
的变量,则此代码将设置包含该值的局部变量$_POST
。但是,superglobals会覆盖此,并且对$_POST
的任何引用都将引用超全局,而不是局部变量,因此本地$_POST
是不可接受的。鉴于PHP的这种功能,不使用global关键字通常不可能完全覆盖超全局