Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/68.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C 通过分叉减少内存泄漏_C_Linux_Memory_Resources_Posix - Fatal编程技术网

C 通过分叉减少内存泄漏

C 通过分叉减少内存泄漏,c,linux,memory,resources,posix,C,Linux,Memory,Resources,Posix,这真是个难看的问题 我有一个C++程序,它在循环中执行以下操作:< /P> 等待JMS消息 计算一些数据 发送JMS消息作为响应 我的程序(我们称之为“Bob”)内存泄漏相当严重。内存泄漏位于其他人编写的共享库中,我必须使用该库,但源代码我无权访问 该内存泄漏导致Bob在循环的“计算一些数据”阶段崩溃。这是一个问题,因为另一个程序正在等待Bob的响应,如果没有收到响应,它将非常不安 由于各种限制(是的,这是一个X/Y问题,我告诉过你这很难看),我决定我唯一可行的策略是修改Bob,使其在循环中

这真是个难看的问题

我有一个C++程序,它在循环中执行以下操作:< /P>
  • 等待JMS消息
  • 计算一些数据
  • 发送JMS消息作为响应
我的程序(我们称之为“Bob”)内存泄漏相当严重。内存泄漏位于其他人编写的共享库中,我必须使用该库,但源代码我无权访问

该内存泄漏导致Bob在循环的“计算一些数据”阶段崩溃。这是一个问题,因为另一个程序正在等待Bob的响应,如果没有收到响应,它将非常不安

由于各种限制(是的,这是一个X/Y问题,我告诉过你这很难看),我决定我唯一可行的策略是修改Bob,使其在循环中执行以下操作:

  • 等待JMS消息
  • 计算一些数据
  • 发送JMS消息作为响应
  • 检查是否存在使用“过多”内存的危险
  • 如果是这样,分叉并执行自身的另一个副本,然后优雅地退出
我的问题如下:


检测我们是否使用了“过多”内存的最佳(可靠但不太低效)方法是什么?我目前的想法是将
getrlimit(RLIMIT_AS)rlim_cur
getrusage(RUSAGE_SELF)ru_maxrss
进行比较;对吗?如果没有,还有什么更好的方法?Bob在各种主机上的Linux虚拟机中运行,所有主机都具有不同的内存量

如果让程序本身重新启动或将“计算一些数据”部分转移到单独的进程中,在任何情况下都需要检查内存消耗情况。由于您使用的是Linux,因此检查这一点的简单方法是获取感兴趣进程的pid编号,并读取文件
/proc/$pid/statm
的内容。第二个数字是常驻集的大小

读取这些proc文件是top和htop等工具获取流程数据的方式。定期读取内存文件中的~30字节以检查内存泄漏,这听起来效率并不太低


如果泄漏是常规的,并且您希望使其更复杂一些,您甚至可以跟踪增长率并相应地调整检查率。

假设内存泄漏发生在“计算一些数据”阶段,我认为将该部分重构成一个单独的程序并在其自己的过程中执行可能更有意义。这样,您至少可以隔离出有问题的代码,并使将来更容易替换它,而不是在内存不足时让程序重新启动来掩盖问题


“计算一些数据”部分可以是一个长时间运行的进程,等待来自主程序的请求并在必要时重新启动,或者(更简单的是)它可以是一个一劳永逸的程序,只在
*argv
中获取数据并将结果发送到
stdout
。然后您的主循环就可以在每次执行时进行分叉,并在返回时读取结果。如果可能的话,我会选择更简单的选项,但这当然取决于您的需要。

假设内存泄漏发生在“计算一些数据”阶段,我想知道将该部分重构为单独的程序并在单独的内存空间中执行是否更有意义。这样,您至少可以隔离出有问题的代码,并使将来更容易替换它,而不是在内存不足时让程序重新启动来掩盖问题。这只是一个想法——在没有看到代码的情况下,我不能说这对你来说是否是一个可行的选择;为什么不在每次计算完成后退出,然后每次重新启动程序呢?Jean,在可行的极端情况下。我想知道是否有可能通过只在严格必要时重新启动来减少开销。或者在处理其他固定的、保守选择的请求数后重新启动。杰夫:这不仅是个好主意,而且完全不需要测量内存使用情况!父级可以处理消息并监视其子级的状态,通过低级IPC传递信息并在SIGCHILD上重新启动子级。给我一个答案,我就接受!