Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/268.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/security/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
PHP-通过引用返回敏感数据以确保安全?_Php_Security_Oop_Reference_Pass By Reference - Fatal编程技术网

PHP-通过引用返回敏感数据以确保安全?

PHP-通过引用返回敏感数据以确保安全?,php,security,oop,reference,pass-by-reference,Php,Security,Oop,Reference,Pass By Reference,也许有点偏执,但我很好奇 假设我正在处理POST的密码。完成后,我想擦拭并移除它。我了解到,在垃圾收集清除$variable之前,PHP可能会或可能不会将$variable=null的值保留在内存中一段时间,因此建议在使用unset($variable)之前,设置$variable=null来清除它,并立即释放内存 现在,我意识到,如果攻击者能够访问服务器的内存,那就太晚了。但是,我想知道PHP是如何处理这个问题的,至少从理论上讲是这样的,如果我没有错的话,在这个问题上稍微加紧一点也不会有什么坏

也许有点偏执,但我很好奇

假设我正在处理POST的密码。完成后,我想擦拭并移除它。我了解到,在垃圾收集清除
$variable
之前,PHP可能会或可能不会将
$variable=null
的值保留在内存中一段时间,因此建议在使用
unset($variable)
之前,设置
$variable=null来清除它,并立即释放内存

现在,我意识到,如果攻击者能够访问服务器的内存,那就太晚了。但是,我想知道PHP是如何处理这个问题的,至少从理论上讲是这样的,如果我没有错的话,在这个问题上稍微加紧一点也不会有什么坏处

我有一个函数,基本上可以做到这一点:

class SomeClass {
    // [...code...]
    public function &example_get_password() {
        $return = $_POST['password']; // or $this->_post['password'], or anything else
        $_POST['password'] = null;
        unset($_POST['password']);
        return $return;
    }
}
这个函数在现实中有点不同,但这就是它的要点(实际上,我从另一个问题中得到了一些非常好的提示)。我想知道的是当我这样做时会发生什么:

$_input = new SomeClass();
$password =& $_input->example_get_password();
//hash password, $hash = hash
$password = null; unset($password);
与所有相同的过程相反,这里发生了什么,但没有引用?我意识到
unset
不会删除引用的变量,但由于它在完成执行的函数的范围内,我希望它在最后一次引用被断开后会自动取消设置,对吗?不管怎样,它已被覆盖为
null


这有什么好处吗?这是一个广泛的问题,但我会尝试一下

PHP为您管理内存,作为一名PHP程序员,您通常不需要担心内存内部的问题,也不应该尝试将内存智能化。对服务器内存的任何不必要的访问都应该被视为PHP本身的一个bug,并在那里修复。您还应该知道,当一个变量被“擦除”时,它的内容仍然可能(部分)存在于内存中;例如,即使指定null,密码字符串也可能可读

垃圾收集

在某些情况下,通过为变量赋值null来确保自己释放内存的建议是正确的。但这纯粹是为了性能,而不是安全性

或者可以吗?

在我看来是可以的。有一类内存bug称为释放bug后使用。顾名思义,问题在于您的程序仍然使用以前释放的内存,攻击者有机会更改内存。在过去的几年里,PHP有很多这样的bug——主要与
非序列化
函数有关。其中一种情况发生在有人在magic
\uuu wakeup
函数中为属性分配了某些内容时。如果你感兴趣的话

与所有相同的过程相反,这里发生了什么,但没有参考?

只要不创建任何循环结构或更改全局变量,就没有区别。例如:

$array = []; $array[] = $array; $array[] = $password;
此处
$password
仅在垃圾收集器运行并收集
$array
时才会被释放

这有什么好处吗?

好奇总是有好处的。但我认为这样一种高级语言对微观管理内存没有什么好处。例外情况一如既往地证明了这一规则


因为我提到了
取消序列化
不要在不受信任的数据上使用它。曾经

简短的回答是否定的。将变量设置为null将告诉PHP立即删除它,但正如您所猜测的,这可能是不够的。有一些工具,比如libnadiumphp(下面讨论),它们试图按照您的建议去做,但简而言之,它们也不起作用

如果您想做一些测试,您可以在进程中向内存写入一些内容,然后在清理完该进程后将其转储(参见下面的文章)。正如他们所说,您需要保护服务器、协议、补丁管理等,这将是最好的方法

非常有趣的文章:

密码提示:

  • “使用旨在散列密码的算法(如bcryt或 argon2(而不是与sha相关的算法或最差的md5)。禁用它们。不要 除非您需要,否则请从数据库加载哈希。不要将其放在 密码内容或长度的限制(但请检查密码是否正确) 强大)。保护自己免受XSS和CRSF攻击,保护您的服务器和 “数据库”

多么美妙的回答,这就是我来这里的原因。非常感谢。如果有任何特别的阅读材料,你可以建议这个主题,请继续。否则我会在一段时间内将此标记为已解决。让我知道,您特别想了解什么。对于PHP的内存管理,我喜欢。最后四篇文章重点介绍了从PHP5到PHP7的一些变化,但它们提供了一个很好的背景知识。对于一个真实的例子,我可以建议。它有点老,但写得很好。那会很好。非常感谢。