Skip to content

Latest commit

 

History

History
1886 lines (1167 loc) · 64.9 KB

gproc.md

File metadata and controls

1886 lines (1167 loc) · 64.9 KB

Module gproc

Extended process registry This module implements an extended process registry.

Behaviours: gen_server.

Authors: Ulf Wiger (ulf@wiger.net).

Description

For a detailed description, see erlang07-wiger.pdf.

NOTE: The functions in the Gproc API expect the Gproc application to be running.

Tuning Gproc performance

Gproc relies on a central server and an ordered-set ets table. Effort is made to perform as much work as possible in the client without sacrificing consistency. A few things can be tuned by setting the following application environment variables in the top application of gproc (usually gproc):

  • {ets_options, list()} - Currently, the options {write_concurrency, F} and {read_concurrency, F} are allowed. The default is [{write_concurrency, true}, {read_concurrency, true}]
  • {server_options, list()} - These will be passed as spawn options when starting the gproc and gproc_dist servers. Default is []. It is likely that {priority, high | max} and/or increasing min_heap_size will improve performance.

Data Types


attr() = {atom(), any()}

attrs() = [attr()]

context() = {scope(), type()} | type()

ctr_incr() = integer()

ctr_setval() = integer()

ctr_thr() = integer()

headpat() = {keypat(), pidpat(), any()}

increment() = ctr_incr() | ctr_update() | [ctr_update()]

key() = {type(), scope(), any()}

keypat() = {sel_type() | sel_var(), l | g | sel_var(), any()}

monitor_type() = info | standby | follow

pidpat() = pid() | sel_var()

reg_id() = {type(), scope(), any()}

scope() = l | g

sel_context() = {scope(), type()} | type()

sel_pattern() = [{headpat(), list(), list()}]

sel_scope() = scope | all | global | local

sel_type() = type() | names | props | counters | aggr_counters | resources | resource_counters

sel_var() = _ | atom()

type() = n | p | c | a | r | rc

unique_id() = {n | a, scope(), any()}

value() = any()

Function Index

