2017-11-03 18:57
采纳率: 100%
浏览 179

PHP exec(),shell_exec(),system(),passthru()在Windows 7 / IIS上不起作用

我在我的开发环境中使用了Windows 7 x64 Enterprise、IIS和PHP 5.6.32。我的应用程序的网站有以下设置:

  • 匿名认证:禁用
  • Windows身份验证:已启用(协商,协商:Kerboeros,NTLM)
  • 应用程序池:域帐户。
  • 除了默认的PHP扩展名之外,我还有在Windows身份验证模式下使用的Microsoft的PHP SQL Server驱动程序(3.2版).

我的生产服务器与Server 2008 R2上运行的安装程序相同。

我需要使用 exec(), shell_exec()等。 执行一个可执行文件(pdftk,如果它是重要的)。然而,当我使用这些函数时,我总是得出 "Unable to fork XXX"在PHP错误日志中。我试着运行 whoami, ping xxx, 以及其他具有相同结果的简单命令。 典型的shell函数均无法正常工作-它们始终会出现相同的错误。 我检查了我的php.ini 文件 并验证这些功能没有被禁用。

但是,在生产环境中,我没有发现这个问题,也不知道为什么会出现这种情况。 它似乎只影响我的开发环境。 在研究期间,我确实偶然发现了这个问题(http://tech.trailmax.info/2012/12/php-warning-shell_exec-unable-to-execute-on-iis-7/),由于某种原因, 解决了我的问题; 但是,它完全破坏了我的SQL Server Windows身份验证(我所需要的)。 我也禁用了我的防病毒软件,希望这不是罪魁祸首。 在进行更多故障排除时,我确实发现了proc_open() 起作用。我们使用Prince来生成pdf,我注意到它是运行的,而我的exec()却没有。 当我查看Prince类时,我发现它正在使用proc_open() 这就解释了为什么它似乎是有效的。

有人知道为什么吗?exec() 并且相关功能似乎在我的生产环境中而不在我的开发环境中正常工作? 为何可以工作,但其他Shell函数却不能工作? 谢谢! proc_open()

  • 点赞
  • 写回答
  • 关注问题
  • 收藏
  • 邀请回答

2条回答 默认 最新

  • dqo58772
    dqo58772 2018-05-01 01:01

    I wanted to post an update to this since I figured out the issue. The answer can be found here in the very last post by 1heer2351 at zonnet dot nl1:

    Located the problem and have been able to fix it.

    I am using a special user for my Application Pool (say AppPoolUser), so PHP runs as this user. The new exec function uses CreateProcessAsUser() with impersonation. This means that the AppPoolUser must have the right to change the process level token.

    You can assign this right to the user in the "Local Security Settings" -> User Rights Assignment.

    I have granted my AppPoolUser the "Replace a process level token" setting -> fork error has gone.

    Thought this might be useful information, so access is required to cmd.exe but in addition the "Replace a process level token" setting.

    This is exactly what I did. I had created a new App Pool User using my domain account. By default, the Replace a process level token setting includes DefaultAppPool. Since I created a new App Pool User, it was not included in this policy setting. Adding the App Pool User I created resolved my issue.

    点赞 评论
  • douxuanwei1980
    douxuanwei1980 2018-04-27 16:14

    Check the permissions on file 'C:\WINDOWS\system32\cmd.exe'. You need read/execute permission on this file.

    I would recommend using the sysinternals Process Monitor 'procmon.exe' to confirm the user that is trying to run 'cmd.exe'. Filter on 'Process Name' is 'php-cgi.exe' and 'Path' ends with 'cmd.exe'. Look at the event properties for the task with the access denied error, and it will show you the 'Impersonating' user name. This is usually the 'Internet Guest Account', often 'NT AUTHORITY\IUSR'.

    点赞 评论