perl – 在Solaris 9上睡觉时的SIGALRM

在Solaris 9(Sparc)上的chroot环境中运行Perl时,我遇到了一些奇怪的错误.我们使用的是自定义Perl,但它几乎完全是Perl 5.8.7,而且这个版本已经在包括Solaris 8-10在内的各种平台上运行了多年.

以下代码非常简单:

#!/usr/bin/perl
use strict; 
use warnings;

print "About to sleep(1)\n";
sleep 1;
print "Just woke up!\n";

但是,如果我这样做,“就是醒来!”从不打印 – 相反,程序结束,“闹钟”响应屏幕.只有在睡眠时才会发生这种情况 – 如果我编写的程序执行大量数学操作并需要10秒钟才能运行,那么一切正常.它也只发生在chroot环境中.

我转储了%SIG,其条目为’ALRM => undef’,这是预期的 – 非chrooted环境具有相同的行为.但是,如果我将脚本更改为包括

$SIG{ALRM} = sub {};

……一切正常那么,这笔交易是什么?我没有很多使用Solaris的经验,但必须有一种方法可以使认的信号处理程序正常运行.

解决方法

我尝试的第一件事是在truss下运行你的示例程序:

truss testprogram.pl

这将显示用于实现睡眠的实际系统调用.在我有权访问的Solaris 8系统上,输出的相关部分是:

write(1," A b o u t   t o   s l e"..,18)      = 18
time()                                          = 1247258429
alarm(0)                                        = 0
sigaction(SIgalRM,0xFFBEF6E0,0xFFBEF790)      = 0
sigfillset(0xFF0C28D0)                          = 0
sigprocmask(SIG_BLOCK,0xFFBEF780,0xFFBEF770)  = 0
alarm(1)                                        = 0
    Received signal #14,SIgalRM,in sigsuspend() [caught]
sigsuspend(0xFFBEF760)                          Err#4 EINTR
setcontext(0xFFBEF448)
alarm(0)                                        = 0
sigprocmask(SIG_UNBLOCK,0x00000000) = 0
sigaction(SIgalRM,0x00000000)      = 0
time()                                          = 1247258430
Just woke up!
write(1," J u s t   w o k e   u p"..,14)      = 14

在Solaris 10主机上,它输出

write(1,18)      = 18
time()                                          = 1247258270
nanosleep(0xFFBFF770,0xFFBFF768)               = 0
time()                                          = 1247258271
Just woke up!
write(1,14)      = 14

我想你会得到更接近Solaris 8输出的东西,它可能会出于某种原因显示sigaction()调用失败.

除此之外,我会检查chroot /usr/lib中的共享库实际上是主机和操作系统版本的正确版本. truss输出还将显示perl正在加载哪些共享库.

相关文章

1. 如何去重 #!/usr/bin/perl use strict; my %hash; while(...
最近写了一个perl脚本,实现的功能是将表格中其中两列的数据...
表的数据字典格式如下:如果手动写MySQL建表语句,确认麻烦,...
巡检类工作经常会出具日报,最近在原有日报的基础上又新增了...
在实际生产环境中,常常需要从后台日志中截取报文,报文的形...
最近写的一个perl程序,通过关键词匹配统计其出现的频率,让...