使用VirtualTreeview和OTL进行内存泄漏

时间:2010-10-13 18:25:23

标签: delphi virtualtreeview omnithreadlibrary

我创建了一个小型多线程应用程序,我正在尝试将其转换为使用OmniThreadLibrary。我正在使用Virtualtreeview显示日志和状态/结果。 Vst Log只有两列,记录只包含两个字符串字段(非常简单,记录中没有对象)。

使用OTL附带的DEMO项目(线程池#11)我将项目更改为使用VirtualTreeview而不是列表框。当我从演示中“运行任务”时没有内存泄漏,但是如果我不止一次运行“运行任务”,就会发生内存泄漏。如果我多次运行任何任务,将发生内存泄漏。如果我根本不使用VirtualTreeView,则任何时候都不会发生内存泄漏。就在我使用VST和任务多次运行时。

我确实使用FreeNode事件并清除字符串,甚至尝试使用Finalize ...

示例:

procedure TFormMain.vstLogFreeNode(Sender: TBaseVirtualTree;
  Node: PVirtualNode);
var
  LogData: PTreeLogData;
begin
  LogData:=Sender.GetNodeData(Node);

  if Assigned(LogData) then begin
    LogData^.Msgtype := '';
    LogData^.Msg := '';
  end; 
  //Finalize(LogData^);

end;

为什么在多次运行任务时会出现内存泄漏? Delphi 2010与FastMM4 最新的Virtualtreeview和OTL

3 个答案:

答案 0 :(得分:10)

仅为验证的节点调用NodeFree事件,验证通常表示一次或多次显示的节点(调用GetText事件时)。 See Memory Leaks when using the Virtual TreeView Component

编辑:您可以通过检查节点数并计算调用NodeFree事件的次数来确认。

答案 1 :(得分:4)

我不知道为什么会发生这种情况,但我知道你怎么知道:打开FastMM的FullDebugMode。 (为此,您需要从SourceForge下载FastMM完整版。)打开在文件中提供内存泄漏报告的选项,并确保项目生成详细的映​​射文件。一旦你完成了这个设置,而不仅仅是一个弹出窗口,FastMM将为你提供一个非常详细的内存泄漏报告,包括堆栈跟踪。这应该可以帮助您缩小正在进行的范围。

答案 2 :(得分:1)

正如梅森所说,FastMM4是你的朋友。您可能需要查看此CodeRage 2会话:Fighting Memory Leaks for Dummies。它主要说明如何使用FastMM来防止/检测Delphi中的内存泄漏。是D2007,但仍然相关。

至于为什么运行两次泄漏但没有运行一次,根据经验,这主要是由于在字段/变量中创建和存储对象而不首先检查是否已分配,泄漏先前的引用。构造如下:

TSomething
FMyObject: TMyObject;
[..]

TSomething.Destroy;
begin
  FMyObject.Free;
end;
[...]

//somewhere in code:
FMyObject := TMyObject.Create; //leaks the previous FMyObject

显然不是那么直截了当,可能隐藏在某些setter中或通过某种List /容器......这里我猜想在不检查的情况下添加到VirtualTreeView ......