@@ -242,8 +242,10 @@ start_link({global, _SupName}, _Group, _Mod, _Args) ->
242242start_link0 (Prefix , Group , Init ) ->
243243 case apply (? SUPERVISOR , start_link ,
244244 Prefix ++ [? MODULE , {overall , Group , Init }]) of
245- {ok , Pid } -> call (Pid , {init , Pid }),
246- {ok , Pid };
245+ {ok , Pid } -> case catch call (Pid , {init , Pid }) of
246+ ok -> {ok , Pid };
247+ E -> E
248+ end ;
247249 Other -> Other
248250 end .
249251
@@ -346,13 +348,20 @@ handle_call({init, Overall}, _From,
346348 end || Pid <- Rest ],
347349 Delegate = child (Overall , delegate ),
348350 erlang :monitor (process , Delegate ),
349- [maybe_start (Group , Delegate , S ) || S <- ChildSpecs ],
350- {reply , ok , State # state {overall = Overall , delegate = Delegate }};
351+ State1 = State # state {overall = Overall , delegate = Delegate },
352+ case all_started ([maybe_start (Group , Delegate , S ) || S <- ChildSpecs ]) of
353+ true -> {reply , ok , State1 };
354+ false -> {stop , shutdown , State1 }
355+ end ;
351356
352357handle_call ({start_child , ChildSpec }, _From ,
353358 State = # state {delegate = Delegate ,
354359 group = Group }) ->
355- {reply , maybe_start (Group , Delegate , ChildSpec ), State };
360+ {reply , case maybe_start (Group , Delegate , ChildSpec ) of
361+ already_in_mnesia -> {error , already_present };
362+ {already_in_mnesia , Pid } -> {error , {already_started , Pid }};
363+ Else -> Else
364+ end , State };
356365
357366handle_call ({delete_child , Id }, _From , State = # state {delegate = Delegate ,
358367 group = Group }) ->
@@ -400,13 +409,16 @@ handle_info({'DOWN', _Ref, process, Pid, _Reason},
400409 % % TODO load balance this
401410 % % No guarantee pg2 will have received the DOWN before us.
402411 Self = self (),
403- case lists :sort (? PG2 :get_members (Group )) -- [Pid ] of
404- [Self | _ ] -> {atomic , ChildSpecs } =
405- mnesia :transaction (fun () -> update_all (Pid ) end ),
406- [start (Delegate , ChildSpec ) || ChildSpec <- ChildSpecs ];
407- _ -> ok
408- end ,
409- {noreply , State };
412+ R = case lists :sort (? PG2 :get_members (Group )) -- [Pid ] of
413+ [Self | _ ] -> {atomic , ChildSpecs } =
414+ mnesia :transaction (fun () -> update_all (Pid ) end ),
415+ [start (Delegate , ChildSpec ) || ChildSpec <- ChildSpecs ];
416+ _ -> []
417+ end ,
418+ case all_started (R ) of
419+ true -> {noreply , State };
420+ false -> {stop , shutdown , State }
421+ end ;
410422
411423handle_info (Info , State ) ->
412424 {stop , {unexpected_info , Info }, State }.
@@ -428,8 +440,8 @@ maybe_start(Group, Delegate, ChildSpec) ->
428440 check_start (Group , Delegate , ChildSpec )
429441 end ) of
430442 {atomic , start } -> start (Delegate , ChildSpec );
431- {atomic , undefined } -> { error , already_present } ;
432- {atomic , Pid } -> {error , { already_started , Pid } };
443+ {atomic , undefined } -> already_in_mnesia ;
444+ {atomic , Pid } -> {already_in_mnesia , Pid };
433445 % % If we are torn down while in the transaction...
434446 {aborted , E } -> {error , E }
435447 end .
@@ -499,6 +511,8 @@ delete_all(Group) ->
499511 [delete (Group , id (C )) ||
500512 C <- mnesia :select (? TABLE , [{MatchHead , [], ['$1' ]}])].
501513
514+ all_started (Results ) -> [] =:= [R || R = {error , _ } <- Results ].
515+
502516% %----------------------------------------------------------------------------
503517
504518create_tables () ->
0 commit comments