[erlang-questions] object vs. actor (Re: Massive Numbers of Actors vs. Massive Numbers of Objects vs. ????)

Jeff Schultz jws@REDACTED
Sun Mar 11 02:03:06 CET 2012


On Thu, Mar 01, 2012 at 02:42:34PM -0500, Miles Fidelman wrote:
> Garrett Smith wrote:
>> Erlang processes aren't persisted, but their state can be, quite easily.

>> A trivial example, in an Erlang shell:

>> 1>  Add = fun(X, Y) ->  X + Y end.
>> 2>  Add(10, 10).
>> 100
>> 3>  file:write_file("addfun", term_to_binary(Add)).
>> 4>  init:stop().

>> And restart Erlang shell:

>> 1>  {ok, Bin} = file:read_file("addfun").
>> 2>  Add = binary_to_term(Bin).
>> 3>  Add(10, 10).
>> 100

> That's not persisting a process' state, though.  It's not so easy to say:
> 1. spawn, say, 10,000 gen_fsms,
> 2. run for a while
> 3. save the internal state of those 10,000 state machines
> 4. stop the shell (really the VM)
> 5. restart
> 6. restore those state machines, complete with their original PIDs

It's a small part of the overall application you're building, but
doing almost all of that is pretty easy, and rather fun.  Here's a
simple example:

-module(per).
-export([start/1]).

loop(State) ->
    io:format("Looping from ~p~n", [State]),
    receive
    {inc, X} ->
	io:format("Incrementing ~p by ~p~n", [State, X]),
	loop(State + X);
    suspend ->
	io:format("Suspending with state ~p~n", [State]),
	fun() -> loop(State) end
    end.

start(InitialValue) ->
    outer(loop(InitialValue)).

outer(Computation) ->
    outer(Computation()).

38> Pid = spawn(per, start, [10]).
Looping from 10
<0.121.0>
39> Pid ! {inc, 5}.               
Incrementing 10 by 5
{inc,5}
Looping from 15
40> Pid ! suspend.                
Suspending with state 15
suspend
Looping from 15
41> Pid ! {inc, 3}.
Incrementing 15 by 3
{inc,3}
Looping from 18
42> Pid ! suspend. 
Suspending with state 18
suspend
Looping from 18

Note that the fun returned from loop/1 on receipt of the suspend
message captures the current State.

This doesn't do your point 6.  The process running loop/1 gets a new
PID each time it's restarted, but if you're depending on Erlang PIDs
to find a *persistent* resource, you're going to have trouble the
first time something goes down anyway.


    Jeff Schultz

> Fairly straightforward to:

> 1. spawn 10,000 gen_fsms
> 2. add their PIDs to a name-to-PID lookup table
> 3. include logic such that an inactive fsm
> - times out
> - writes it's state to a file
> - updates the name-to-PID table to point the file
> - kill itself
> 4. write a listener that takes incoming messages, identifies the associated 
> fsm by name and either
> - passes the message to the file, or
> - loads and restarts the process, then passes the messages

> What I've really done is rewrite erlang's hibernation functionality.



More information about the erlang-questions mailing list