17
votes

I am creating an application which is a kind of gallery - it shows different media content as a fullscreen viewer. Allocations instrument shows that Live Bytes parameter doesn't grow higher than 40 Mb when using application. Meanwhile the app is 100% being killed after I slide pages 20-30 times. I checked Dirty Memory parameter and found it was 10 times bigger than Live Bytes size. And the most of that dirty memory consumed Image IO:

Screenshot

EDIT, another screenshot:

Screenshot

The allocations peaks above are switching video/image media contents. The problem is the dirty memory grows almost linearly and I need to release it somehow.

Now about application design. Application screen has one horizontal scroll view. Scroll view contains videos or collage objects which contain multiple images. To save memory only three pages are created at a time - current page and pages on the left/right. So pages always created and removed on-fly when sliding scroll view.

All the images I load using [UIImage imageWithContentOfFile: path] method. Collage object stores UIImage instances inside imagesArray. In dealloc method imagesArray attribute is cleared.

So, questions:

  • Is it a kind of system bug in [UIImage imageWithContentOfFile?]
  • Is it Image IO cache?
  • Can I clear it?
2
This is not a bug in iOS - if it was thousands of apps would not be working. Somehow your images are not getting released.David H
Obviously the problem in my program, but as you can see in screenshot, user memory is cleared correctly (the first chart shows limited consumption). On the other hand, we see huge dirty memory growth. And I really do not understand what kind of problem could be. By the way, I logged dealloc method and I saw it was called.ZAN
So what does the disclosure triangle show for Image_IO? That is, expose the list and update your question.David H
Added a new screenshot. By the way, I tried to test a suspicious component (collage with multiple pictures) in a test application - created and deleted 1000 ones in a circle, but didn't catch that leak.ZAN
@ZAN hi.. i have the same issue. application memory continuosly increase and after some time it crash. plz look into it in my code stackoverflow.com/questions/29017579/… please help me. where i am wrong.Hitarth

2 Answers

22
votes

Putting this here as too big for a comment, just some ideas:

1) one way to retain objects by mistake is to have objects in views that get hidden but not removed from their superview (and thus stay retained)

2) if you do anything with UIImageView etc on any thread not the main thread bad things can happen (like this)

3) copy your project so you can freely mess with it, and try a bunch of things:

  • instead of multiple images, always load the same image, but leave the other parts of your code as they are - do things change?

  • In any subclasses you create that would hold/retain images, put a log message in the dealloc to see if in fact those objects are getting dealloced.

  • subclass UIImageView, use it for the images, and log the dealloc

  • subclass UIImage, use it for these images, log the dealloc

4) I am having a hard time believing imageio has a defect that would do this, but what you could do is switch to using imageWithData, and load the data yourself. Use the F_NOCACHE flag when you actually read the data - there is other code on SO on how to do this, you can search on it (I answered a question on it).

If you can create a demo project with this defect, it would be a lot easier to debug it than just guess at what to do. Logging the class that gets dealloc'd goes a long way, since you will see immediately what is not getting released, and then better focus in on the problem.

2
votes

In addition to David H's answer I would recommend anyone who's experiencing this problem to also check if your View Controller's, Model's, UIDocument's (if you use it) deinitializers are called when not needed.

If you don't properly deallocate these classes and they contain the image / VDO / content data that UIKit refers to it, then this may result in this scenario where you see VM: ImageIO memory usage always increasing, and yet you see no memory leak when you use Instruments since these contents are now retained internally by UIKit.

I experienced this very issue too, twice, and in my case it turned out that my Model's deinitializer was never called due to unrelated issues. By fixing those unrelated issues and making sure my Model is deallocated, these VM: ImageIO continuous growth disappeared.

enter image description here