检查Linux中给定进程的打开FD限制

我最近有一个“泄露”文件描述符的Linux进程:它打开了它们,并没有正确closures其中的一些。

如果我监控了这一点,我可以提前告诉我们这个过程已经到了极限。

有没有一个很好的,Bash \ Python的方式来检查一个Ubuntu Linux系统中给定进程的FD使用率?

编辑:

我现在知道如何检查有多less个打开的文件描述符。 我只需要知道一个进程允许多less个文件描述符 。 某些系统(如Amazon EC2)没有/proc/pid/limits文件。

谢谢,

乌迪

计算/proc/<pid>/fd/的条目。 适用于该过程的硬限制和软限制可以在/proc/<pid>/limits

Linux内核为获得资源限制提供的唯一接口是getrlimit()/proc/ pid /limitsgetrlimit()只能获取调用进程的资源限制。 /proc/ pid /limits允许你获得具有相同用户ID的任何进程的资源限制,可以在RHEL 5.2,RHEL 4.7,Ubuntu 9.04以及任何具有2.6.24或更高版本内核的发行版上使用。

如果您需要支持较旧的Linux系统,那么您将必须让进程本身调用getrlimit() 。 当然,最简单的方法是修改程序或者它使用的库。 如果你正在运行程序,那么你可以使用LD_PRELOAD将你自己的代码加载到程序中。 如果这些都不可能,那么你可以使用gdb附加到进程,并让它在进程内执行调用。 你也可以用ptrace()自己做同样的事情来附加进程,将调用插入到内存中,但是这样做很复杂,不适合正确使用。

有了适当的权限,其他的方法可以通过内核内存,加载内核模块,或者修改内核来实现,但是我认为这是不可能的。

您可以尝试编写定期在给定lsof -p {PID}上调用lsof -p {PID}脚本。

你问了bash / python方法。 ulimit将是最好的bash方式(通过/proc/$pid/fd之类的手工来完成)。 对于python,你可以使用资源模块。

 import resource print(resource.getrlimit(resource.RLIMIT_NOFILE)) 
 $ python test.py (1024, 65536) 

resource.getrlimit对应于C程序中的getrlimit调用。 结果表示请求资源的当前值和最大值。 在上面的示例中,当前(软)限制是1024.这些值是Linux系统上的典型默认值。

使用进程查看前20个文件句柄:

 for x in `ps -eF| awk '{ print $2 }'`;do echo `ls /proc/$x/fd 2> /dev/null | wc -l` $x `cat /proc/$x/cmdline 2> /dev/null`;done | sort -n -r | head -n 20 

输出格式为文件句柄计数,pid,cmndline为进程

示例输出

 701 1216 /sbin/rsyslogd-n-c5 169 11835 postgres: spaceuser spaceschema [local] idle 164 13621 postgres: spaceuser spaceschema [local] idle 161 13622 postgres: spaceuser spaceschema [local] idle 161 13618 postgres: spaceuser spaceschema [local] idle 

在CentOS 6及以下版本(使用GCC 3的任何内容)中,您可能会发现调整内核限制并不能解决问题。 这是因为有一个在GCC使用的编译时设置的FD_SETSIZE值。 为此,您需要增加该值,然后重新编译该过程。

此外,如果您正在使用该库,则可能由于libpthread中的已知问题而发现正在泄漏文件描述符。 这个调用已经集成到GCC 4 / CentOS7 / RHEL 7中,这似乎已经解决了线程问题。