Btw, it's not necessary to check that a call out exists before passing it to remove_call_out. That function actually accepts anything.
/ Martin Stjernholm, Roxen IS
Previous text:
2003-09-20 21:32: Subject: Bilaga (_Process.pmod) till: Re: Contribution
/*
A non blocking Process starter for Pike
19 September 2003 vida@caudium.net David Gourdelier
*/
class create_process { inherit Process.create_process; private function cb; private function timeout_cb;
// start a process. It inherits Process.create_process // command_args and modifiers are the same as in create_process // timeout is the timeout in seconds after which we will kill the process // and call back the timeout_callback function // calllback function is called when process has finished void create(array(string) command_args, void|mapping modifiers) { if(modifiers->read_callback && functionp(modifiers->read_callback)) { int timeout = 15; cb = modifiers->read_callback; if(modifiers->timeout_callback) timeout_cb = modifiers->timeout_callback; ::create(command_args, modifiers); call_out(watcher, 0.1); if(timeout_cb && functionp(timeout_cb)) { if(modifiers->timeout) timeout = modifiers->timeout; call_out(killer, timeout); } } else ::create(command_args, modifiers); }
void destroy() { if(!zero_type(find_call_out(watcher))) remove_call_out(watcher); if(!zero_type(find_call_out(killer))) remove_call_out(killer); }
private void watcher() { // it was another sigchld but not the one from our process if(::status() == 0) { call_out(watcher, 0.1); } else { /* process has finished */ if(!zero_type(find_call_out(killer))) remove_call_out(killer); if(cb) cb(); } }
private void killer() { remove_call_out(watcher); #if constant(kill) ::kill(signum("SIGKILL")); #endif if(timeout_cb) timeout_cb(); } };
/ Brevbäraren