[erlang-questions] Unidirectional linking?

Mazen Harake <>
Wed May 25 09:28:31 CEST 2011


Perhaps something like this:

process_flag(trap_exit, true),
Parent = self(),
Child = spawn_link(fun() -> Parent ! (catch Op) end),
receive
  {'EXIT', ParentsParent, Reason} ->
    exit(Reason);
  Result ->
    Result
 after N ->
    unlink(Child),
    exit(Child, timeout),
    timeout
end.

if you get an exit signal from the parent's parent you will exit if you are
in the receive clause and you will ignore it (unless it is a kill) if you
are in between the unlink and exit child?

I do however still think that this is very defensive and that the
probability of getting an exit between unlink and exit is very small unless
the timeout in N is exactly the same (very very close to) the timeout that
the parent's parent has for exiting the parent.



On 25 May 2011 08:51, Igor Ribeiro Sucupira <> wrote:

> Supposing someone used the same logic (with timeout/kill) to spawn the
> parent process, the parent could be killed at any moment (but yeah: it
> would be bad luck to have that happening right after it called
> unlink).
>
> Thanks.
> Igor.
>
> On Wed, May 25, 2011 at 3:20 AM, Mazen Harake <>
> wrote:
> > Why would someone "kill the parent"? Do you have processes which are
> > randomly choosing other processes to terminate? ;)
> >
> > If your answer is "No" then I would suggest that you just kill the worker
> > processes that is taking to long, kill it in cold blood, imo.
> >
> > There is no reason to think about too many "if"-scenarios when the
> scenarios
> > are too far fetched. Try the simple version first :)
> >
> > otherwise you can either trap_exits or use monitors instead.
> >
> > /M
> >
> > On 25 May 2011 08:00, Igor Ribeiro Sucupira <> wrote:
> >>
> >> Suppose there is a heavy operation Op that in some cases takes so long
> >> to finish that the caller loses interest in the result and gives up.
> >>
> >> I want to perform that operation in a way that allows me to:
> >> 1) Interrupt its execution if it does not finish in N milliseconds.
> >> 2) Interrupt its execution if the calling process exits (here I'm
> >> already supposing Op has to be run in another Erlang process, due to
> >> goal 1).
> >>
> >> To implement that, it seems unidirectional linking would be needed. Is
> >> there another safe and convenient way to do it?
> >>
> >> The first idea I had was something like this:
> >>
> >> Parent = self(),
> >> Child = spawn_link(fun() -> Parent ! (catch Op) end),
> >> receive Result -> Result
> >> after N -> unlink(Child), exit(Child, timeout), timeout
> >> end.
> >>
> >> But, if Parent is killed by another process right after calling
> >> unlink, Child would be left executing.
> >> Another problem is that I don't want Parent to die if Child exits for
> >> non-timeout reasons (although it seems very unlikely in the code
> >> above, with the catch).
> >>
> >> I was now thinking of substituting unlink(Child) with
> >> process_flag(trap_exit, true) and then kill Child, receive its exit
> >> message, set trap_exit to false again (I'm assuming it was false), and
> >> finally check if there were other exit messages (suiciding if it was
> >> the case).
> >>
> >> But then the code would become too ugly, so I got lazy and decided to
> >> post to this list.  :-)
> >>
> >> What do you think?
> >>
> >> Thanks.
> >> Igor.
> >> _______________________________________________
> >> erlang-questions mailing list
> >> 
> >> http://erlang.org/mailman/listinfo/erlang-questions
> >
> >
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20110525/656475e1/attachment.html>


More information about the erlang-questions mailing list