【发布时间】:2016-08-12 01:51:47
【问题描述】:
我继承了自己编写的 CGI 应用程序的维护,但没有 文档,从未见过原作者。应用程序 在 Debian 8 中停止工作,但在 Debian 7 和 CentOS 5 中工作。 主要变化是从 Apache 2.2 升级(由 Debian 7 和 CentOS 5) 到 Apache 2.4(由 Debian 8 使用)以及从 perl 升级 5.8(在 CentOS 5 中)分别从 perl 5.14(在 Debian 7 中)到 perl 5.20。 有问题的部分归结为以下脚本(a 302-重定向):
#!/usr/bin/perl
$|=1; # activate auto-flushing of stdout
use strict;
use warnings;
my $CRLF = "\015\012";
print STDOUT "Status: 302 Moved Temporarily$CRLF" .
"Location: /does_not_matter$CRLF" .
"URI: /does_not_matter$CRLF" .
"Connection: close$CRLF" .
"Content-type: text/html; charset=UTF-8$CRLF$CRLF";
close STDOUT;
while(1) {
sleep 1;
}
观察到的行为是 重定向永远不会到达客户端
只要脚本在与 Apache 2.4 一起使用时仍在运行,但
Apache 的 error.log 中没有错误消息。我换了客户端
(Firefox, Chromium, wget), Apache 模块 (mod_cgid & mod_cgi),
发送了额外的标题,删除了close STDOUT,删除了
$|=1,将$CRLF 替换为\n 并制作了脚本
fork 并退出父进程(这样 Apache 就不再是
父进程),一切都无济于事。唯一有效的方法:使用
Apache 2.2,将脚本转换为 NPH-CGI 脚本(必须发送
Apache 不会以任何方式修改的完整 HTTP 标头,即使
它们包含错误),使脚本退出而不是输入
无限循环。我通过 tcpdump 确认了带有
在脚本被杀死之前,重定向确实永远不会离开服务器。
并从响应中的日期线和最终的时间
到达我收集到 Apache 立即收到我的输出(&
立即将日期行添加到标题中),但不发送
回复客户。
不用回答了,我自己已经想好了解决办法 并将写一个答案。我只是想让解决方案可用 给其他可能遇到同样问题的人。
【问题讨论】:
标签: cgi http-redirect apache2.4