Exercício 11

OC 1999/2000 (Exercícios Práticos)


Enunciado

Altere o exercício 4, por forma a tornar o sistema tolerante a falhas.

Escolha a melhor estratégia de controlo em função do sistema e da implementação já existente.


Solução

-module(exercicio11).
-export([start/2,init/2,p1/1,p2/1,p3/1,p4/1]).
start(X,Y) ->
	spawn(?MODULE,init,[X,Y]).
init(X,Y) ->
	process_flag(trap_exit,true),
	P4=spawn_link(?MODULE,p4,[self()]),
	P3=spawn_link(?MODULE,p3,[P4]),
	P2=spawn_link(?MODULE,p2,[P3]),
	P1=spawn_link(?MODULE,p1,[P3]),
	P1!X,
	P2!Y,
	loop(P4,P3,P2,P1,X,Y).
loop(P4,P3,P2,P1,X,Y) ->
	receive
		{'EXIT', P4, Reason} ->
			P4_new=spawn_link(?MODULE,p4,[self()]),
			P3!{pid_change,P4_new},
			loop(P4_new,P3,P2,P1,X,Y);
		{'EXIT', P3, Reason} ->
			P3_new=spawn_link(?MODULE,p3,[P4]),
			P1!{pid_change,P3_new},
			P2!{pid_change,P3_new},
			loop(P4,P3_new,P2,P1,X,Y);
		{'EXIT', P2, Reason} ->
			P2_new=spawn_link(?MODULE,p2,[P3]),
			P2_new!Y,
			loop(P4,P3,P2_new,P1,X,Y);
		{'EXIT', P1, Reason} ->
			P1_new=spawn_link(?MODULE,p1,[P3]),
			P1_new!X,
			loop(P4,P3,P2,P1_new,X,Y);
		Result when number(Result) ->
			io:format("Resultado: ~w.~n",[Result]),
			exit(result_ok)
	end.
p1(P3) ->
	receive
		X when number(X) -> ok
	end,
	A = 2*X,
	P3 ! A,
	loop_worker(P3,A).
p2(P3) ->
	receive
		X when number(X) -> ok
	end,
	B = X div 2,
	P3 ! B,
	loop_worker(P3,B).
p3(P4) ->
	receive
		A -> ok
	end,
	receive
		B -> ok
	end,
	C=A+B,
	P4 ! C,
	loop_worker(P4,C).
p4(PidStart) ->
	receive
		C when number(C) -> C
	end,
	Result=factorial(C),
	PidStart!Result.
factorial(0) -> 1;
factorial(N) -> N*factorial(N-1).
loop_worker(Pid,Result) ->
	receive
		{change_pid, Pid_new} ->
			Pid_new!Result,
			loop_worker(Pid_new,Result)
	end.


Última actualização: 19-05-2000

OC 1999/2000 (Exercícios Práticos)