caml-list - the Caml user's mailing list
 help / color / mirror / Atom feed
From: Till Varoquaux <till@pps.jussieu.fr>
To: yoann padioleau <pad.aryx@gmail.com>
Cc: caml-list@inria.fr
Subject: Re: [Caml-list] threads, signals, and timeout
Date: Mon, 26 Oct 2009 14:36:10 -0400	[thread overview]
Message-ID: <9d3ec8300910261136w3cee8329od4b0a02365cde8db@mail.gmail.com> (raw)
In-Reply-To: <c55bbbbc0910261108l5e59836j1508d69c664bdf8f@mail.gmail.com>

You'd have the same problem in any other programming language; this is
due to the underlying POSIX model.
The POSIX standard mentions that alarms are global to the process [1].

" There were two possible choices for alarm generation in
multi-threaded applications: generation for the calling thread or
generation for the process. The first option would not have been
particularly useful since the alarm state is maintained on a
per-process basis and the alarm that is established by the last
invocation of alarm() is the only one that would be active."

As a general matter mixing signals and threads is a thorny issue under
unix; you should avoid doing so unless you have a good grasp of what
is going to happen. Having a global timer thread that kills timed-out
threads would be possible but seems very painful. If you give us more
information on what you are trying to achieve (eg your computations
threads are crunshing numbers in a tight loop or you are performing io
etc...) we might be able to guide you. Here is a quick run down of my
flawed and partial understand of the world:

For heavy computations threads will not help you. I am sure you are
aware of this but there never is more than one ocaml thread running at
the same time. If you can fork and collect the resulting data through
pipes or shared memory you should be able to get a noticeable
performance boost. There have been countless posts on the subject; I
am too lazy to google them up.

I/O is a very different beast and you are probably better of with an
asynchronous framework. Luckily for you Ocaml has a pretty good one
already available [2]

Till

[1]: http://www.opengroup.org/onlinepubs/000095399/functions/alarm.html
[2]: http://ocsigen.org/lwt/
On Mon, Oct 26, 2009 at 2:08 PM, yoann padioleau <pad.aryx@gmail.com> wrote:
> Hi,
>
> I would like to create different threads where each thread do some
> computation and are subject to different
> timeout. Without threads I usually use Unix.alarm with a SIGALARM
> handler that just raise a Timeout exception
> and everything works fine, but when I try to do something similar with
> threads it does not work
> because apparently the Unix.alarm done in one thread override the
> Unix.alarm done in another
> thread. I had a look at thread.mli but was not able to find anything
> related to timeout.
> Is there a way to have multiple timeout and multiple threads at the same time ?
>
> Here is a program that unforunately get the first timeout, but not the second :(
>
>
> (*
> ocamlc -g -thread unix.cma threads.cma signals_and_threads.ml
> *)
>
> exception Timeout
>
> let mytid () =
>  let t = Thread.self () in
>  let i = Thread.id t in
>  i
>
> let set_timeout () =
>
>  Sys.set_signal Sys.sigalrm
>    (Sys.Signal_handle (fun _ ->
>      prerr_endline "Time is up!";
>      print_string (Printf.sprintf "id: %d\n" (mytid()));
>      raise Timeout
>    ));
>
>  ignore(Unix.alarm 1);
>  ()
>
>
> let main =
>  let t1 =
>    Thread.create (fun () ->
>      set_timeout ();
>      print_string (Printf.sprintf "t1 id: %d\n" (mytid()));
>
>      let xs = [1;2;3] in
>      while(true) do
>        let _ = List.map (fun x -> x + 1) xs in
>        ()
>      done;
>      ()
>    ) ()
>  in
>
>  let t2 =
>    Thread.create (fun () ->
>      set_timeout ();
>      print_string (Printf.sprintf "t2 id: %d\n" (mytid()));
>
>      let xs = [1;2;3] in
>      while(true) do
>        let _ = List.map (fun x -> x + 1) xs in
>        ()
>      done;
>      ()
>    ) ()
>  in
>  Thread.join t1;
>  Thread.join t2;
>  ()
>
> ------------------
>
>
>
>
> Here is the output
> Time is up!
> t2 id: 2
> t1 id: 1
> id: 1
> Thread 1 killed on uncaught exception Signals_and_threads.Timeout
> .... <the program loops, meaning the second thread never received its timeout
>
> _______________________________________________
> Caml-list mailing list. Subscription management:
> http://yquem.inria.fr/cgi-bin/mailman/listinfo/caml-list
> Archives: http://caml.inria.fr
> Beginner's list: http://groups.yahoo.com/group/ocaml_beginners
> Bug reports: http://caml.inria.fr/bin/caml-bugs
>


  reply	other threads:[~2009-10-26 18:36 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2009-10-26 18:08 yoann padioleau
2009-10-26 18:36 ` Till Varoquaux [this message]
2009-10-26 19:06   ` [Caml-list] " yoann padioleau
2009-10-26 22:14     ` Gerd Stolpmann
2009-10-27 10:01     ` Gabriel Kerneis
2009-10-26 23:13 ` Philippe Wang

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=9d3ec8300910261136w3cee8329od4b0a02365cde8db@mail.gmail.com \
    --to=till@pps.jussieu.fr \
    --cc=caml-list@inria.fr \
    --cc=pad.aryx@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).