一种动态内存泄漏检测方法及系统与流程

文档序号:11519526阅读:328来源:国知局
一种动态内存泄漏检测方法及系统与流程

本发明属于计算机技术领域,具体涉及一种动态内存泄漏检测方法及系统。



背景技术:

在用c/c++语言开发程序时,常常使用动态内存分配技术。动态内存使用系统的堆空间,从而有效地利用了系统的内存资源。程序员在运行的时候用malloc、realloc、calloc或new申请任意多少的内存,然而,动态内存必须依赖程序员自己去调用内存释放函数free或delete显式的释放。由于程序员的疏忽,程序中非常容易出现内存泄漏的问题。

内存泄漏,是用动态存储分配函数动态开辟的空间,在使用完毕后未释放,导致一直占据该内存单元的现象。

在电力继电保护领域,由于后台监控服务和保护装置程序日益复杂,内存泄漏错误时常发生,短时间少量的内存泄漏容易被忽视。但由于继电保护产品系统庞大性和运行周期长期性的特性,少量的内存泄漏积累到一定的程度有可能导致继电保护产品死机甚至系统崩溃,这样将导致变电站无法正常运行从而导致巨大的经济损失。而且,使用常规的调试手段很难远程实时定位正在运行大型系统的内存泄漏出现的具体位置。

《信息技术》2007年第9期中出版的《一种linux下动态内存泄漏检测技术的实现》中介绍了一种基于动态代码插装技术的内存泄漏检测器的实现方法,程序整体框架由三部分组成:内存检测模块、注射器和报告进程。内存检测模块实现使用跟踪和泄漏检测;注射器对目标进程进行动态代码插装,并在内存泄漏发生时刻向报告进程发送消息;报告进程用于产生最终报告。该方法只能在本地进行检测,并且使用的ptrace读写内存方式是会影响系统性能的方式,可扩展性不强,无法通过工具端来远程控制内存泄漏检测,并以代理服务端无损害的读写被监视进程内存信息。



技术实现要素:

本发明的目的在于提供一种动态内存泄漏检测方法及系统,用以解决现有技术中无法无损地对内存泄漏情况进行检测的问题。

为解决上述技术问题,本发明的技术方案为:

本发明的一种动态内存泄漏检测方法,包括如下步骤:

1)工具端启动内存监视系统,向系统中的代理服务端发送读写内存命令;

2)被监视进程调用接口动态库中的三个接口函数来接入系统,实现代理服务端通过共享内存和消息队列与被监视进程交互;所述三个接口函数为:注册接口函数、启动服务接口函数和注销接口函数;

3)工具端将动态链接库中的内存监视模块挂接到被监视进程地址空间中,获取被监视进程的内存操作信息。

进一步的,工具端通过修改被监视进程的plt过程连接表的内存管理条目,将动态链接库中的内存监视模块插入被监视进程,将被监视进程的内存管理函数替换为所述内存监视模块的内存管理函数,执行所述内存监视模块的内存管理函数,获取被监视进程的内存操作信息;所述内存监视模块的内存管理函数包括内存分配函数和内存释放函数。

进一步的,工具端通过udp协议与代理服务端交互。

进一步的,还包括工具端在获取内存操作信息后,处理内存操作信息并判断内存泄漏情况的步骤:判断节点信息是分配内存还是释放内存,若是分配内存,则根据节点信息中分配长度来设置节点内存泄漏总差值和总字节数,并将节点信息放入全局链表中;若是释放内存,则在全局链表中查找有无此节点信息后,判断节点是否溢出,若无溢出,则删除链表中的节点,并根据全局链表中查询到的节点信息的内存释放长度设置节点内存泄漏总差值和总字节数。

进一步的,还包括在判断为分配内存、并根据节点信息中分配长度设置节点内存泄漏总差值和总字节数后,根据节点信息中新的分配函数的调用堆栈信息计算md5码,并根据md5码、thread_id、信息地址和result变量来定位被监测进程中内存泄漏位置的步骤。

本发明的一种动态内存泄漏检测系统,包括工具端和linux系统,所述linux系统包括代理服务端和接口动态库;

所述工具端用于启动内存监视系统,向系统中的代理服务端发送读写内存命令;并将动态链接库中的内存监视模块挂接到被监视进程地址空间中,获取被监视进程的内存操作信息;

所述代理服务端用于通过共享内存和消息队列与被监视进程交互;

所述接口动态库用于提供三个接口函数来使被监视进程接入系统;所述三个接口函数为:注册接口函数、启动服务接口函数和注销接口函数。

