Jos*_*osh 16 perl redirect stdin stdout stderr
我有一个Perl脚本,它自己分叉和守护.它由cron运行,所以为了不留下僵尸,我关闭了STDIN,STDOUT和STDERR:
open STDIN, '/dev/null' or die "Can't read /dev/null: $!";
open STDOUT, '>>/dev/null' or die "Can't write to /dev/null: $!";
open STDERR, '>>/dev/null' or die "Can't write to /dev/null: $!";
if (!fork()) {
do_some_fork_stuff();
}
Run Code Online (Sandbox Code Playgroud)
我的问题是:我想在此之后恢复至少STDOUT(恢复其他2会很好).但是我需要使用什么魔术符号来重新打开STDOUT,就像STDOUT一样?
我知道如果我是从tty运行的话我可以使用"/ dev/tty"(但我是从cron运行并依赖于其他地方的stdout).我也读过你可以把STDOUT放在一边的技巧open SAVEOUT,">&STDOUT",但只是制作这个副本的行为并没有解决留下僵尸的原始问题.
我正在寻找是否有一些神奇的东西open STDOUT,"|-"(我知道不是这样)以打开它应该打开的方式打开STDOUT.
小智 15
#文件描述符的副本
open(CPERR, ">&STDERR");
Run Code Online (Sandbox Code Playgroud)
#将stderr重定向到警告文件
open(STDERR, ">>xyz.log") || die "Error stderr: $!";
Run Code Online (Sandbox Code Playgroud)
#关闭重定向的文件句柄
close(STDERR) || die "Can't close STDERR: $!";
Run Code Online (Sandbox Code Playgroud)
#recovery stdout和stderr
open(STDERR, ">&CPERR") || die "Can't restore stderr: $!";
Run Code Online (Sandbox Code Playgroud)
#I希望这适合你.
#-Hariprasad AJ
如果它仍然有用,我会想到两件事:
你可以在子进程中关闭STDOUT/STDERR/STDIN(即if(!fork()).这将允许父进程仍然使用它们,因为它们仍然会在那里打开.
我认为您可以使用更简单的关闭(STDOUT)而不是将其打开到/ dev/null.
例如:
if (!fork()) {
close(STDIN) or die "Can't close STDIN: $!\n";
close(STDOUT) or die "Can't close STDOUT: $!\n";
close(STDERR) or die "Can't close STDERR: $!\n";
do_some_fork_stuff();
}
Run Code Online (Sandbox Code Playgroud)