Dealing with crashes due to memory issues

I have a large ZIM-based application that has recently started crashing midway.
I suspect it’s a memory or performance issue.
I added ZIM’s Meter, and the performance readings there look fine.

I added some memory logging in the code, and it seems that over time the app accumulates memory — likely causing it to crash at some point.

I tried to reproduce the problem on a clean page, and I noticed that even when I load just the attached code, the memory usage rises significantly after the image is loaded, and even after I remove the image, the memory does not drop back down.

I did notice that an image displayed inside a mask needs to be released from its mask before being removed — otherwise, the memory doesn’t go down at all.

I haven’t made any major changes recently since the crashes began.
The main change was updating the ZIM and CreateJS versions.

By the way, since updating, I occasionally see console messages saying: “boundary set”.

setInterval(() => {
                const used = performance.memory?.usedJSHeapSize / 1024 / 1024;
                if (used) console.log(">>>>> Memory usage:", used.toFixed(2), "MB");
            }, 1500);


            let circle = new Circle(300, purple).center().tap(() => {
                let pic = new Pic("https://res.cloudinary.com/closeapp/image/upload/v1762243947/test/scenic-view-of-sea-against-sky-at-sunset-4.jpg");
                pic.on("complete", () => {
                    pic.center();
                    pic.setMask(circle);
                    S.update();

                    setTimeout(() => {
                        pic.setMask(null);
                        // pic.bitmap.dispose();
                        // pic.bitmap = null;
                        // pic.image.remove();
                        pic.dispose();
                        pic = null;
                        S.update();
                    }, 5000);

                })
            });
1 Like

@danzen please help :slight_smile:

1 Like

Thanks for letting us know.

Was the app crashing before you updated the version of ZIM and CreateJS? Which versions did you update from?

We see the zog of the boundary set... just removed that. Cheers.

We have also added the removal of a mask (if it has one) as we dispose(). The app starts at about 22M for us. We are getting the app to come down to 27M if we do not have a mask and eventually down to 24M - not sure if that is the HTML clearing its memory. If it has a mask it comes down to sometimes 28, sometimes 33M. This is even if we press the circle a bunch of times.

The Bitmap - 5 of them are there to start. 3 more get added when pressed on and that seems to be it, no matter how many times we press. Will see if we can figure out why they are not being disposed and why 3 get added. Maybe using the lazy loading is storing a blank one... and perhaps that is not getting cleared when disposed.

So... working on it. Let us know about the original version.

I am doing Heap snapshots under Memory in Chrome. I wonder if the performance .memory can located ZIM based objects as a data object with values. Will check on that too - but cool to see the code version of it... that will make a good tool as @amihanya suggested.

Just tried preloading the image and it then starts with 6 bitmaps and goes to 7 bitmaps when making a Pic. So the two extra bitmaps, when lazy loading, are a common bitmap used to test loading (once by ZIM - for CreateJS always - note, when we preload, it showed up at the start) and then a temporary one, I suppose for the lazy load. So even though those two will be very small - we can probably dispose those once they are used.

The question remains, though, as to why the actual bitmap is not being disposed despite all efforts. We will test against older versions as they were disposing and see if something new has caused it to stay in memory.

Oh... and we will keep track of our efforts here... but no response is expected as we go ;-).

We’re working with the latest versions of ZIM and CreateJS.
We believe the issue started about two versions ago (around ZIM 18).
The app simply freezes after about 20 minutes of being active, and we can see the metrics Racheli mentioned just keep rising without clearing from memory.

If you’d like, I can send you a private link so you can see the freeze yourself — gradually, the animations start slowing down, the cursor stops changing shape when hovering over buttons, until eventually the whole app freezes and nothing can be done.

The main problem is that all the memory gets stuck — even the console stops responding, and JavaScript calculations that are unrelated to graphics stop running as well.

If it was working without freezing and then new versions cause freezing, it should be pretty easy to identify the culprit. It would be helpful to know specifically the last version of ZIM when it was working. Sure, please send a DM with some extra info. If you think you know the code that is causing it, that would be helpful too. For instance, if you comment out the mask... is there still a problem? Or is it somewhere else.

Thank you! We have sent a private message.

1 Like

Okay... it looks like going from ZIM ZIM 01 to ZIM 014 the dispose stopped removing objects from memory. This could be for any object - we tested with a Circle, a Button, and a Pic. So having a look for any dispose differences or any way we may be storing general references. For instance, if we introduced global cursor and a global cursor object registers each DisplayObject made... then we may have missed removing that reference.

Hahaha - just went to the Updates to see what we adding in ZIM 014 and we actually did introduce the global cursor. Was just using that as an example... but maybe that is it! Digging.

Also did work on global blurDetect...

Indeed, there is an F.cursorList that keeps track of any objects with a cur set, including drag(), tap(), and cur(). This object was not removed from the list when dispose was called.

We had two circles with taps. We disposed one on tap and there are still two circles in the cursorList. So that is an easy fix.

BUT - darn it. Even when we don't use cursors on the circles, they are still not disposing right. So it is something else too.

Tried replacing ZIM.gD - global dispose with the ZIM version ZIM 02 gD but it still leaves the circle - so not in how we are disposing. Looked through all the frame properties and could not see anything that would keep the object - fixed the cursorList issue. Easy.

Now checking the global ZIM object. Pain as lots is on that. Nope... 270 changes... should have compared ZIM 02 to 014 - but compared ZIM 02 to 108 and did not see anything out of order.

Next, checking the Container as that is what these objects extend. Nothing really... changes but all inside methods or new methods.

Will check on that blurDetect... but don't think that registers DisplayObjects... but will see. Nope - it is not even running.

So... time to take a break and let the brain think overnight.

Okay... well, made a new file with just a single circle rather than two... and it is now disposing. And a Button is disposing, so doing more testing, but this is good. And now the other is working. So... not sure what the issue was - clogged heap trace... wasn't a cache issue as we were noting positive change on the cursorList issue and had removed the cursors anyway. So... it looks like we are good. The only thing we found was the cursorList.

We will consider if there is a way to retro patch the other versions... currently, I don't think there is an easy way... 014, 015, 016, 017. No way to do the NPM. The minified code is tricky, we would have to re-minify by setting our current versions back and running our build. Will give it some thought but that risks messing running apps.

An app patch if an object has a cursor, would be just BEFORE the dispose do:

F.cursorList.remove(obj); 
obj.dispose();
obj = null;

We will give it some thought, and @amihanya and @racheli you can do a test of that perhaps... and then will decide tomorrow how to proceed.

Wow, great that you found it!
Which ZIM version should we test, and which CreateJS version?

That's great! Thank you for all the work!
Where can I find the latest version?
Is this already updated with the changes you made?
https://zimjs.org/cdn/018/zim_min.js

Yes - the removal from the F.cursorList has been added to ZIM 018.

So this file has the change https://zimjs.org/cdn/018/zim_min.js