跟踪函数调用的基本步骤是在非活动节点上:
> dbg:start(). % start dbg
> dbg:tracer(). % start a simple tracer process
> dbg:tp(Module, Function, Arity, []). % specify MFA you are interested in
> dbg:p(all, c). % trace calls (c) of that MFA for all processes.
... trace here
> dbg:stop_clear(). % stop tracer and clear effect of tp and p calls.
您可以同时跟踪多个功能。通过为每个函数调用 tp 添加函数。如果要跟踪未导出的函数,则需要调用tpl。要删除函数,请以类似方式调用ctp 或ctpl。一些通用的 tp 调用是:
> dbg:tpl(Module, '_', []). % all calls in Module
> dbg:tpl(Module, Function, '_', []). % all calls to Module:Function with any arity.
> dbg:tpl(Module, Function, Arity, []). % all calls to Module:Function/Arity.
> dbg:tpl(M, F, A, [{'_', [], [{return_trace}]}]). % same as before, but also show return value.
最后一个参数是一个匹配规范。你可以使用dbg:fun2ms来玩弄它。
您可以通过调用 p() 来选择要跟踪的进程。这些项目在 erlang:trace 下进行了描述。一些调用是:
> dbg:p(all, c). % trace calls to selected functions by all functions
> dbg:p(new, c). % trace calls by processes spawned from now on
> dbg:p(Pid, c). % trace calls by given process
> dbg:p(Pid, [c, m]). % trace calls and messages of a given process
我猜你永远不需要直接调用erlang:trace,因为dbg 几乎可以为你做所有事情。
活动节点的黄金法则是只向 shell 生成一定量的跟踪输出,这样您就可以输入dbg:stop_clear().。 :)
我经常使用一个跟踪器,它会在发生一些事件后自动停止。例如:
dbg:tracer(process, {fun (_,100) -> dbg:stop_clear();
(Msg, N) -> io:format("~p~n", [Msg]), N+1 end, 0
}).
如果您要在远程节点(或多个节点)上进行调试,请搜索 pan、eper、inviso 或 onviso。