使用
erlang:trace/3
时,跟踪进程会收到“跟踪消息”,该消息讲述了被跟踪进程的情况。出于消息排序的目的(即保证固定发送者和接收者之间的消息按顺序传递(如果已传递)),谁是跟踪消息的发送者?
例如,如果被跟踪进程向
p1
发送消息,然后再向p2
发送消息,我是否可以保证跟踪进程将在p1
之前收到有关p2
的通知?
再举个例子,如果跟踪的进程如下所示
proc() ->
p1 ! ok,
receive X -> ok end,
p2 ! ok.
'receive'
跟踪消息是否始终恰好位于 send
到 p1
和 p2
之间?
我的另一个疑问是,如果同一个跟踪器跟踪更多进程怎么办:
proc1() ->
proc2 ! ok.
proc2() ->
receive ok -> ok end.
这里保证
proc1
在proc2
接收之前发送。我是否可以推断,如果我同时跟踪 proc1
和 proc2
,我会按照这个确切的顺序获知这些事件?
这篇文章可能看起来有很多问题,但共同点是我想知道我可以假设系统中事件的顺序与跟踪器观察的顺序之间的关系。我在文档中找不到任何提及此事的内容,但我可能以某种方式错过了它。
唯一的订购保证是针对单个流程的。您可以将其视为对于每个跟踪的进程,都有另一个进程向跟踪接收器发送跟踪消息。根据进程之间的锁冲突和其他调度细节,跟踪消息可能会以不可预测的顺序到达。然而,除了从同一进程接收的所有跟踪消息都是可预测的。
至于你的例子:
例如,如果被跟踪进程向p1发送消息,然后向p2发送消息,我是否可以保证跟踪进程会在p2之前收到有关p1的通知?
不,没有这样的保证。
再举个例子,如果跟踪的进程如下所示
proc() -> p1 ! ok, receive X -> ok end, p2 ! ok.
“接收”跟踪消息是否始终正好位于发送到 p1 和 p2 之间?
接收跟踪发生在邮件放入邮箱时,而不是邮件从邮箱中删除时。所以它保证在
p2 ! ok
之前,但也可能在 p1 ! ok
之前或之后。
我的另一个疑问是,如果同一个跟踪器跟踪更多进程会怎样:
proc1() -> proc2 ! ok. proc2() -> receive ok -> ok end.
这里保证 proc1 在 proc2 接收之前发送。我是否可以推断,如果我同时跟踪 proc1 和 proc2,我会按照这个确切的顺序获知这些事件?
不。接收跟踪消息可以在发送之前到达。在当前的实现中不太可能,但由于虚拟机内部不同的竞争条件,它可能会发生。
我在文档中找不到任何提及此事的内容,但我可能以某种方式错过了它。
我认为几年前我重新实现跟踪器实现时我已经更好地记录了这一点,但似乎连我都找不到它,所以它可能不存在。也许我应该花点时间把这一切写下来......