首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >睡在Solaris 9上

睡在Solaris 9上
EN

Stack Overflow用户
提问于 2009-07-06 02:47:26
回答 3查看 1.9K关注 0票数 3

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

以下代码非常简单:

代码语言:javascript
复制
#!/usr/bin/perl
use strict; 
use warnings;

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

不过,如果我这么说的话,“醒来吧!”永远不会被打印-相反,程序结束和“闹钟”被回声到屏幕上。只有在有睡眠的情况下才会发生这种情况--如果我编写了一个计算量很大、运行时间为10秒的程序,那么一切都很好。这种情况也只发生在色度环境中。

我已经转储了%SIG,它的条目为'ALRM => undef',这是预期的-非着色环境具有相同的行为。但是,如果我将脚本更改为包括:

代码语言:javascript
复制
$SIG{ALRM} = sub {};

..。一切都很好。那么,怎么回事?我对Solaris没有太多的经验,但是必须有一种方法来使默认的信号处理程序正常工作。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2009-07-10 20:47:35

我要尝试的第一件事是在桁架下运行您的示例程序:

代码语言:javascript
复制
truss testprogram.pl

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

代码语言:javascript
复制
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, 0xFFBEF780, 0x00000000) = 0
sigaction(SIGALRM, 0xFFBEF6E0, 0x00000000)      = 0
time()                                          = 1247258430
Just woke up!
write(1, " J u s t   w o k e   u p".., 14)      = 14

在Solaris 10主机上,它输出:

代码语言:javascript
复制
write(1, " A b o u t   t o   s l e".., 18)      = 18
time()                                          = 1247258270
nanosleep(0xFFBFF770, 0xFFBFF768)               = 0
time()                                          = 1247258271
Just woke up!
write(1, " J u s t   w o k e   u p".., 14)      = 14

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

除此之外,我还要检查chroot /usr/lib中的共享库实际上是主机和OS版本的正确版本。桁架输出还将显示perl正在加载哪些共享库。

票数 3
EN

Stack Overflow用户

发布于 2009-07-06 04:00:08

我建议简单地将sleep 1调用替换为select(undef, undef, undef, 1),并避免整个问题。

从您给出的症状来看,我敢打赌您的chroot'd perl脚本是根据sleep (POSIX所允许的)实现SIGALRM的,而且出于某种原因,perl没有像它应该的那样捕捉到这个信号,可能是因为它没有预料到该实现。这是您自定义的perl构建吗?这是色度libc中的一种特质吗?chroot下的perl -e "sleep 1"是否也出现了同样的问题?等。等。如果没有环境和像桁架这样的工具,很难说。

同样,整个问题是可以避免的:select不会与SIGALRM混为一谈。

票数 9
EN

Stack Overflow用户

发布于 2009-07-06 12:46:01

您还有Solaris附带的Perl版本吗?如果是的话,那就在上面试试你的代码。如果您没有这个版本,那么我建议下载Perl 5.8.7,编译一个股票版本,然后在上面测试您的脚本。

如果您的脚本在这两个版本中的任何一个上正确运行,那么您就知道这个问题与您的Perl版本的更改有关。如果脚本有相同的错误,那么我建议下载Perl 5.8.9,编译它,然后检查bug是否消失。如果没有,那么恭喜您,您已经在Perl中发现了一个bug。您可能希望运行黑虱来报告它。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1085215

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档