add_global_aggr_counter/1Registers a global (unique) aggregated counter.
add_global_counter/2Registers a global (non-unique) counter.
add_global_name/1Registers a global (unique) name.
add_global_property/2Registers a global (non-unique) property.
add_local_aggr_counter/1Registers a local (unique) aggregated counter.
add_local_counter/2Registers a local (non-unique) counter.
add_local_name/1Registers a local (unique) name.
add_local_property/2Registers a local (non-unique) property.
add_shared_local_counter/2Registers a local shared (unique) counter.
audit_process/1
await/1Equivalent to await(Key, infinity).
await/2Wait for a name or aggregated counter to be registered.
await/3Wait for a name or aggregated counter to be registered on Node.
bcast/2Equivalent to bcast(nodes(), Key, Msg).
bcast/3Sends a message to processes corresponding to Key on Nodes.
cancel_wait/2Cancels a previous call to nb_wait/1.
cancel_wait/3Cancels a previous call to nb_wait/2.
cancel_wait_or_monitor/1
default/1
demonitor/2Remove a monitor on a registered name This function is the reverse of monitor/1.
ensure_reg/1Equivalent to ensure_reg(Key, default(Key), []).
ensure_reg/2Equivalent to ensure_reg(Key, Value, []).
ensure_reg/3Registers a new name or property unless such and entry (by key) has already been registered by the current process.
ensure_reg_other/2
ensure_reg_other/3Equivalent to ensure_reg_other(Key, Pid, Value, []).
ensure_reg_other/4Register or update name or property to another process.
first/1Behaves as ets:first(Tab) for a given type of registration.
get_attribute/2Get attribute value of Attr associated with Key for most likely Pid.
get_attribute/3Get the attribute value of Attr associated with Key for process Pid.
get_attribute_shared/2Get the attribute value of Attr associated with the shared Key.
get_attributes/1Get attributes associated with registration.
get_attributes/2Returns the list of attributes associated with the registration.
get_env/3Equivalent to get_env(Scope, App, Key, [app_env]).
get_env/4Read an environment value, potentially cached as a gproc_env property.
get_set_env/3Equivalent to get_set_env(Scope, App, Key, [app_env]).
get_set_env/4Fetch and cache an environment value, if not already cached.
get_value/1Reads the value stored with a key registered to the current process.
get_value/2Reads the value stored with a key registered to the process Pid.
get_value_shared/1Reads the value stored with a shared key.
give_away/2Atomically transfers the key From to the process identified by To.
goodbye/0Unregister all items of the calling process and inform gproc to forget about the calling process.
i/0Similar to the built-in shell command i() but inserts information about names and properties registered in Gproc, where applicable.
info/1Similar to process_info(Pid) but with additional gproc info.
info/2Similar to process_info(Pid, Item), but with additional gproc info.
last/1Behaves as ets:last(Tab) for a given type of registration.
lookup_global_aggr_counter/1Lookup a global (unique) aggregated counter and returns its value.
lookup_global_counters/1Look up all global (non-unique) instances of a given Counter.
lookup_global_name/1Lookup a global unique name.
lookup_global_properties/1Look up all global (non-unique) instances of a given Property.
lookup_global_resources/1Look up all global (non-unique) instances of a given Resource.
lookup_local_aggr_counter/1Lookup a local (unique) aggregated counter and returns its value.
lookup_local_counters/1Look up all local (non-unique) instances of a given Counter.
lookup_local_name/1Lookup a local unique name.
lookup_local_properties/1Look up all local (non-unique) instances of a given Property.
lookup_local_resources/1Look up all local (non-unique) instances of a given Resource.
lookup_pid/1Lookup the Pid stored with a key.
lookup_pids/1Returns a list of pids with the published key Key.
lookup_value/1Lookup the value stored with a key.
lookup_values/1Retrieve the {Pid,Value} pairs corresponding to Key.
monitor/1Equivalent to monitor(Key, info).
monitor/2monitor a registered name monitor(Key, info) works much like erlang:monitor(process, Pid), but monitors a unique name registered via gproc.
mreg/3Register multiple {Key,Value} pairs of a given type and scope.
munreg/3Unregister multiple Key items of a given type and scope.
nb_wait/1Wait for a name or aggregated counter to be registered.
nb_wait/2Wait for a name or aggregated counter to be registered on Node.
next/2Behaves as ets:next(Tab,Key) for a given type of registration.
prev/2Behaves as ets:prev(Tab,Key) for a given type of registration.
reg/1Equivalent to reg(Key, default(Key), []).
reg/2Register a name or property for the current process.
reg/3Register a name or property for the current process Attrs (default: []) can be inspected using get_attribute/2.
reg_or_locate/1Equivalent to reg_or_locate(Key, default(Key)).
reg_or_locate/2Try registering a unique name, or return existing registration.
reg_or_locate/3Spawn a process with a registered name, or return existing registration.
reg_other/2Equivalent to reg_other(Key, Pid, default(Key), []).
reg_other/3Equivalent to reg_other(Key, Pid, Value, []).
reg_other/4Register name or property to another process.
reg_remote/2
reg_remote/3
reg_remote/4
reg_shared/1Register a resource, but don't tie it to a particular process.
reg_shared/2Register a resource, but don't tie it to a particular process.
reg_shared/3
register_name/2Behaviour support callback.
reset_counter/1Reads and resets a counter in a "thread-safe" way.
select/1Perform a select operation on the process registry.
select/2Perform a select operation with limited context on the process registry.
select/3Like select/2 but returns Limit objects at a time.
select_count/1Equivalent to select_count(all, Pat).
select_count/2Perform a select_count operation on the process registry.
send/2Sends a message to the process, or processes, corresponding to Key.
set_attributes/2Add/modify {Key, Value} attributes associated with a registration.
set_attributes_shared/2Add/modify {Key, Value} attributes associated with a shared registration.
set_env/5Updates the cached value as well as underlying environment.
set_value/2Sets the value of the registration given by Key.
set_value_remote/3
set_value_shared/2Sets the value of the shared registration given by Key.
start_link/0Starts the gproc server.
table/0Equivalent to table({all, all}).
table/1Equivalent to table(Context, []).
table/2QLC table generator for the gproc registry.
unreg/1Unregister a name or property.
unreg_other/2Unregister a name registered to another process.
unreg_remote/2
unreg_shared/1Unregister a shared resource.
unregister_name/1Equivalent to unreg / 1.
update_counter/2Updates the counter registered as Key for the current process.
update_counter/3
update_counter_remote/3
update_counters/2Update a list of counters.
update_shared_counter/2Updates the shared counter registered as Key.
where/1Returns the pid registered as Key.
whereis_name/1Equivalent to where / 1.
wide_await/3Wait for a local name to be registered on any of Nodes.

Function Details

add_global_aggr_counter/1

add_global_aggr_counter(Name) -> any()

Equivalent to reg({a, g, Name}).

Registers a global (unique) aggregated counter.

add_global_counter/2

add_global_counter(Name, Initial) -> any()

Registers a global (non-unique) counter. @equiv reg({c,g,Name},Value)

add_global_name/1

add_global_name(Name) -> any()

Registers a global (unique) name. @equiv reg({n,g,Name})

add_global_property/2

add_global_property(Name, Value) -> any()

Registers a global (non-unique) property. @equiv reg({p,g,Name},Value)

add_local_aggr_counter/1

add_local_aggr_counter(Name) -> any()

Equivalent to reg({a, l, Name}).

Registers a local (unique) aggregated counter.

add_local_counter/2

add_local_counter(Name, Initial) -> any()

Registers a local (non-unique) counter. @equiv reg({c,l,Name},Value)

add_local_name/1

add_local_name(Name) -> any()

Registers a local (unique) name. @equiv reg({n,l,Name})

add_local_property/2

add_local_property(Name, Value) -> any()

