Unnoticeable memory leaks. Part 1

by - 16:03

(I have been relatively silent for several last days to respond to comments here on the blog and on the forum. My apologies if this frustrated you. At Intel, we are approaching a release cycle of Intel Parallel Studio and this requires a good deal of efforts to synchronize among multiple teams to ensure that something important is not overlooked. In addition to other activities, this eats much of my time).

This time I'd like to touch a subject what often does not get developers' attention it probably deserves. It's about memory leaks; and not about those which you can easily detect with specialized tools (including Intel Parallel Inspector, part of the Parallel Studio). It's not even about pseudo-leaks that some novice Open CASCADE users blame it of (I hope someday to write more about CASCADE memory management) when freed memory is not returned to the system but remains under the Open CASCADE memory manager. I mean cases when memory is still occupied by some (formally) useful contents but which your application doest not track/need any longer. This may result in orphan data residing in memory and eating out megabytes.

Let me show you a couple of particular examples that could inspire you to review your code for similar cases.

I was recently debugging my app which uses OCAF. There was a document class that contains a handle to OCAF document (TDocStd_Document) and a singleton application class that contains a handle to TDocStd_Application subclass. So once I put a breakpoint into my document destructor to check a reference count of the OCAF document. I expected it to be 1 so that upon destruction of my document, the ref count is decremented to 0 calling a destructor of TDocStd_Document and freeing its memory. To my surprise there a ref count was 3.



Tracing documentation creation revealed 2 additional references – one was from the global session object that registered all open documents and the other was from the TDocStd_Owner attribute that was attached to a root label (this is done automatically by OCAF). Searching around promptly gave an answer – I forgot to call TDocStd_Application::Close() before destroying my document. Once this had been done, document reference count correctly decremented to 0 and started freeing occupied memory.

The point is that until I discovered this manually, there were no any symptoms that document contents (which can be quite memory consuming for a complex structured doc) remained orphaned. The application continued to run and exit gracefully.

Another time I intentionally tried to inspect memory deallocation when importing and exporting IGES. The Data Exchange framework in Open CASCADE is too feature-rich and its architecture involves numerous classes with references between each other. My concern was that there could be cyclic handle cross-references making objects non-destroyable (recall my first posts on Handles about this potential issue). Another suspicion was that some data are not fully cleaned upon after every translation. So I went and used the debugger to see what happens...

(to be continued...)

You May Also Like

2 comments

  1. Are you sure??
    I use the method Close of hte TDocStd_Application Class! And leak still occurs, no single byte are released!

    ReplyDelete
  2. Can you check with MMGT_OPT=0 and see if leak still occurs ?

    ReplyDelete