2013-05-07 111 views
3

正如我们所知,堆用于为应用程序动态分配内存。在应用程序异常终止的情况下,堆内存如何被清除(从而避免内存泄漏)?应用程序突然关闭时的堆内存清除

考虑以下方案:

  • 说,一个应用程序崩溃突然在Windows或Linux。
  • 我们强制在linux中杀死一个应用程序:kill -9 <process_name>
  • Visual Studio中的C++程序在执行过程中抛出一个错误。

是堆管理和清理在上述情况下,有什么不同? [请添加更多的用例场景,这可能是准备在这里]

这个问题在我脑海里想出了,因为我们总是在谈论保证没有内存泄漏发生在我们的代码。现在我们如何处理那些强制关闭可能导致程序退出的应用程序而不调用内存释放调用的场景。

如果这种内存泄漏重复发生,操作系统是否可能缺少堆内存?抑或是OS具有处理它的方式...

回答

1

至于动态内存管理,你应该使用RAII智能指针就是一个例子)拍摄期间的异常等保健内存泄漏和管理。
在您的应用程序退出的情况下,操作系统只是回收它提供给进程的所有内存。操作系统不理解泄漏,它只是收回它给过程的东西。所以本身没有泄漏。所有内存都被回收。您可能会泄漏其他资源(文件描述符等),但聪明地使用RAII应该防范这种情况。

+0

感谢您的意见。我忽略了一个明显的问题,即每个进程都提供了一个单独的堆空间。 – vishal 2013-05-08 01:38:56

+0

实际上,我已经研究过一个实时操作系统,每个进程没有单独的heapspace(因为如果在跨越进程边界时必须分配并释放每条消息,堆中发送消息会变得麻烦,所以它更好为[一组进程或所有进程]拥有一个共同的堆栈)。它以每个进程为基础跟踪分配的内存,当进程退出/死亡时,它将释放属于该进程的所有内存。所需要的是操作系统跟踪所有内存分配,而不是堆属于进程。 – 2013-05-08 08:56:20

0

不要紧,你的过程是如何关闭,从进程分配的任何剩余的内存由操作系统的内存管理器它关闭时释放。在你的进程死亡之前释放你分配的所有内存是一个很好的习惯,但是当你的进程关闭时,OS /其他应用程序的可用堆是相同的。

6

假设操作系统是UNIX或Windows的典型实现,当应用程序被杀死了,无论用什么方法是通过杀死堆内存是由操作系统释放。

有意思的是,其他操作系统可能不会这样做,这取决于每个操作系统以有意义的方式解决这个问题 - 我不知道有任何操作系统不会“在杀死进程后清理”,但我相信这样的事情可能存在于这个世界的某个角落。

编辑:可能有其他资源不太容易被释放,例如多个使用的共享内存或信号量。但是大多数操作系统倾向于通过释放被杀应用程序的引用来处理这些问题,并让等待任何“可等待对象”(互斥体,信号量等)的其他进程将“让其运行”。

+3

作为一个方面说明,析构函数不会被调用,因此如果在析构函数中有一些关键代码(例如缓存到文件的缓冲区),可能会导致可怕的情况。 – Fabien 2013-05-07 12:14:45

+0

是的,编写文件后半部分的代码的后半部分可能还没有运行...... “zip”写入大部分压缩文件,但不包含位于文件末尾的“目录”......如果代码崩溃或死亡[没有“捕获”失败],则结果是“不完整的” “和”未定义“。 – 2013-05-07 12:18:09

+0

@Mats:感谢您的输入。你的回答很有帮助。 – vishal 2013-05-08 01:39:55

2

“的堆典型地由运行时分配在应用程序启动,并且当所述应用程序(技术上过程)离开被回收”,以便杀死/关闭一个应用程序异常/常不会泄漏的任何存储器。

相关问题