Registers a local (non-unique) property. @equiv reg({p,l,Name},Value)

add_shared_local_counter/2

add_shared_local_counter(Name, Initial) -> any()

Equivalent to reg_shared({c, l, Name}, Value).

Registers a local shared (unique) counter.

audit_process/1


audit_process(Pid::pid()) -> ok

await/1


await(Key::key()) -> {pid(), Value}

Equivalent to await(Key, infinity).

await/2


await(Key::key(), Timeout) -> {pid(), Value}
  • Timeout = integer() | infinity

Wait for a name or aggregated counter to be registered. The function raises an exception if the timeout expires. Timeout must be either an integer > 0 or 'infinity'. A small optimization: we first perform a lookup, to see if the name is already registered. This way, the cost of the operation will be roughly the same as of where/1 in the case where the name is already registered (the difference: await/2 also returns the value).

await/3


await(Node::node(), Key::key(), Timeout) -> {pid(), Value}
  • Timeout = integer() | infinity

Wait for a name or aggregated counter to be registered on Node. This function works exactly like await/2, but queries a remote node instead. An exception is thrown if Node cannot be reached. If gproc is not running on a given node, this is treated the same as the node being down.

bcast/2


bcast(Key::key(), Msg::any()) -> Msg

Equivalent to bcast(nodes(), Key, Msg).

bcast/3


bcast(Nodes::[atom()], Key::key(), Msg::any()) -> Msg

Sends a message to processes corresponding to Key on Nodes.

This function complements send/2 and works on locally registered resources that send/2 supports. Messages are routed via a special broadcast server on each node to ensure that ordering is preserved. Distributed delivery is asynchronous and carries the same guarantees as normal message passing (with the added proviso that the broadcast server also needs to be available).

See also: send/2.

cancel_wait/2


cancel_wait(Key::key(), Ref) -> ok
  • Ref = all | reference()

Cancels a previous call to nb_wait/1

If Ref = all, all wait requests on Key from the calling process are canceled.

cancel_wait/3


cancel_wait(Node::node(), Key::key(), Ref) -> ok
  • Ref = all | reference()

Cancels a previous call to nb_wait/2

This function works just like cancel_wait/2, but talks to a remote node.

cancel_wait_or_monitor/1

cancel_wait_or_monitor(Key) -> any()

default/1

default(X1) -> any()

demonitor/2


demonitor(Key::key(), Ref::reference()) -> ok

Remove a monitor on a registered name This function is the reverse of monitor/1. It removes a monitor previously set on a unique name. This function always succeeds given legal input.

ensure_reg/1

ensure_reg(Key) -> any()

Equivalent to ensure_reg(Key, default(Key), []).

ensure_reg/2


ensure_reg(Key::key(), Value::value()) -> new | updated

Equivalent to ensure_reg(Key, Value, []).

ensure_reg/3


ensure_reg(Key::key(), Value::value(), Attrs::attrs()) -> new | updated

Registers a new name or property unless such and entry (by key) has already been registered by the current process. If Key already exists, the entry will be updated with the given Value and Attrs.

This function allows the caller to efficiently register an entry without first checking whether it has already been registered. An exception is raised if the name or property is already registered by someone else.

ensure_reg_other/2

ensure_reg_other(Key, Pid) -> any()

ensure_reg_other/3

ensure_reg_other(Key, Pid, Value) -> any()

Equivalent to ensure_reg_other(Key, Pid, Value, []).

ensure_reg_other/4


ensure_reg_other(Key::key(), Pid::pid(), Value::value(), Attrs::attrs()) -> new | updated

Register or update name or property to another process.

Equivalent to reg_other/3, but allows for registration of another process instead of the current process. Also see ensure_reg/3.

first/1


first(Context::context()) -> key() | $end_of_table

Behaves as ets:first(Tab) for a given type of registration.

See http://www.erlang.org/doc/man/ets.html#first-1. The registry behaves as an ordered_set table.

get_attribute/2


get_attribute(Key, Attribute::atom()) -> Value

Get attribute value of Attr associated with Key for most likely Pid.

The most likely Pid in this case is self() for properties and counters, and the current registration holder in case of names or aggregated counters. An exception is raised if Key is not registered for the given process.

get_attribute/3


get_attribute(Key, Pid::pid() | shared, Attr::atom()) -> Value

Get the attribute value of Attr associated with Key for process Pid.

If Pid == shared, the attribute of a shared key (see reg_shared/1) will be read.

get_attribute_shared/2


get_attribute_shared(Key, Attr::atom()) -> Value

Get the attribute value of Attr associated with the shared Key.

Equivalent to get_attribute(Key, shared, Attr) (see get_attribute/3).

get_attributes/1


get_attributes(Key::key()) -> [{K, V}]

Equivalent to get_attributes(Key, self()).

Get attributes associated with registration.

get_attributes/2


get_attributes(Key::key(), Pid::pid() | shared) -> [{K, V}]

Returns the list of attributes associated with the registration.

This function raises a badarg exception if there is no corresponding registration.

