In CocoaTouch (iPhone OS), how can I find / fix leaks that Leak tool tool cannot find?

I have an iPhone app that works great in a simulator. It responds well to warnings about memory, getting rid of everything that is not absolutely necessary. When I run it on the device, it works well. But after a certain amount of use, it crashes with error code 101, which, as far as I can tell, is the OS killing it due to memory usage. I see a memory warning (I register it), and my application responds to it, but dies shortly after.

If I look at the application in the Tools (on the device or in the SIM), it does not detect leaks. In addition, the use of network memory is 600-700 thousand bytes. Moving from different views of my application increases memory usage (as expected), but when releases and controllers are freed and freed, memory usage never becomes as low as it was. However, the addition is usually just something in the range of 1000-2000 bytes. Therefore, until the leaks show me the leaks, I suspect there is a problem. I also looked at all the objects that I select, and all of them seem to be fixed, as expected. The only objects that I see that continue to grow are GeneralBlock-N (where N is a number)

Should I not pay attention to the number of tools used? What will be the following steps when trying to diagnose a problem?

ADDED: I do not call malloc () or any CoreFoundation libraries that return a buffer for which I am responsible. The only non-Obj-C calls I make are logging NSLog statements.

+4
memory-management iphone cocoa-touch
Nov 11 '08 at 18:29
source share
5 answers

Here is a summary of what I found out (thanks to the excellent answers and comments):

  • The distribution of objects does not match memory usage. The answer to my question about the netAlloc net bytes element is that you should not pay attention to this - at least not when determining problems with the amount of used memory or a failure in it. This does not reflect the true memory usage of your application.
  • I think that ObjectAlloc only shows the memory occupied by the direct object itself. Therefore, if you have a UIImageView, it takes only a few bytes to store the various properties, but this may indicate a heap of image in memory. Therefore, viewing ObjectAlloc is only useful to ensure that you are not creating or storing objects; this will not give you an idea of ​​how much memory you are using or how much you can use before the crash.
  • MemoryMonitor will give you general memory usage. You can restrict it to viewing only your application using the search tool in the lower right corner of the "Tools" window.
  • Both ObjectAlloc and Memory Monitor objects (as well as the Leaks tool) are plug-ins for the tools - just in case, which are not obvious to someone else. You can run the Tools from Xcode by running Run -> Start with Performance Tool. After using the tools, you can open the library and add new plugins to monitor various aspects of performance.
+2
Nov 14 '08 at 5:13
source share
β€” -

One quick try is to run the Clang static analyzer . This will find some, but not all, problems in your code that may be missing. It checks the code at compile time, so it is by no means faultless, but it will almost certainly find the most egregious problems.

+7
Nov 11 '08 at 18:52
source share

You should also start the application using the tools of the memory monitor to see the general use of the system on the device.

+4
Nov 11 '08 at 22:08
source share

Leaks detect only memory, to which nothing refers, but are nevertheless saved.

What you see is that you left the memory saved and still referring to something.

One thing, especially for searching, is that if you pass the class reference to something else as a delegate, then you will release it in your dealloc method.

Similarly, if you subscribed to any notifications, you should unsubscribe from viewWillDisappear: (if you use the general unsubscribe method in the view controller, be sure to re-subscribe to the memory alert notification.

The timers are the same, deactivate them when the view leaves and turn them back on when the view appears (unless, of course, you need a timer that runs all the time when the application is running).

Basically, you should be suspicious of everything that you give a class reference, and try to figure out how you could eliminate this link whenever possible (either in dealloc or in viewWillDisappear: or both).

+2
Nov 12 '08 at 3:37
source share

One thing to look for is circular links.

(I don’t want this to sound patronized - I just want to make sure that I will be clear :) If object a refers to object b and object b refers to object a , a β€œleak” cannot be reported, because all memory is still referenced - but it may be an orphaned island of objects, separated from your application and never returned. Of course, this may include more objects ( a refers to b , b refers to c , c refers to a , etc.).

If you create an object graph somewhere, and there are any backward or cross-references, be sure to break the circles if you let go of the root (there are different ways to do this. The easiest way, of course, each class in question has a releaseAll method or similar - which calls releaseAll on it the children and then releases the children - but this is not always the best solution).

0
Nov 14 '08 at 9:40
source share



All Articles