develooper Front page | perl.dbi.users | Postings from September 2002

Re: Interesting DBI/alarm()/Solaris problem? !?

Thread Previous | Thread Next
From:
Tim Bunce
Date:
September 10, 2002 02:28
Subject:
Re: Interesting DBI/alarm()/Solaris problem? !?
Message ID:
20020910102800.D2793@dansat.data-plan.com
CC'd to perl5-porters since the delayed signal handling part almost
certainly relates to the new "safe signals" in recent perl versions.
They may be able to suggest something.

Tim.

On Thu, Aug 29, 2002 at 02:22:53PM -0600, Tkil wrote:
> 
> >>>>> "Joe" == Joe Slagel <slagel@geospiza.com> writes:
> 
> Joe> We're seeing some very odd behavior with using alarm() around the
> Joe> DBI->connect() call only on Solaris platforms. It appears that
> Joe> even though we clear the alarm after a successful connection, for
> Joe> some reason the alarm signal is still getting sent and we receive
> Joe> a very nice "Alarm Clock" message.  The following script
> Joe> demostrates the problem (on Solaris), but works fine on Linux.
> Joe> Anyone have any guesses why this may be?
> 
> >>>>> "David" == "David M. Lloyd" <dmlloyd@tds.net> writes:
> 
> David> This is a Perl bug on Solaris.  Doing an alarm(0) doesn't
> David> really clear the alarm.
> 
> >>>>> "Tim" == "Tim Bunce" <Tim.Bunce@pobox.com> writes:
> 
> Tim> Can you point me to a url for more information on the bug?
> 
> I've been following this thread through the archives, and I found
> another report which was very helpful:
> 
>    http://groups.google.com/groups?selm=93he36%24egc%241%40nnrp1.deja.com
> 
> Adam points out that, after DBD::Oracle is loaded, perl's alarm() gets
> turned into a call to lwp_alarm, instead of basic alarm().  The fix
> for this is to manually load DBD::Oracle before trying to do anything
> with perl's alarm(), and that does indeed make all the system calls
> lwp_alarm().
> 
> Sadly, I'm still having issues.  Now, instead of getting a rogue
> "Alarm Clock" message, it looks like the alarm is ignored until a read
> completes, then the message is passed on.  Using this script:
> 
> perl -MDBI -we \
>   '$dbh = DBI->connect("dbi:Oracle:db", "user", "pass", {});
>   alarm 1;
>   @info = $dbh->selectrow_array("SELECT COUNT(*) FROM big_table")
>     or warn $dbh->errstr();
>   print join("|", @info), "\n";
>   $dbh->disconnect();'
> 
> This works correctly.  After one second, it prints "Alarm Clock" then
> exits.
> 
> If I install a SIGALRM handler like:
> 
>   $SIG{ALRM} = sub { die "foo!\n" };
> 
> Then it still takes a long time (executing the whole query to
> completion), and I get that message at the end of the run.
> Interestingly enough, if I interrupt it with SIGINT (after the alarm
> has fired), I still see the "foo!" message.
> 
> Looking at the truss output (with "-f -l", so the first column is
> pid/lwp_id), I see this:
> 
>    13013/1: lwp_alarm(1)                                    = 0
> 
> Ok, set the alarm...
> 
>    13013/1: write(5, "\0 v\0\006\0\0\0\0\011 k".., 118)     = 118
>    13013/1: read(5, "\0 s\0\006\0\0\0\0\01019".., 2064)     = 115
>    13013/1: write(5, "\0 n\0\006\0\0\0\0\003 ^".., 110)     = 110
> 
> Send the query, read something, send again, and start reading the
> query result:
> 
>    13013/1:     Received signal #14, SIGALRM, in read() [caught]
>    13013/1: read(5, 0x082981DE, 2064)                       Err#4 EINTR
> 
> Which gets interrupted by the SIGALRM
> 
>    13013/1: sigprocmask(SIG_SETMASK, 0xDF35A8F4, 0x00000000) = 0
>    13013/1: sigprocmask(SIG_SETMASK, 0xDF365E98, 0x00000000) = 0
>    13013/1: setcontext(0x080450B4)
>    13013/1: read(5, 0x082981DE, 2064)       (sleeping...)
> 
> But do some magic, and then resume the read!
> 
>    13013/2: signotifywait()                 (sleeping...)
>    13013/3: lwp_sema_wait(0xDEF06E3C)       (sleeping...)
>    13013/4: lwp_cond_wait(0xDF360E6C, 0xDF360E7C, 0xDF35A66C) (sleeping...)
>    13013/5: door_return(0x00000000, 0, 0x00000000, 0) (sleeping...)
>    13013/6: lwp_cond_wait(0xDF360E6C, 0xDF360E7C, 0xDF35A66C) (sleeping...)
>    13013/1: read(5, "\09C\0\006\0\0\0\0\01019".., 2064)     = 156
> 
> Read actual result here
> 
>    13013/1: brk(0x082AEAF0)                                 = 0
>    13013/1: brk(0x082B4AF0)                                 = 0
>    13013/1: getcontext(0x08046B04)
>    13013/1: setcontext(0x080467E4)
>    13013/1: write(2, " f o o !   a t   - e   l".., 19)      = 19
> 
> But there's an error pending, so print that ...
> 
> Anyway.  Anyone have ideas?
> 
> Thanks,
> t.

Thread Previous | Thread Next


nntp.perl.org: Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at ask@perl.org | Group listing | About