Finding Abandoned Memory

Detect abandoned and unused memory allocated by your app using the Allocations instrument. Releasing this memory increases memory efficiency, improving the quality of your app.

To find abandoned memory
  1. In the Instruments analysis tool, open the Allocations template.

  2. Choose your app from the Choose Target pop-up menu.

  3. Click the Record button.

  4. Repetitively perform an action in your app that starts and finishes in the same state.

  5. After each iteration of the repeated action, click the Mark Generations button to take a snapshot of the heap.

  6. Repeat steps 4 and 5 until you see whether the heap is growing without limit, and then click the Stop button.

  7. Analyze objects captured by the heap snapshot to locate abandoned memory.

To avoid having abandoned memory, make sure the heap does not continue to grow when the same set of operations are continuously repeated. For example, actions such as opening a window and then immediately closing it, or setting a preference and then immediately unsetting it, return the app to a previous and stable memory state. Extensive cycling through such operations should not result in unbounded heap growth.

To ensure that none of your code abandons memory, repeat user scenarios and use the Mark Generations feature after each iteration. After the first few iterations (where caches may be warmed), the persistent memory of these iterations should fall to zero. If persistent memory is still accumulating, selecting the focus arrow provides a call tree of the memory. This tree identifies which code paths are responsible for the allocations that are eventually being abandoned. Your code is colored black in the stack trace. Make sure that your scenarios exercise all your code that allocates memory.

If the heap continues to grow after the first few iterations of the cycle, you know your app is abandoning memory. Find a heap snapshot that seems representative of the repeated heap growth. Click the focus button to the right of the heap snapshot name to display objects created during that time range that are still living at the end of the program’s execution.

After you stop the trace, you can still take snapshots by dragging the inspection head in the trace window timeline to where you want the snapshot and clicking Mark Generations. After stopping the trace, take one last snapshot at the end of the trace. At that point, the number of persistent objects should be zero.