[erlang-questions] race condition when stopping/starting a gen_server - bug?

Lukas P <>
Wed Nov 16 13:38:54 CET 2011


Hello,

I found that the race condition along with a workaround is described
here: http://stackoverflow.com/questions/6490377/erlang-eunit-and-gen-server-context-cleanup-failed

I am now waiting for the termination of each gen_server, e.g.

stop() ->
    gen_server:call(?SERVER, stop),
    utils:wait_for_exit(?SERVER).

Best regards, Lukas

2011/11/6 Fred Hebert <>
>
> It's hard to help without actually seeing the code (or the test suite), but the problem is not a bug, although it does appear to be a race condition.
>
> As you have found, you need to use gen_server:call/2-3 and make the termination of a gen_server synchronous to be very useful with tests.
> The other things to be careful about after this is to make sure that starting/stopping the server doesn't happen at the same time. If you're using fixtures or just test generating functions, using the '{inorder, TestObjects}' representation can help:
> {inorder, [ListOfTests]}
> or in a fixture:
> some_test_() ->
>    {"test description",
>     {setup,
>      fun setup/0,
>      fun teardown/1,
>      fun(SetupArg) ->
>        {inorder, [
>          ?_assert(...),
>          ...
>        ]}
>      end}}.
>
> The other reason I can imagine is that you're making the mistake of calling your start/stop functions within a test generator (within a ?_Macro(Assertion)): these are actually equivalent to 'fun() -> ?Macro(Assertion) end' and won't be run at declare time, but only later, which can provoke a few errors if you're not careful.
>
> On Thu, Nov 3, 2011 at 6:35 AM, Lukas P <> wrote:
>>
>> Hello,
>> in my eunit tests I am starting/stopping a gen_server.
>> The code used to fail occassionally - gen_server's process name was still registered when gen_server:call(?SERVER, stop) returned and the next gen_server:start_link({local, ?SERVER}...) failed with {error,{already_started,_}}.
>> Adding unregister to gen_server's terminate/2 solved the problem (terminate/2 is called before responding to the stop request), but is there a reason why gen_server does not unregister its name at the right time?
>> Thanks, Lukas
>>
>> _______________________________________________
>> erlang-questions mailing list
>> 
>> http://erlang.org/mailman/listinfo/erlang-questions
>>
>



More information about the erlang-questions mailing list