【问题标题】:system() always returns non-zero when called as CGIsystem() 在作为 CGI 调用时总是返回非零值
【发布时间】:2012-06-20 13:08:19
【问题描述】:

当从 cgi 调用 system() 时,它总是返回 -1(表示错误)。 errno 设置为 10,ECHILD。

test.cgi 包含:

cout << "/bin/true " << system("/bin/true") << endl;
cout << "/bin/false " << system("/bin/false") << endl;
cout << "/bin/touch /tmp/foo" << system("/bin/touch /tmp/foo") << endl;

从命令行调用,因为 ./test.cgi 返回:

/bin/true 0
/bin/false 256
/bin/touch /tmp/foo 0

但将其作为来自网络浏览器的链接调用会返回(在预期的格式错误的标头错误消息之后):

/bin/true -1
/bin/false -1
/bin/touch /tmp/foo -1

我已验证命令在两种情况下都执行(文件 /tmp/foo 已创建),但通过 httpd(mongoose、ARM9、Linux)调用它们会返回 -1。

任何提示,如何解决?

【问题讨论】:

  • C 中没有 cout &lt;&lt; whatever
  • @eckes:好的,关键字已相应调整。我怀疑编译器的选择:gcc 或 g++ 在这里有问题,但无论如何......
  • 猜是权限问题:运行web服务器的用户是否有权限执行/bin/true/bin/false
  • /bin/sh/bin/true 是否存在于 Web 服务器的命名空间中?如果是chrooted,也许不是。您是如何“验证命令已执行”的?
  • @Rob:确实如此。我正在启动一个不同的命令,它以相同的方式发出小扬声器的哔哔声,我可以听到它哔哔声。 (当从 httpd 调用时,它返回相同的 -1 而不是实际的返回码。)

标签: c++ linux shell cgi system


【解决方案1】:

您的system 调用因ECHILD 错误而失败。当wait 正在等待但没有待处理的孩子时会发生这种情况。造成这种情况的一个可能原因是您的代码(或您调用的某些代码)已将SIGCHLD 的信号处理程序设置为SIG_IGN。要对此进行测试,您可以将SIGCHLD 信号处理程序设置为SIG_DFL,以便在调用system 之前将其恢复为默认信号处理程序。

我不想走得太远,所以检查一下上面的测试是否有效。如果是这样,如果您的程序是单线程的,您可以考虑使用测试作为修复,并且您将信号处理程序恢复到它在system 完成后设置的值。但是,实际的解决方法是找出信号处理程序的设置位置和原因,然后判断您要对此做什么。

【讨论】:

  • 是的,它有效!开头的signal(SIGCHLD,SIG_DFL); 会导致返回正确的结果。现在我只希望谁/在哪里/为什么/什么来破坏处理程序......
猜你喜欢
  • 2018-04-08
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多