get_env/3


get_env(Scope::scope(), App::atom(), Key::atom()) -> term()

Equivalent to get_env(Scope, App, Key, [app_env]).

get_env/4


get_env(Scope::scope(), App::atom(), Key::atom(), Strategy) -> term()
  • Strategy = [Alternative]
  • Alternative = app_env | os_env | inherit | {inherit, pid()} | {inherit, unique_id()} | init_arg | {mnesia, ActivityType, Oid, Pos} | {default, term()} | error

Read an environment value, potentially cached as a gproc_env property.

This function first tries to read the value of a cached property, {p, Scope, {gproc_env, App, Key}}. If this fails, it will try the provided alternative strategy. Strategy is a list of alternatives, tried in order. Each alternative can be one of:

  • app_env - try application:get_env(App, Key)
  • os_env - try os:getenv(ENV), where ENV is Key converted into an uppercase string
  • {os_env, ENV} - try os:getenv(ENV)
  • inherit - inherit the cached value, if any, held by the parent process.
  • {inherit, Pid} - inherit the cached value, if any, held by Pid.
  • {inherit, Id} - inherit the cached value, if any, held by the process registered in gproc as Id.
  • init_arg - try init:get_argument(Key); expects a single value, if any.
  • {mnesia, ActivityType, Oid, Pos} - try mnesia:activity(ActivityType, fun() -> mnesia:read(Oid) end); retrieve the value in position Pos if object found.
  • {default, Value} - set a default value to return once alternatives have been exhausted; if not set, undefined will be returned.
  • error - raise an exception, erlang:error(gproc_env, [App, Key, Scope]).

While any alternative can occur more than once, the only one that might make sense to use multiple times is {default, Value}.

The return value will be one of:

  • The value of the first matching alternative, or error exception, whichever comes first
  • The last instance of {default, Value}, or undefined, if there is no matching alternative, default or error entry in the list.

The error option can be used to assert that a value has been previously cached. Alternatively, it can be used to assert that a value is either cached or at least defined somewhere, e.g. get_env(l, mnesia, dir, [app_env, error]).

get_set_env/3


get_set_env(Scope::scope(), App::atom(), Key::atom()) -> term()

Equivalent to get_set_env(Scope, App, Key, [app_env]).

get_set_env/4


get_set_env(Scope::scope(), App::atom(), Key::atom(), Strategy) -> Value

Fetch and cache an environment value, if not already cached.

This function does the same thing as get_env/4, but also updates the cache. Note that the cache will be updated even if the result of the lookup is undefined.

See also: get_env/4.

get_value/1


get_value(Key) -> Value

Reads the value stored with a key registered to the current process.

If no such key is registered to the current process, this function exits.

get_value/2


get_value(Key, Pid) -> Value

Reads the value stored with a key registered to the process Pid.

If Pid == shared, the value of a shared key (see reg_shared/1) will be read.

get_value_shared/1


get_value_shared(Key) -> Value

Reads the value stored with a shared key.

If no such shared key is registered, this function exits.

give_away/2


give_away(From::key(), To::pid() | key()) -> undefined | pid()

Atomically transfers the key From to the process identified by To.

This function transfers any gproc key (name, property, counter, aggr counter) from one process to another, and returns the pid of the new owner.

To must be either a pid or a unique name (name or aggregated counter), but does not necessarily have to resolve to an existing process. If there is no process registered with the To key, give_away/2 returns undefined, and the From key is effectively unregistered.

It is allowed to give away a key to oneself, but of course, this operation will have no effect.

Fails with badarg if the calling process does not have a From key registered.

goodbye/0


goodbye() -> ok

Unregister all items of the calling process and inform gproc to forget about the calling process.

This function is more efficient than letting gproc perform these cleanup operations.

i/0


i() -> ok

Similar to the built-in shell command i() but inserts information about names and properties registered in Gproc, where applicable.

info/1


info(Pid::pid()) -> ProcessInfo
  • ProcessInfo = [{gproc, [{Key, Value}]} | ProcessInfo]

Similar to process_info(Pid) but with additional gproc info.

Returns the same information as process_info(Pid), but with the addition of a gproc information item, containing the {Key,Value} pairs registered to the process.

info/2


info(Pid::pid(), Item::atom()) -> {Item, Info}

Similar to process_info(Pid, Item), but with additional gproc info.

For Item = gproc, this function returns a list of {Key, Value} pairs registered to the process Pid. For other values of Item, it returns the same as http://www.erlang.org/doc/man/erlang.html#process_info-2.

last/1


last(Context::context()) -> key() | $end_of_table

Behaves as ets:last(Tab) for a given type of registration.

See http://www.erlang.org/doc/man/ets.html#last-1. The registry behaves as an ordered_set table.

lookup_global_aggr_counter/1


lookup_global_aggr_counter(Name::any()) -> integer()

Equivalent to lookup_value({a, g, Name}).

Lookup a global (unique) aggregated counter and returns its value. Fails if there is no such object.

