Source

hello / erlang / ringbench.erl

% $Id$
% page 150: Problems.
%
-module(ringbench).
-export([start/2, b/2]).

start(AnAtom, Fun)->
    {ok, AnAtom, Fun}.
%    register(AnAtom, spawn( fun ringbench:hoge/0 )).

b(N, M)->
    Max = erlang:system_info( process_limit ),
    io:format("Max: ~p~n", [Max]),
    case N > Max - 100 of
	true -> exit(1);
     	false -> %io:format("hogeho"),
	    {_, Time}=statistics(wall_clock),
	    ring_many(N, M, "hogehoge"),
	    io:format( "~p processes: time = ~p us ~n", [N, Time/1000] )
    end.
%    {ok, Head}.

%spawn N processes in ring and exchange M messages.
ring_many(N, M, Message)->
    Manager = self(),
    Head = spawn( fun() -> make_ring( Manager, self(), N) end ), % create ring
    io:format("~p started from ~p:~p.~n", [Head, Manager, N]),
    receive
	{ok, Tail} ->  % creating ring done
	    io:format("all process kicked: ~p.~n",[Tail]),
	    io:format("ring_many started: ~p, ~px~p~n", [self(), Message, M]),
	    Head ! {M, Message}; %send_many_message( Head, M, Message );
	Any ->
	    io:format("~p.~n", [Any])
    after 3000 ->
	    true
%	    ring_wait(Head)
    end.
make_ring(Manager, Start, 1)->
    Manager ! {ok, self()},
%    io:format("message sent to ~p.~n", [Manager]);
    receive
	{ M, Message } -> send_many_message( Start, M, Message )
    after 3000 ->
	    true
    end;
make_ring(Manager, Start, N)->
    Next = spawn( fun()->make_ring(Manager, Start, N-1)end),
    io:format("~p started from ~p:~p.~n", [Next, self(), N]),
    receive
	{ M, Message } -> send_many_message( Next, M, Message )
    after 3000 ->
	    true
    end.


send_many_message(To, 0, Message)->
    To ! { 0, Message };
send_many_message(To, M, Message)->
    To ! { M, Message },
    io:format("from ~p to ~p: ~p~n", [self(), To, Message]),
    send_many_message( To, M-1, Message ).
		    

%just spawn N processes
spawn_many(N)->
    statistics(runtime),
    statistics(wall_clock),
    L = for(1, N, fun() -> spawn(fun()->wait() end)end),
    {_, Time1}=statistics(runtime),
    {_, Time2}=statistics(wall_clock),
    lists:foreach( fun(Pid) -> Pid ! die end, L ),
    U1 = Time1 * 1000 / N,
    U2 = Time2 * 1000 / N,
    io:format( "Process spawn time = ~p (~p) us ~n", [U1, U2] ),
    {ok, N}.

wait() ->
    %io:format("hogehoge ~p ~n", [self()]),
    receive 
	die -> void
    end.
	     
for( N, N, F) -> [F()];
for( I, N, F) -> [F()| for( I+1, N, F)].