Stuff Goes Bad:Erlang In Anger


Similarly to processes, Erlang ports allow a lot of introspection. The info can be accessed by calling erlang:port_info(Port, Key) , and more info is available through the inet module. Most of it has been regrouped by the recon:port_info/1-2 functions, which work using a somewhat similar interface to their process-related counterparts.


id internal index of a port. Of no particular use except to differentiate ports.
name type of the port — with names such as "tcp_inet", "udp_inet", or "efile", for example.
os_pid if the port is not an inet socket, but rather represents an external process or program, this value contains the os pid related to the said external program.

id : 端口的内部索引。除了用于区分端口外没有其它特殊用途。
name: 端口的类型--比如:可以是"tcp_inet","upd_inet"或"efile"。
os_pid: 如果端口不是一个inet socket,而是代表一个外部进程或程序,这个值就是来表示他是一个外部程序的os pid。

connected Each port has a controlling process in charge of it, and this process’ pid is the connected one.
links ports can be linked with processes, much like other processes can be. The list of linked processes is contained here. Unless the process has been owned by or manually linked to a lot of processes, this should be safe to use.
monitors ports that represent external programs can have these programs end up monitoring Erlang processes. These processes are listed here.

connected: 每个端口都被一个控制进程所负责,这个就是控制进程的pid。
links: 端口可以link到进程,和其它进程一样的。返回它link的进程列表。在进程linked了很多进程时调用是不安全的。

input the number of bytes read from the port.
output the number of bytes written to the port.

input: 从端口读取的数据大小(bytes)。
output: 写入端口的数据大小(bytes)。

Memory Used
memory this is the memory (in bytes) allocated by the runtime system for the port. This number tends to be small-ish and excludes space allocated by the port itself.  queue_size Port programs have a specific queue, called the driver queue 24. This return the size of this queue, in bytes.

Memory Used
memory : 运行时Erlang系统为端口分配的内存大小(bytes)。这个值往往会小于实际值,它忽略了端口自身的分配空间。
queue_size: 端口程序有一个特定的队列:叫做dirver queue24。返回这个队列的大小(bytes)。

Inet Ports Returns inet-specific data, including statistics 25, the local address and port number for the socket (sockname), and the inet options used 26.
Others currently no other form than inet ports are supported in recon, and an empty list is returned.

Inet Ports: 返回inet-specific数据。包括statistics25:本地地址,sockname的端口数,和inet的使用的选项26

The list can be obtained as follows:


1> recon:port_info("#Port<0.818>").
 On top of this, functions to find out specific problematic ports exist the way they do for processes. The gotcha is that so far, recon only supports them for inet ports and with restricted attributes: the number of octets (bytes) sent, received, or both (send_oct, recv_oct, oct, respectively), or the number of packets sent, received, or both (send_cnt, recv_cnt, cnt, respectively).
 So for the cumulative total, which can help find out who is slowly but surely eating up all your bandwidth:

 除此之外,函数可以找到具体存在问题的端口。目前为止,recon 只支持inet 端口的下面属性:octets发送接收的数据大小(bytes)(send_oct, recv_oct, oct),或packets发送接收的数据大小(send_cnt, recv_cnt, cnt)。

2> recon:inet_count(oct, 3).
 Which suggest some ports are doing only input and eating lots of bytes. You can then use recon:port_info("#Port<0.6821166>") to dig in and find who owns that socket, and what is going on with it.
 Or in any other case, we can look at what is sending the most data within any time window 27 with the recon:inet_window(Attribute, Count, Milliseconds) function:

 或者其它情况,我们可以使用窗口27全程查看数据的流向: recon:inet_window(Attribute, Count, Milliseconds)

3> recon:inet_window(send_oct, 3, 5000).
 For this one, the value in the middle of the tuple is what send_oct was worth (or any chosen attribute for each call) during the specific time interval chosen (5 seconds here).
 There is still some manual work involved into properly linking a misbehaving port to a process (and then possibly to a specific user or customer), but all the tools are in place.


[24] The driver queue is available to queue output from the emulator to the driver (data from the driver to the emulator is queued by the emulator in normal Erlang message queues). This can be useful if the driver has to wait for slow devices etc, and wants to yield back to the emulator.
[27] See the explanations for the recon:proc_window/3 in the preceding subsection

[注24]:driver queue在从模拟器(emulator)输出到dirver的数据时有用,数据从dirver到模拟器的队列使用的是正常的Erlang消息队列。如果dirver处理数据快一些时,它就会屈服(yield back)于模拟器。