Fanning Software Consulting

Leaking Memory from IDL File Objects

QUESTION: I created a little procedure to plot shapefiles with IDLffShape. The routine works great, but when I have to add graphics to 800 images, I run out of memory at around 500 images. On investigation, it appears the object has a memory leak. Am I doing something wrong to cause this?

ANSWER: This is an error of omission rather than commission, so you only have to do five Hail Mary's and you can go.

This is actually an issue with many of IDL's file reading objects (for example, IDLgrSHAPE, IDLgrDICOM, and IDLffDXF). The problem is that these objects return structures that have pointers in them. This is really the only way it can be done, because the object doesn't know anything about the actual data file (in this case, a shapefile) you will be reading. Since the object can't read your mind and know what you will be doing with the information it returns to you, it can't destroy those pointers on its own. It is going to leave that up to you.

You could choose to free the pointers individually. For example, your code might look like this:

   *pEnts = oShapefile->GetEntity(/ALL, /ATTRIBUTES)
   FOR I = N_ELEMENTS(*pEnts)-1, 0, -1 DO BEGIN
     PlotEnt, (*pEnts)[I], color=color
     Ptr_Free, ((*pEnts)[I]).vertices
     Ptr_Free, ((*pEnts)[I]).measure
     Ptr_Free, ((*pEnts)[I]).parts
     Ptr_Free, ((*pEnts)[I]).part_types
     Ptr_Free, ((*pEnts)[I]).attributes
   Ptr_Free, pEnts

But this is a lot of work, and requires some specialized knowledge on your part to know what to destroy. A better solution is to use the IDL-supplied tool HEAP_FREE. Unlike its counterpart, HEAP_GC (which you would only want to use after you had sent your office mate down to the cafeteria for some Danish and closed your office door), HEAP_FREE is a command respectable programmers can feel comfortable using.

In fact, HEAP_FREE, was probably written with exactly this purpose in mind. It recursively frees all heap variables (pointers or objects) referenced by its input argument. In this case, you would use it like this:

   HEAP_FREE, *pEnts
   Ptr_Free, pEnts

Web Coyote's Guide to IDL Programming