进一步的,工具端通过修改被监视进程的plt过程连接表的内存管理条目,将动态链接库中的内存监视模块插入被监视进程,将被监视进程的内存管理函数替换为所述内存监视模块的内存管理函数,执行所述内存监视模块的内存管理函数,获取被监视进程的内存操作信息;所述内存监视模块的内存管理函数包括内存分配函数和内存释放函数。

进一步的,工具端通过udp协议与代理服务端交互。

进一步的,所述工具端还用于在获取内存操作信息后,处理内存操作信息并判断内存泄漏情况:判断节点信息是分配内存还是释放内存,若是分配内存,则根据节点信息中此次分配长度来设置节点内存泄漏总差值和总字节数,并将节点信息放入全局链表中;若是释放内存,则在全局链表中查找有无此节点信息后,判断节点是否溢出,若无溢出,则删除链表中的节点,并根据全局链表中查询到的节点信息的内存释放长度设置节点内存泄漏总差值和总字节数。

进一步的,所述工具端还用于在判断为分配内存、并根据节点信息中分配长度来设置节点内存泄漏总差值和总字节数后,根据节点信息中新的分配函数的调用堆栈信息计算md5码,并根据md5码、thread_id、信息地址和result变量来定位被监测进程中内存泄漏位置。

本发明的有益效果:

本发明的动态内存泄漏检测方法及系统,工具端动态的把“动态链接库”中的内存监视模块挂接到被监视进程的地址空间中,从而让被监视进程自身具有内存泄漏检测功能,内存监视模块记录内存的操作行为,并将这些消息放入到消息队列中,发送给代理服务端,代理服务端将消息队列中的内存信息进行统一管理,发送给工具端。本发明可以在不中断目标进程的情况下实时监视进程空间中内存泄漏情况,实现了真正的在线监测;能够通过工具端来远程控制内存泄漏检测,并以代理服务端无损害的读写被监视进程内存信息,对定位内存错误、诊断问题最有非常实用的价值,适用于linux系统c/c++程序、电力系统程序等不同场景。

附图说明

图1是本发明的总体结构图;

图2是本发明的实体原理图;

图3是本发明的整体框架图;

图4是本发明的内存信息链表管理流程图;

图5是本发明的结果显示波形图。

具体实施方式

为使本发明的目的、技术方案及优点更加清楚,下面结合附图及实施例,对本发明作进一步的详细说明,但本发明的实施方式并不局限于此。

本发明的动态内存泄漏检测系统实施例:

如图1所示,本发明的动态内存泄漏检测系统包括三层结构:工具端、代理服务端和被监视进程。三者相互协作,通过动态探针技术,将“动态链接库”中的内存监视模块挂接到被监视进程的地址空间,并将内存监视模块收集的内存管理信息实时的显示到工具端。其中,内存监视模块为测试人员开发编写的代码,包括自定义的内存分配函数(new_malloc)、(new_realloc)、(new_calloc)和内存释放函数(new_free)。

该系统在实现内存泄漏检测方法时,本质上采用的是程序插装的方法。程序插装是软件开发和测试中的一种基本方法,插装的目的是获取程序执行中的动态信息。程序插装技术的插装过程是静态的,而信息收集过程是动态的,是联系静态分析与动态信息的关键纽带。下面具体说明该三层结构的具体功能及实现方法。

工具端运行在windows平台下,用于分析被监视进程,动态的把“动态链接库”中的内存监视模块挂接到被监视进程的地址空间中,对被监视进程中的内存操作函数进行拦截,插入被监视进程的代码中,从而截获相关内存管理函数的控制权,让被监视进程自身具有内存泄漏检测功能。同时,工具端定时接收内存监视模块收集到的信息并通过一定的形式显示出来,供测试人员测试与分析,实现了对内存相关操作的监控和管理。

代理服务端运行在linux系统下,为工具端读写被监视进程端内存信息的中转服务程序,代理服务端通过udp协议接收工具端发送过来的请求命令并放入共享内存和消息队列中,服务处理线程接收消息队列发送过来的信息定位共享内存中的命令队列索引,并处理共享内存中代理服务本进程命令和被监视进程中回复的命令,最后通过udp协议发送给工具端。

被监视进程在通过调用“接口动态库”中提供的三个接口函数来接入系统,从而实现代理服务端通过共享内存和消息队列与被监视进程交互。这三个接口函数为:注册接口函数、启动服务接口函数、注销接口函数。注册接口函数用于初始化共享内存和消息队列;启动服务接口函数用于注册进程列表和处理代理服务发送到共享内存和消息队列中的命令;注销接口函数用于结束进程、删除消息队列和共享内存。启动服务接口函数处理代理进程放入共享内存中被监视进程的命令,并将处理结果通过消息队列发送给代理服务处理线程,进行统一处理。