lookup_global_counters/1


lookup_global_counters(Counter::any()) -> [{pid(), Value::integer()}]

Equivalent to lookup_values({c, g, Counter}).

Look up all global (non-unique) instances of a given Counter. Returns a list of {Pid, Value} tuples for all matching objects.

lookup_global_name/1


lookup_global_name(Name::any()) -> pid()

Equivalent to where({n, g, Name}).

Lookup a global unique name. Fails if there is no such name.

lookup_global_properties/1


lookup_global_properties(Property::any()) -> [{pid(), Value}]

Equivalent to lookup_values({p, g, Property}).

Look up all global (non-unique) instances of a given Property. Returns a list of {Pid, Value} tuples for all matching objects.

lookup_global_resources/1


lookup_global_resources(Resource::any()) -> [{pid(), Value::integer()}]

Equivalent to lookup_values({r, g, Resource}).

Look up all global (non-unique) instances of a given Resource. Returns a list of {Pid, Value} tuples for all matching objects.

lookup_local_aggr_counter/1


lookup_local_aggr_counter(Name::any()) -> integer()

Equivalent to where({a, l, Name}).

Lookup a local (unique) aggregated counter and returns its value. Fails if there is no such object.

lookup_local_counters/1


lookup_local_counters(Counter::any()) -> [{pid(), Value::integer()}]

Equivalent to lookup_values({c, l, Counter}).

Look up all local (non-unique) instances of a given Counter. Returns a list of {Pid, Value} tuples for all matching objects.

lookup_local_name/1


lookup_local_name(Name::any()) -> pid()

Equivalent to where({n, l, Name}).

Lookup a local unique name. Fails if there is no such name.

lookup_local_properties/1


lookup_local_properties(Property::any()) -> [{pid(), Value}]

Equivalent to lookup_values({p, l, Property}).

Look up all local (non-unique) instances of a given Property. Returns a list of {Pid, Value} tuples for all matching objects.

lookup_local_resources/1


lookup_local_resources(Resource::any()) -> [{pid(), Value::integer()}]

Equivalent to lookup_values({r, l, Resource}).

Look up all local (non-unique) instances of a given Resource. Returns a list of {Pid, Value} tuples for all matching objects.

lookup_pid/1


lookup_pid(Key) -> Pid

Lookup the Pid stored with a key.

This function raises a badarg exception if Key is not registered.

lookup_pids/1


lookup_pids(Key::key()) -> [pid()]

Returns a list of pids with the published key Key

If the type of registration is either name or aggregated counter, this function will return either an empty list, or a list of one pid. For non-unique types, the return value can be a list of any length.

Note: shared resources are not associated with any pid, and will therefore be excluded.

lookup_value/1


lookup_value(Key) -> Value

Lookup the value stored with a key.

This function raises a badarg exception if Key is not registered.

lookup_values/1


lookup_values(Key::key()) -> [{pid(), Value}]

Retrieve the {Pid,Value} pairs corresponding to Key.

Key refer to any type of registry object. If it refers to a unique object, the list will be of length 0 or 1. If it refers to a non-unique object, the return value can be a list of any length.

monitor/1

monitor(Key) -> any()

Equivalent to monitor(Key, info).

monitor/2


monitor(Key::key(), Type::monitor_type()) -> reference()

monitor a registered name monitor(Key, info) works much like erlang:monitor(process, Pid), but monitors a unique name registered via gproc. A message, {gproc, unreg, Ref, Key} will be sent to the requesting process, if the name is unregistered or the registered process dies. If there is a standby monitor (see below), a message {gproc, {failover, ToPid}, Ref, Key} is sent to all monitors. If the name is passed to another process using give_away/2, the event {gproc, {migrated, ToPid}, Ref, Key} is sent to all monitors.

monitor(Key, standby) sets up the monitoring process as a standby for the registered name. If the registered process dies, the first standby process inherits the name, and a message {gproc, {failover, ToPid}, Ref, Key} is sent to all monitors, including the one that inherited the name.

If the name is not yet registered, the unreg event is sent immediately. If the calling process in this case tried to start a standby monitoring, it receives the registered name and the failover event immediately.

monitor(Key, follow) keeps monitoring the registered name even if it is temporarily unregistered. The messages received are the same as for the other monitor types, but {gproc, registered, Ref, Key} is also sent when a new process registers the name.

mreg/3


mreg(T::type(), C::scope(), KVL::[{Key::any(), Value::any()}]) -> true

Register multiple {Key,Value} pairs of a given type and scope.

This function is more efficient than calling reg/2 repeatedly. It is also atomic in regard to unique names; either all names are registered or none are.

munreg/3


munreg(T::type(), C::scope(), L::[Key::any()]) -> true

Unregister multiple Key items of a given type and scope.

This function is usually more efficient than calling unreg/1 repeatedly.

nb_wait/1


nb_wait(Key::key()) -> Ref

Wait for a name or aggregated counter to be registered. The caller can expect to receive a message, {gproc, Ref, registered, {Key, Pid, Value}}, once the name is registered.

