2012-04-18 72 views
4

我正在这个相对较大的代码库中工作,我看到文件描述符泄漏,并且进程开始抱怨他们在运行某些程序后无法打开文件。调试文件描述符泄漏(在内核?)

虽然后6天出现这种情况,我可以通过在/ proc/SYS/FS /文件的最大减少值重现该问题在3-4小时为9000

有运行多个进程任何时候。我已经能够指出几个可能导致泄漏的过程。但是,我没有看到任何文件描述符通过lsof或通过/ proc // fd泄漏。

如果我杀死了我怀疑泄漏的进程(它们相互通信),泄漏消失了。 FD被释放。

cat/proc/sys/fs/file-nr在while(1)循环中显示泄漏。但是,在任何过程中我都看不到任何泄漏。

这里是一个脚本,我写来检测泄漏发生的事情:

#!/bin/bash 

if [ "$#" != "2" ];then 
    name=`basename $0` 
    echo "Usage : $name <threshold for number of pids> <check_interval>" 
    exit 1 
fi 


fd_threshold=$1 
check_interval=$2 
total_num_desc=0 
touch pid_monitor.txt 
nowdate=`date` 
echo "=================================================================================================================================" >> pid_monitor.txt 
echo "****************************************MONITORING STARTS AT $nowdate***************************************************" >> pid_monitor.txt 

while [ 1 ] 
do 
    for x in `ps -ef | awk '{ print $2 }'` 
    do 
     if [ "$x" != "PID" ];then 
      num_fd=`ls -l /proc/$x/fd 2>/dev/null | wc -l` 
      pname=`cat /proc/$x/cmdline 2> /dev/null` 
      total_num_desc=`expr $total_num_desc + $num_fd` 
      if [ $num_fd -gt $fd_threshold ]; then 
       echo "Proces name $pname($x) and number of open descriptor = $num_fd" >> pid_monitor.txt 
      fi 
     fi 
    done 
    total_nr_desc=`cat /proc/sys/fs/file-nr` 
    lsof_desc=`lsof | wc -l` 
    nowdate=`date` 
    echo "$nowdate : Total number of open file descriptor = $total_num_desc lsof desc: = $lsof_desc file-nr descriptor = $total_nr_desc" >> pid_monitor.txt 
    total_num_desc=0 
    sleep $2 
done 

./monitor.fd.sh 500 2 & 尾-f pid_monitor.txt

正如我前面提到的,我没有在/ proc // fd中看到任何漏洞,但是漏洞确实发生,并且系统耗尽了文件描述符。

我怀疑内核中有东西在泄漏。 Linux内核版本2.6.23。

我的问题如下:

  1. 意志 'LS的/ proc // FD' 节目列表描述符与过程采用PID任何库。如果不是,我该如何确定何时在我链接到的库中有泄漏。

  2. 如何确认泄漏是在用户空间还是在内核中。

  3. 如果泄漏在内核中,我可以使用哪些工具进行调试?

  4. 您可以给我的任何其他提示。

感谢您耐心解决问题。

真的很感激任何帮助。

+0

是的,它会显示所有的描述,包括那些来自链接库。 2.内核中的fd泄漏是不太可能的。 3.看2. 4.这个问题很不清楚,你能提供更多的细节吗?哪个系统调用失败,出现什么错误? – strkol 2012-04-22 10:59:24

回答

0

哪些进程开始抱怨?你看到的错误是什么?监控脚本的输出是什么?

要打开文件,您需要两件事情,一个文件描述符和一个struct file或文件描述。文件描述符是用户空间使用的内容,它在内核中用于查找struct file。我不清楚你在泄漏什么。

0

找到了解决问题的办法。

在某些函数中发生共享内存附加,并且该函数每30秒调用一次。共享内存连接永远不会被分离,因此描述符泄漏。我猜/ proc // fd不显示共享内存附加作为描述符。因此我的脚本无法缓存哪个进程正在泄漏描述符。