工具端通过udp服务发送命令给代理服务端。代理服务端通过共享内存和消息队列与被监视进程进行通信,被监视进程通过调用“接口动态库”中提供的三个接口函数接入系统,进行数据处理。

如图2所示,主程序以及所有的动态链接库(.so)文件都有自己的plt表。plt表的作用是将重定位的地方移到plt表中,使得代码段不用重定位,从而实现动态库代码段的共享。通过分析并修改所有模块plt表的相应条目,就可以实现api拦截,实现我们自己特定的功能。利用plt表拦截了malloc、realloc、calloc和free函数,使得所有调用malloc、realloc、calloc和free的地方,都执行到了我们自定义的new_malloc、new_realloc、new_calloc和new_free函数,这样我们就可以收集malloc、realloc、calloc和free的相关信息了。

下面具体介绍该系统的具体实现过程。

如图3所示,工具端分析被监视进程,动态插入“动态链接库”中的内存监视模块,对被监视进程中内存操作函数进行拦截。内存监视模块收集内存管理函数信息,通过消息队列发送数据到代理服务进程,代理服务进程获取消息队列中内存相关操作信息并通过udp协议发送给工具端。工具端将接收到udp报文解析到内存信息结构体中,经过统一的内存管理模块处理,将被监视进程中内存信息情况实时的显示到波形图中和导出到.txt文件中,帮助精确定位内存错误信息。

本发明的内存信息链表管理流程图如图4所示,工具端将接收到的udp报文解析成内存信息结构体,判断节点信息是分配内存还是释放内存:

如果是释放内存,判断链表中是否有此地址的节点信息,如果没有此节点信息则退出查找,重新获取节点;如果链表中有此地址的节点信息,获取节点信息,判断其节点信息是否溢出:如果溢出,应将此溢出节点中溢出标志位置1,存放在链表中;如果没有溢出删除链表中节点信息并根据malloc、realloc、calloc及free函数中的分配及释放内存的信息的差值来设置节点结构体中内存泄漏总差值和总字节数。

如果是分配内存,则根据malloc、realloc、calloc函数中的分配内存信息情况将此节点信息放入到链表中并设置节点结构体中内存泄漏总差值和总字节数。同时,通过节点信息中函数调用堆栈数组计算md5码,综合md5码,thread_id,内存分配地址和内存管理标识来设置节点颜色。最后通过定时控件,每隔一秒将链表信息显示到波形图上。同时也可以导出链表信息到.txt文件中,以供分析、精确定位错误信息。

本发明的结果波形图如图5所示,图形中上边的曲线代表内存泄漏总字节数,下边的曲线代表内存泄漏总差值。当工具端加载被监视进程符号文件连接到服务器后,点击启动监视后,就能将被监视进程中内存泄漏情况实时显示到界面上,界面下方同时会显示内存泄漏的差值和内存泄漏总的字节数。为便于分析,界面同时提供了内存泄漏函数调用堆栈导出功能,为之后分析被监视进程内存错误操作提供了重要依据。

整体来说,只需将环境部署到linux系统服务器上,被监视进程调用“接口动态库”中提供的三个接口函数,就可以通过linux装置调试分析工具端,加载符号文件,在不中断linux系统进程运行的情况下实时监视进程的内存分配情况,并通过波形图显示出来。

本发明的动态内存泄漏检测方法实施例:

上述介绍了本发明的动态内存泄漏检测系统,其实质在于提供了一种动态内存泄漏检测方法,包括如下步骤:

1)工具端启动内存监视系统,向系统中的代理服务端发送读写内存命令;

2)被监视进程调用接口动态库中的三个接口函数来接入系统,实现代理服务端通过共享内存和消息队列与被监视进程交互;所述三个接口函数为:注册接口函数、启动服务接口函数和注销接口函数;

3)工具端将动态链接库中的内存监视模块挂接到被监视进程地址空间中,获取被监视进程的内存操作信息。

该系统是对上述方法的一种具体实现,基于该系统实现的动态内存泄漏检测方法在对上述动态内存泄漏检测系统的介绍中已做详细说明,故对该方法不再详细介绍。

尽管本发明的内容已经通过上述优选实施例作了详细介绍,但应当认识到上述的描述不应被认为是对本发明的限制。在本领域技术人员阅读了上述内容后,对于本发明的多种修改和替代都将是显而易见的。因此,本发明的保护范围应由所附的权利要求来限定。

当前第1页1 2 
网友询问留言 已有0条留言
  • 还没有人留言评论。精彩留言会获得点赞!
1