nb_wait/2


nb_wait(Node::node(), Key::key()) -> Ref

Wait for a name or aggregated counter to be registered on Node. The caller can expect to receive a message, {gproc, Ref, registered, {Key, Pid, Value}}, once the name is registered.

next/2


next(Context::context(), Key::key()) -> key() | $end_of_table

Behaves as ets:next(Tab,Key) for a given type of registration.

See http://www.erlang.org/doc/man/ets.html#next-2. The registry behaves as an ordered_set table.

prev/2


prev(Context::context(), Key::key()) -> key() | $end_of_table

Behaves as ets:prev(Tab,Key) for a given type of registration.

See http://www.erlang.org/doc/man/ets.html#prev-2. The registry behaves as an ordered_set table.

reg/1


reg(Key::key()) -> true

Equivalent to reg(Key, default(Key), []).

reg/2


reg(Key::key(), Value::value()) -> true

Register a name or property for the current process

reg/3


reg(Key::key(), Value::value(), Attrs::attrs()) -> true

Register a name or property for the current process Attrs (default: []) can be inspected using get_attribute/2.

The structure of Key is {Type, Context, Name}, where:

  • Context :: l | g - l means 'local' context; g means 'global'
  • Type :: p | n | c | a | r | rc specifies the type of entry

The semantics of the different types:

  • p - 'property', is non-unique, i.e. different processes can each register a property with the same name.
  • n - 'name, is unique within the given context (local or global).
  • c - 'counter', is similar to a property, but has a numeric value and behaves roughly as an ets counter (see update_counter/2.)
  • a - 'aggregated counter', is automatically updated by gproc, and reflects the sum of all counter objects with the same name in the given scope. The initial value for an aggregated counter must be undefined.
  • r - 'resource property', behaves like a property, but can be tracked with a 'resource counter'. Note that using an rc wildcard name pattern (see below) for a resource property is not allowed.
  • rc - 'resource counter', tracks the number of resource properties with the same name. When the resource count reaches 0, any triggers specified using an on_zero attribute may be executed (see below). If Name is a tuple, the last element of the name can contain a wildcard, using the symbol '\\_'. This will make the resource counter keep track of any resources where all elements match except the last position. For example, {rc,l,{a,b,'\\_'}} would keep track of both {r,l,{a,b,1}} and {r,l,{a,b,2}}.

On-zero triggers:

Msg = {gproc, resource_on_zero, Context, Name, Pid}

  • {send, Key} - run gproc:send(Key, Msg)
  • {bcast, Key} - run gproc:bcast(Key, Msg)
  • publish - run gproc_ps:publish(Context, gproc_resource_on_zero, {Context, Name, Pid})
  • {unreg_shared, Type, Name} - unregister the shared key {Type, Context, Name}

reg_or_locate/1


reg_or_locate(Key::key()) -> {pid(), NewValue}

Equivalent to reg_or_locate(Key, default(Key)).

reg_or_locate/2


reg_or_locate(Key::key(), Value) -> {pid(), NewValue}

Try registering a unique name, or return existing registration.

This function tries to register the name Key, if available. If such a registration object already exists, the pid and value of the current registration is returned instead.

reg_or_locate/3


reg_or_locate(Key::key(), Value, Fun::function()) -> {pid(), NewValue}

Spawn a process with a registered name, or return existing registration.

This function checks whether a local name is registered; if not, it spawns a new process (with spawn(Fun)) and gives it the name. The pid and value of the resulting registration is returned.

When a global name is registered in this fashion, the process is spawned on the caller's node, and the group_leader of the spawned process is set to the group_leader of the calling process.

reg_other/2

reg_other(Key, Pid) -> any()

Equivalent to reg_other(Key, Pid, default(Key), []).

reg_other/3

reg_other(Key, Pid, Value) -> any()

Equivalent to reg_other(Key, Pid, Value, []).

reg_other/4


reg_other(Key, Pid, Value, Attrs) -> true

Register name or property to another process.

Equivalent to reg/3, but allows for registration of another process instead of the current process.

Note that registering other processes introduces the possibility of confusing race conditions in user code. Letting each process register its own resources is highly recommended.

Only the following resource types can be registered through this function:

  • n - unique names
  • a - aggregated counters
  • r - resource properties
  • rc - resource counters

reg_remote/2

reg_remote(Node, Key) -> any()

reg_remote/3

reg_remote(Node, Key, Value) -> any()

reg_remote/4

reg_remote(Node, Key, Value, Attrs) -> any()

reg_shared/1


reg_shared(Key::key()) -> true

Register a resource, but don't tie it to a particular process.

reg_shared({c,l,C}) -> reg_shared({c,l,C}, 0). reg_shared({a,l,A}) -> reg_shared({a,l,A}, undefined).

reg_shared/2


reg_shared(Key::key(), Value) -> true

Register a resource, but don't tie it to a particular process.

