Actor Model : Can we get the semantics of a shared lock with the actor model?

194 views Asked by At

The fact that an actor processes one message at a time and encapsulates state, which it does not share, is sufficient to provide synchronization semantics. So mutual exclusion (write-lock) is taken care of. However how do we go about implementing a read-write lock semantics where multiple readers can work in parallel but readers and writers are mutually exclusive? Eg : Concurrent HashMap.

4

There are 4 answers

0
Mo Ein On

mutual context in the actor model solution handle by queue concept and its avoiding lock mechanism for handling back pressure. if you want shard memory use other stuff like ets .

0
aronisstav On

With message-passing, an actor that "models" the lock can handle write/read access modes, with correct permissions. The idea is that other actors send requests to grab the lock to the lock actor, and wait for a reply. Using Erlang, the state of the lock actor can be something like #{writer := boolean(), readers := integer()} and the control loop something like:

%% A writer holds the lock:
loop(#{writer := true, readers := 0}) ->
  receive
    unlock_write -> loop(#{writer => false, readers => 0})
  end;
%% One or more readers hold the lock:
loop(#{writer := false, readers := N}) when N > 0 ->
  receive
    {lock_read, Who} -> Who ! lock_granted, loop(#{writer => false, readers => N + 1});
    unlock_read -> loop(#{writer => false, readers => N - 1})
  end;
%% No writer or readers hold the lock:
loop(#{writer := false, readers := 0}) ->
  receive
    {lock_read, Who} -> Who ! lock_granted, loop(#{writer => false, readers => 1});
    {lock_write, Who} -> Who ! lock_granted, loop(#{writer => true, readers => 0})
  end.

Notice how at each state the only messages that can be processed are the ones 'allowed' by that state (e.g. when the lock is held by a writer only an unlock_write message can be processed and change the state).

0
Ming L. On

Use gen_server. The hash map can be preserved in the state. You may have functions to operate over the state, the hashmap.

0
Zachary K On

In Erlang, you can do this in a few ways. The most obvious way is to use an ETS Table. All ets writes are atomic (even if they contain several records) What might be even better is to setup a protected ets table where 1 process can write but all processes can read.