Timing out arbitrary functions

David Wahler dwahler at gmail.com
Sat Dec 24 18:13:33 CET 2005


Steven D'Aprano wrote:
> I have a problem and I don't know where to start looking for a solution.
>
> I have a class that needs to call an arbitrary function and wait for a
> result. The function, being completely arbitrary and not under my control,
> may be very time consuming and possibly may not even halt. My class needs
> to be able to give up waiting for a result after a specified amount of
> time.
>
> I'm thinking something conceptually like this:
>
> # pseudo-code:
> set time out to 30 seconds
> try:
>     result = somefunction()
> except TimeOut:
>     # 30 second time out happened
>     print "somefunction() timed out without returning"
> else:
>     print "somefunction() returned %s" % result
>
>
> The easy (for some definition of easy) solution would be to code
> somefunction() so that it raised an exception if it hadn't returned a
> result within a certain time. Unfortunately, I can't do rely on that -- I
> only have control over the calling code, not the called somefunction(),
> which may be any arbitrary function.
>
> How do others handle something like this? What should I be looking for?
> I'm after a lightweight solution, if any such thing exists.

For simple cases, I would use signal.alarm() with a SIGALARM handler
that raises a TimeOut exception. However, this is by no means
foolproof; you have to rely on the called function not to mess with
your signal handler. Plus, if your alarm occurs within a try-except
block that catches the TimeOut, it'll still be dropped. And to the best
of my knowledge, you can't otherwise forcibly terminate the execution
of a Python thread or block of code.

If you're going to be running untrusted code, I would use the
subprocess module to invoke a separate Python instance which takes the
code to be executed on stdin, and returns a pickled copy of the return
value on stdout. Then you can start it running, wait 30 seconds, and
then kill it if it hasn't already returned.

-- David




More information about the Python-list mailing list