On Windows, signals are emulated. alarm($timeout) sets up a timer that must be polled.
That's not a very good description of what actually happens.
On Windows, alarm is simulated using the SetTimer() system API, which send a message to the process' message queue when the time expires.
From perl5.18/Win32.c:
And that message is received when the run loop checks the message queue:
And, at least since the advent of SAFE_SIGNALS in 5.8.1, *nix perls, also only process signals, between opcodes, by "polling" (from the run loop) to see if any have been received during the last opcode. Ie. in exactly the same way as Windows perls do.
The reason your rather over-elaborate demo "works" on *nix and not under windows, is because under *nix, signals are also delivered (by the OS) to child processes, whereas they are obviously not on Windows. Thus, the locker child process also receives the alrm signal which interrupts the 10 second sleep, thus the lock it holds gets removed, and the main() process can therefore acquire its lock before the alarm is triggered.
This is clearly shown by the output you posted:
>perl lockdemo.pl locker: flock LOCK_EX locker: locked locker: sleep 10 main: alarm 5 main: flock LOCK_EX ### The lock is acquired +here main: timeout at lockdemo.pl line 30. ### before the timeout oc +curs. main: 5 seconds have passed locker: flock LOCK_UN locker: unlocked
Perl's "Safe Signals" (unless disabled) are also implemented on *nix perls, and are only acted upon between opcodes, just as they are on Windows perls. Your demo is deceptive (I'm not suggesting deliberately so), because the alarm is not interrupting the flock opcode in the main() process, but the sleep in the child process. The lock is only acquired early in the main process because the child process relinquished its lock early.
That doesn't happen in the Windows example, because the OS doesn't do signals, thus doesn't deliver the signal to the child process.
I agree that the emulated signals on Windows are less complete than the real ones on *nix; but then the reason Perl has "Safe signals" in the first place is because the entire concept of using asynchronous interrupts as a flow-control mechanism is terminally brain-dead.
In reply to Re^4: Strawberry Perl and alarm() on Windows
by BrowserUk
in thread Strawberry Perl and alarm() on Windows
by bloonix
| For: | Use: | ||
| & | & | ||
| < | < | ||
| > | > | ||
| [ | [ | ||
| ] | ] |