global
global
模块
global
模块摘要
全球名称注册设施。
描述
该模块由以下服务组成:
- 注册全局名称
- 全局锁
- 维护完全连接的网络
这些服务通过global_name_server
每个节点上存在的进程进行控制。全局
名称服务器在节点启动时自动启动。术语全局
意味着通过由许多Erlang节点组成的系统。
在分布式Erlang系统编程中,全局注册名称是一个中心概念。在这个模块中,提供了等价的register/2
和whereis/1
BIF(用于本地名称注册),但是用于Erlang节点的网络。注册名称是进程标识符(pid)的别名。全局名称服务器监视全局注册的pid。如果进程终止,则该名称也是全局未注册的。
注册名称存储在每个节点上的副本全局名称表中。没有中央储存点。因此,将名称翻译为pid是很快的,因为它始终在本地完成。对于导致全局名称表更改的任何操作,其他节点上的所有表都会自动更新。
全局锁具有锁定标识并设置在特定资源上。例如,指定的资源可以是一个pid。当设置全局锁定时,对锁定请求者以外的所有资源都将拒绝对锁定资源的访问。
注册和锁定服务都是原子的。涉及这些操作的所有节点都具有相同的信息视图。
全球名称服务器还执行连续监视节点配置更改的关键任务。如果运行全局注册进程的节点关闭,则该名称将全局注销。为此,全局名称服务器订阅nodeup
并nodedown
从模块发送消息net_kernel
。在这方面相关的内核应用程序变量为net_setuptime
,net_ticktime
和dist_auto_connect
。另见kernel(6)
。
名称服务器还维护完全连接的网络。例如,如果节点N1
连接到节点N2
(其已经连接到N3
),则节点上的全球名称服务器N1
和N3
确保也N1
和N3
被连接。如果不需要,-connect_all false
可以使用命令行标志(另请参阅erl(1)
)。在这种情况下,名称注册服务不能使用,但锁定机制仍然有效。
如果全局名称服务器无法连接节点(N1
和N3
在本例中),警告事件被发送到错误日志。这种事件的出现并不排除节点以后要连接(例如,你可以尝试rpc:call(N1, net_adm, ping, [N2])
在Erlang shell中执行命令),但它表示网络问题。
注
如果完全连接的网络设置不正确,请尝试先增加值net_setuptime
。
数据类型
id() = {ResourceId :: term(), LockRequesterId :: term()}
出口
del_lock(Id) -> true
del_lock(Id, Nodes) -> true
类型
删除锁Id
同步。
notify_all_name(Name, Pid1, Pid2) -> none
类型
可作为一个名称解析功能register_name/3
和re_register_name/3
。
该函数取消注册这两个pid并将消息发送{global_name_conflict, Name, OtherPid}
到两个进程。
random_exit_name(Name, Pid1, Pid2) -> pid()
类型
可作为一个名称解析功能register_name/3
和re_register_name/3
。
该功能随机选择一个pid进行注册并杀死另一个pid。
random_notify_name(Name, Pid1, Pid2) -> pid()
类型
可作为一个名称解析功能register_name/3
和re_register_name/3
。
该函数随机选择一个pid进行注册,并将消息发送{global_name_conflict, Name}
给其他pid。
re_register_name(Name, Pid) -> yes
re_register_name(Name, Pid, Resolve) -> yes
类型
{`Module`, `Function`} is also allowed.
原子上更改Name
所有节点上的注册名称以供参考Pid
。
函数Resolve
具有与在中相同的行为register_name/2,3
。
register_name(Name, Pid) -> yes | no
register_name(Name, Pid, Resolve) -> yes | no
类型
{`Module`,`Function`}也允许向后兼容,但不推荐使用它。
在全局范围内,将名称Name
与pid 相关联,即全局通知Erlang节点网络中所有节点的新全局名称。
当新节点添加到网络中时,会通知他们已存在的全局注册名称。网络还会通知新连接的节点中的全局名称。如果发现任何名称冲突,Resolve
则调用函数。其目的是决定哪个pid是正确的。如果函数崩溃,或者返回除某个pid之外的任何内容,则该名称将被取消注册。每个名称冲突都会调用一次该函数。
警告
如果您打算在不重新启动系统的情况下更改代码,则必须使用外部fun(fun Module:Function/Arity
)作为函数Resolve
。如果您使用本地乐趣,则永远无法替换该乐趣所属模块的代码。
三个预定义的决心功能存在:random_exit_name/3
,random_notify_name/3
,和notify_all_name/3
。如果没有Resolve
定义功能,random_exit_name
则使用。这意味着两个注册过程中的一个被选择为正确,另一个被杀死。
这个函数是完全同步的,也就是说,当这个函数返回时,这个名字可以在所有节点上注册,也可以不注册。
如果成功,该函数返回yes
,如果失败。例如,no
如果尝试注册已注册的进程或注册名称已被使用的进程,则返回no
。
注
直到并包括Erlang/OTP R10的版本不检查进程是否已经注册。全球名称表可能因此变得不一致。旧的(童车)行为可以通过给内核应用程序变量被选择global_multi_name_action
的值allow
。
如果注册名称的进程死亡或节点关闭,则该名称在所有节点上都未注册。
registered_names() -> Name
类型
返回所有全局注册名称的列表。
send(Name, Msg) -> Pid
类型
将消息发送Msg
到全局注册为pid的pid Name
。
如果Name
不是全球注册的名称,则调用功能将随着原因退出{badarg, {Name, Msg}}
。
set_lock(Id) -> boolean()
set_lock(Id, Nodes) -> boolean()
set_lock(Id, Nodes, Retries) -> boolean()
类型
在指定节点上(或者如果没有指定任何节点,则在所有节点上)设置ResourceId
for 的锁定LockRequesterId
。如果ResourceId
另一个请求者的锁已经存在LockRequesterId
并且Retries
不等于0
,则该进程会休眠一段时间并尝试稍后执行该操作。当Retries
人们试图,false
则返回,否则true
。如果Retries
是infinity
,true
最终返回(除非锁从未释放)。
如果未Retries
指定值,infinity
则使用。
这个函数是完全同步的。
如果持有锁的进程死亡,或节点停止运行,则会删除该进程持有的锁。
全局名称服务器会跟踪共享同一个锁的所有进程,也就是说,如果两个进程设置了相同的锁,那么这两个进程都必须删除该锁。
这个函数没有解决死锁的问题。只要进程一次只锁定一个资源,就不会发生死锁。如果某些进程试图锁定两个或多个资源,则会发生死锁。由应用程序来检测并纠正死锁。
注
避免以下值ResourceId
,否则Erlang/OTP无法正常工作:
dist_ac
global
mnesia_adjust_log_writes
mnesia_table_lock
pg2
sync() -> ok | {error, Reason :: term()}
使全局名称服务器与此节点已知的所有节点同步。这些是从中返回的节点erlang:nodes()
。当此函数返回时,全局名称服务器将从所有节点接收全局信息。当新节点添加到网络中时,可以调用此功能。
唯一可能的错误原因Reason
是{"global_groups definition error", Error}
。
trans(Id, Fun) -> Res | aborted
trans(Id, Fun, Nodes) -> Res | aborted
trans(Id, Fun, Nodes, Retries) -> Res | aborted
类型
设置锁定Id
(使用set_lock/3
)。如果成功,Fun()
则评估并返回结果Res
。aborted
如果锁定尝试失败,则返回。如果Retries
设置为infinity
,交易不会中止。
infinity
是默认设置,并在没有指定值时使用Retries
。
unregister_name(Name) -> term()
类型
Name
从Erlang节点网络中删除全局注册的名称。
whereis_name(Name) -> pid() | undefined
类型
以全局注册名称返回pid Name
。如果名称未全局注册,则返回undefined
。
另见
global_group(3)
,net_kernel(3)