Shared resources are all unique. They remain until explicitly unregistered (using unreg_shared/1). The types of shared resources currently supported are counter and aggregated counter. In listings and query results, shared resources appear as other similar resources, except that Pid == shared. To wit, update_counter({c,l,myCounter}, shared, 1) would increment the shared counter myCounter with 1, provided it exists.

A shared aggregated counter will track updates in exactly the same way as an aggregated counter which is owned by a process.

reg_shared/3

reg_shared(Key, Value, Attrs) -> any()

register_name/2


register_name(Name::key(), Pid::pid()) -> yes | no

Behaviour support callback

reset_counter/1


reset_counter(Key) -> {ValueBefore, ValueAfter}
  • Key = {c, Scope, Name} | {n, Scope, Name}
  • Scope = l | g
  • ValueBefore = integer()
  • ValueAfter = integer()

Reads and resets a counter in a "thread-safe" way

This function reads the current value of a counter and then resets it to its initial value. The reset operation is done using update_counter/2, which allows for concurrent calls to update_counter/2 without losing updates. Aggregated counters are updated accordingly.

If Key refers to a unique name, the operation will depend on the value part of the registration being an integer(). While non-integer values are not permitted at all for counter objects, it is the user's responsibility to ensure that a name, on which reset_counter/1 is to be performed, has the appropriate value type.

select/1


select(Continuation::Arg) -> [Match] | {[Match], Continuation} | $end_of_table

Perform a select operation on the process registry

