PHP - realpath不工作;文件肯定存在

时间:2016-01-11 21:20:44

标签: php

我正在尝试使用realpath()来避免目录遍历攻击,而我无法弄清楚为什么它会在肯定存在的文件上返回false。

这些文件托管在Apache用户可以访问的NFS共享上。整个层次结构是755,除了文件本身是777。

以下是代码段:

$path = "/mnt/share/path/to/20160111-133552-msg0000.wav";
$path = realpath($path);
var_dump($path);

结果是:

bool(false)

文件绝对存在。我进入Apache用户并运行:

bash-4.2$ ls -lah /mnt/share/path/to/20160111-133552-msg0000.wav
-rwxrwxrwx. 1 1001 1001 77K Jan 11 13:35 /mnt/share/path/to/3000-20160111-133552-msg0000.wav

另一个观察结果:当我从$ path变量中删除文件名时:

$path = "/mnt/share/path/to/

它运作得很好:

string(39) "/mnt/share/path/to"

之前有人遇到过这种行为吗?

2 个答案:

答案 0 :(得分:1)

我想我自己想出了这个!好的'selinux阻止了httpd访问该文件:

type=AVC msg=audit(1452550767.071:18495): avc:  denied  { read } for  pid=10397 comm="httpd" name="3000-20160111-133552-msg0000.wav" dev="0:41" ino=12483 scontext=system_u:system_r:httpd_t:s0 tcontext=system_u:object_r:nfs_t:s0 tclass=file
    Was caused by:
    One of the following booleans was set incorrectly.
    Description:
    Allow httpd to use nfs

    Allow access by executing:
    # setsebool -P httpd_use_nfs 1

当我尝试在有问题的.wav文件上执行readfile()并获得权限被拒绝错误时,我才发现这一点,这在777文件中没有意义。检查了/var/log/audit/audit.log,这很明显。

正在运行setsebool -P httpd_use_nfs 1为我修好了。

答案 1 :(得分:0)

不要采取以下措施:这个答案是根据访问权限的详细组合的错误记录编写的:755已经允许所有人执行!

你说:

  

整个层次结构是755,除了文件本身是777。

虽然PHP manual page说:

  

正在运行的脚本必须对层次结构中所有目录具有可执行权限,否则realpath()将返回FALSE。

因此,您要将整个层次结构设置为777到此realpath()才能生效。