lalarm & io:read()?

classic Classic list List threaded Threaded
6 messages Options
Reply | Threaded
Open this post in threaded view
|

lalarm & io:read()?

Petite Abeille
Hello,

Trying to use LHF's lalarm [1] library to simulate a little timer of sort.

All good except when used in conjunction with io:read(), in which case the alarm is not triggered until after the read completes.

Is that how it's meant to be? E.g. read() is blocking everything and hoping for an alert is wishful thinking? Or am I missing something?

Thanks in advance.

[1] http://www.tecgraf.puc-rio.br/~lhf/ftp/lua/#lalarm

P.S.

Perhaps it would be worthwhile to update lalarm to play well with require(), instead of registering its name globally.
Reply | Threaded
Open this post in threaded view
|

Re: lalarm & io:read()?

Alexander Gladysh
On Sun, Mar 25, 2012 at 16:02, Petite Abeille <[hidden email]> wrote:
> Hello,
>
> Trying to use LHF's lalarm [1] library to simulate a little timer of sort.
>
> All good except when used in conjunction with io:read(), in which case the alarm is not triggered until after the read completes.
>
> Is that how it's meant to be? E.g. read() is blocking everything and hoping for an alert is wishful thinking? Or am I missing something?

This is common and painful problem for all code that deals with
signals in Lua. Haven't seen lalarm implementation, but signal handler
usually merely enables the Lua hook to fire on the next instruction
(since you can't do much in a signal handler), the actual signal
handler is run only after execution returns to the Lua VM (which
wouldn't happen until io:read() finishes).

And I can't see anything that could be done with that... :-( (Aside of
throwing out io:read() and using something non-blocking instead. Maybe
lua-ev?)

Alexander.

Reply | Threaded
Open this post in threaded view
|

Re: lalarm & io:read()?

Petite Abeille

On Mar 25, 2012, at 2:10 PM, Alexander Gladysh wrote:

> This is common and painful problem for all code that deals with
> signals in Lua. Haven't seen lalarm implementation, but signal handler
> usually merely enables the Lua hook to fire on the next instruction
> (since you can't do much in a signal handler), the actual signal
> handler is run only after execution returns to the Lua VM (which
> wouldn't happen until io:read() finishes).

Thanks for the feedback.

Just to check, I tried Jesse Luehrs' LuaSignal [1] instead of LHF's lalarm.

There is a  handy alarm_test.lua included which mimics LHF's lalarm behavior.

And… LuaSignal seems to handle io:read() differently, in the sense that it does interrupt read() and keeps going, e.g.:

$ lua alarm_test.lua
hello
in alarm! 17:10:26 0 0%
io.stdin:read nil Interrupted system call 4
in alarm! 17:10:27 1 0%
io.stdin:read nil Interrupted system call 4
...

This looks more like the behavior I had in mind.

[1] https://github.com/doy/luasignal
Reply | Threaded
Open this post in threaded view
|

Re: lalarm & io:read()?

Sam Roberts
In reply to this post by Alexander Gladysh
On Sun, Mar 25, 2012 at 5:10 AM, Alexander Gladysh <[hidden email]> wrote:
> On Sun, Mar 25, 2012 at 16:02, Petite Abeille <[hidden email]> wrote:
> This is common and painful problem for all code that deals with
> signals in Lua. Haven't seen lalarm implementation, but signal handler
> usually merely enables the Lua hook to fire on the next instruction
> (since you can't do much in a signal handler), the actual signal
> handler is run only after execution returns to the Lua VM (which
> wouldn't happen until io:read() finishes).

I don't think that's the problem here. What's probably happening is
the signal handler is being attached with signal(), which is legacy,
and has inconsistent behaviours. I have a very dim memory that lalarm
might be able to call either signal or sigaction, but defaults to
signal(), if so, try it with sigaction().

In particular, whether or not signal restarts system calls depends on
the system. The C handler should be registered with sigaction(), which
would allow RESTART to be set to false. That way, the system call will
return with EINTR, it will then hopefully return to the lua VM, and
the VM will cause the hook to fire.

I see this all the time with our lua code, which is usually blocked on
a socket. Symptom is it takes two Ctrl-C to kill from the command line
(first one fires the C sighandler, which clears the handler but just
restarts the blocking system call so no return to the VM occurs; the
second one happens, and since the handler has been cleared, default
action occurs, which is exit).

Its annoying enough I've thought about writing a small sig module
that's capable of getting lua's sig handler for SIGINT, and resetting
the action so it clears RESTART, but not so annoying I've actually
bothered. Two control-Cs in a row isn't so bad for me.  There are
various lua signal handling modules around, but none allow you to
reset how an existing signal handler is set. I'd want this so I can
change the flags of the standalone lua's C handler.

Anyhow, that's what I think is happening.

Cheers,
Sam

Reply | Threaded
Open this post in threaded view
|

Re: lalarm & io:read()?

Luiz Henrique de Figueiredo
In reply to this post by Alexander Gladysh
> Haven't seen lalarm implementation, but signal handler usually merely
> enables the Lua hook to fire on the next instruction (since you can't
> do much in a signal handler), the actual signal handler is run only
> after execution returns to the Lua VM (which wouldn't happen until
> io:read() finishes).

That's exactly what is happening. If you print something in l_signal in
lalarm.c then you'll see that printed before io:read() finishes.

Reply | Threaded
Open this post in threaded view
|

Re: lalarm & io:read()?

Luiz Henrique de Figueiredo
In reply to this post by Sam Roberts
> I have a very dim memory that lalarm might be able to call either
> signal or sigaction, but defaults to signal(), if so, try it with
> sigaction().

No, it does not support sigaction.

But given the existence of other signal libraries such as Jesse Luehrs'
LuaSignal and Patrick Donnelly's Lua Signal (and probably others),
do I really need to update lalarm?

Of course, I can do it if there is demand.