When Arg = Contination, resume a gproc:select/1 operation (see ets:select/1

When Arg = sel_pattern(), this function executes a select operation, emulating ets:select/1

select/2 offers the opportunity to narrow the search (by limiting to only global or local scope, or a single type of object). When only a pattern as single argument is given, both global and local scope, as well as all types of object can be searched. Note that the pattern may still limit the select operation so that scanning the entire table is avoided.

The physical representation in the registry may differ from the above, but the select patterns are transformed appropriately. The logical representation for the gproc select operations is given by headpat().

select/2


select(Context::sel_context(), Pat::sel_pattern()) -> [{Key, Pid, Value}]

Perform a select operation with limited context on the process registry

The physical representation in the registry may differ from the above, but the select patterns are transformed appropriately.

Note that limiting the context is just a convenience function, allowing you to write a simpler select pattern and still avoid searching the entire registry. Whenever variables are used in the head pattern, this will result in a wider scan, even if the values are restricted through a guard (e.g. select([{'$1','$2','$3'}, [{'==', {element,1,'$1'}, p}], ...]) will count as a wild pattern on the key and result in a full scan). In this case, specifying a Context will allow gproc to perform some variable substitution and ensure that the scan is limited.

select/3


select(Context::context(), Pat::sel_patten(), Limit::integer()) -> {[Match], Continuation} | $end_of_table

Like select/2 but returns Limit objects at a time.

See http://www.erlang.org/doc/man/ets.html#select-3.

select_count/1


select_count(Pat::sel_pattern()) -> [sel_object()]

Equivalent to select_count(all, Pat).

select_count/2


select_count(Context::context(), Pat::sel_pattern()) -> [{Key, Pid, Value}]

Perform a select_count operation on the process registry.

The physical representation in the registry may differ from the above, but the select patterns are transformed appropriately.

send/2


send(Key::process() | key(), Msg::any()) -> Msg

Sends a message to the process, or processes, corresponding to Key.

If Key belongs to a unique object (name or aggregated counter), this function will send a message to the corresponding process, or fail if there is no such process. If Key is for a non-unique object type (counter or property), Msg will be send to all processes that have such an object.

Key can also be anything that the erlang:send/2, or '!' operator accepts as a process identifier, namely a pid(), an atom(), or {Name::atom(), Node::atom()}.

set_attributes/2


set_attributes(Key::key(), Props::[{atom(), any()}]) -> true

Add/modify {Key, Value} attributes associated with a registration.

Gproc registration objects can have {Key, Value} attributes associated with them. These are stored in a way that doesn't affect the cost of name lookup.

Attributes can be retrieved using gproc:get_attribute/3 or gproc:get_attributes/2.

set_attributes_shared/2


set_attributes_shared(Key::key(), Props::[{K, V}]) -> true

Add/modify {Key, Value} attributes associated with a shared registration.

Gproc registration objects can have {Key, Value} attributes associated with them. These are stored in a way that doesn't affect the cost of name lookup.

Attributes can be retrieved using gproc:get_attribute/3 or gproc:get_attributes/2.

set_env/5


set_env(Scope::scope(), App::atom(), Key::atom(), Value::term(), Strategy) -> Value
  • Strategy = [Alternative]
  • Alternative = app_env | os_env | {os_env, VAR} | {mnesia, ActivityType, Oid, Pos}

Updates the cached value as well as underlying environment.

This function should be exercised with caution, as it affects the larger environment outside gproc. This function modifies the cached value, and then proceeds to update the underlying environment (OS environment variable or application environment variable).

When the mnesia alternative is used, gproc will try to update any existing object, changing only the Pos position. If no such object exists, it will create a new object, setting any other attributes (except Pos and the key) to undefined.

set_value/2


set_value(Key::key(), Value) -> true

Sets the value of the registration given by Key

Key is assumed to exist and belong to the calling process. If it doesn't, this function will exit.

Value can be any term, unless the object is a counter, in which case it must be an integer.

set_value_remote/3

set_value_remote(Node, Key, Value) -> any()

set_value_shared/2


set_value_shared(Key::key(), Value) -> true

Sets the value of the shared registration given by Key

Key is assumed to exist as a shared entity. If it doesn't, this function will exit.

Value can be any term, unless the object is a counter, in which case it must be an integer.

start_link/0


start_link() -> {ok, pid()}

Starts the gproc server.

This function is intended to be called from gproc_sup, as part of starting the gproc application.

table/0


table() -> any()

Equivalent to table({all, all}).

table/1


table(Context::context()) -> any()

Equivalent to table(Context, []).

table/2


table(Context::context(), Opts) -> any()

QLC table generator for the gproc registry. Context specifies which subset of the registry should be queried. See http://www.erlang.org/doc/man/qlc.html.

NOTE: By default, the gproc table generator will not filter out entries belonging to processes that have just died, but which have yet to be cleared out of the registry. Use the option check_pids (or {check_pids, true}) if you want to filter out dead entries already in the query. There will be some overhead associated with doing so, and given that the process monitoring is asynchronous, there can never be any guarantee that there are no dead entries in the list by the time your program processes it.

unreg/1


unreg(Key::key()) -> true

Unregister a name or property.

unreg_other/2


unreg_other(Key::key(), Pid::pid()) -> true

Unregister a name registered to another process.

This function is equivalent to unreg/1, but specifies another process as the holder of the registration. An exception is raised if the name or property is not registered to the given process.

unreg_remote/2

unreg_remote(Node, Key) -> any()

unreg_shared/1


unreg_shared(Key::key()) -> true

Unregister a shared resource.

unregister_name/1

unregister_name(Key) -> any()

Equivalent to unreg / 1.

update_counter/2


update_counter(Key::key(), Incr::increment()) -> integer() | [integer()]

Updates the counter registered as Key for the current process.

This function works almost exactly like ets:update_counter/3 (see http://www.erlang.org/doc/man/ets.html#update_counter-3), but will fail if the type of object referred to by Key is not a counter or a unique name (update_counter/2 can be performed on names as well, but they do not count as counter objects, and do not affect aggregated counters).

Aggregated counters with the same name will be updated automatically. The UpdateOp patterns are the same as for ets:update_counter/3, except that the position is omitted; in gproc, the value position is always 3.

If Key refers to a unique name, the operation will depend on the value part of the registration being an integer(). While non-integer values are not permitted at all for counter objects, it is the user's responsibility to ensure that a name, on which update_counter/2 is to be performed, has the appropriate value type.

update_counter/3

update_counter(Key, Pid, Incr) -> any()

update_counter_remote/3

update_counter_remote(Node, Key, Incr) -> any()

update_counters/2


update_counters(X1::scope(), Cs::[{key(), pid(), increment()}]) -> [{key(), pid(), integer()}]

Update a list of counters

This function is not atomic, except (in a sense) for global counters. For local counters, it is more of a convenience function. For global counters, it is much more efficient than calling gproc:update_counter/2 for each individual counter.

The return value is the corresponding list of [{Counter, Pid, NewValue}].

update_shared_counter/2


update_shared_counter(Key::key(), Incr) -> integer() | [integer()]
  • Incr = IncrVal | UpdateOp | [UpdateOp]
  • UpdateOp = IncrVal | {IncrVal, Threshold, SetValue}
  • IncrVal = integer()

Updates the shared counter registered as Key.

This function works almost exactly like ets:update_counter/3 (see http://www.erlang.org/doc/man/ets.html#update_counter-3), but will fail if the type of object referred to by Key is not a counter.

Aggregated counters with the same name will be updated automatically. The UpdateOp patterns are the same as for ets:update_counter/3, except that the position is omitted; in gproc, the value position is always 3.

where/1


where(Key::key()) -> pid() | undefined

Returns the pid registered as Key

The type of registration must be either name or aggregated counter. Otherwise this function will raise a badarg exception. Use lookup_pids/1 in these cases.

whereis_name/1

whereis_name(Key) -> any()

Equivalent to where / 1.

wide_await/3


wide_await(Nodes::[node()], Key::key(), Timeout) -> {pid(), Value}
  • Timeout = integer() | infinity

Wait for a local name to be registered on any of Nodes. This function works rather like await/2, but queries all nodes in the Nodes list at the same time. The first node to respond with a process registered as Key will provide the result. Other results are ignored. Key must be a unique name with local scope, i.e. {n,l,Name}.

An exception is thrown upon timeout, or if no node can be reached (if gproc is not running on a given node, this is treated the same as the node being down).