[erlang-questions] Programming question
Samuel Rivas
samuelrivas@REDACTED
Fri Jan 26 09:01:22 CET 2007
Ulf Wiger (TN/EAB) wrote:
> I agree that gen_server shouldn't touch the EXIT
> messages. While changing this might cause some
> consternation among a few users with legacy code,
> I believe the current behaviour violates the
> principle of least astonishment and, as you've
> described, can lead to highly unexpected timing bugs.
>
> gen:call() doesn't enable exit trapping under any
> circumstances (nor does it link to the server),
> so if the process is trapping exits, and is linked
> to the server, it is certainly because someone else
> made it so. It is then reasonable to expect that
> some other code expects an EXIT message to arrive.
There is another issue with the catch sentence in the block that
handles call requests in gen_server.erl:
call(Name, Request) ->
case catch gen:call(Name, '$gen_call', Request) of
{ok,Res} ->
Res;
{'EXIT',Reason} ->
exit({Reason, {?MODULE, call, [Name, Request]}})
end.
call(Name, Request, Timeout) ->
case catch gen:call(Name, '$gen_call', Request, Timeout) of
{ok,Res} ->
Res;
{'EXIT',Reason} ->
exit({Reason, {?MODULE, call, [Name, Request, Timeout]}})
end.
That does not do well with the behaviour that a try-catch user
expects. An uncatched signal becomes a return term. So a gen_server with
the next code:
handle_call(trhow_it, _From, State) ->
throw(ouch),
{reply, ok, State};
handle_call(weird, _From, State) ->
throw({reply, ok, State}),
{stop, ok, State};
handle_call(expected, _From, State) ->
erlang:error({nocatch, ouch}),
{reply, ok, State}.
Behaves as funny as:
16> gen_server_throw:start_link().
{ok,<0.78.0>}
17> gen_server:call(test, weird).
ok
18> gen_server:call(test, trhow_it).
=ERROR REPORT==== 26-Jan-2007::08:47:46 ===
** Generic server test terminating
** Last message in was trhow_it
** When Server state == {}
** Reason for termination ==
** {bad_return_value,ouch}
** exited: {bad_return_value,ouch} **
19> gen_server_throw:start_link().
ok,<0.83.0>}
20> gen_server:call(test, expected).
=ERROR REPORT==== 26-Jan-2007::08:48:07 ===
** Generic server test terminating
** Last message in was expected
** When Server state == {}
** Reason for termination ==
** {{nocatch,ouch},
[{gen_server_throw,handle_call,3},
{gen_server,handle_msg,6},
{proc_lib,init_p,5}]}
** exited: {{nocatch,ouch},
[{gen_server_throw,handle_call,3},
{gen_server,handle_msg,6},
{proc_lib,init_p,5}]} **
- I would expect that 'throw_it' caused an exception similar
to 'expected' (with the right stack trace)
- I would expect that 'weird' caused a similar exception too, but it
does not even crash the server.
I did not find any mention about throw issues in the manual either.
Regards
--
Samuel
More information about the erlang-questions
mailing list