Whys it causing a memory leak? (types and lists)
BlitzMax Forums/BlitzMax Beginners Area/Whys it causing a memory leak? (types and lists)
| ||
Hey peeps this is a particle system that i made for that supernova2d game i did. It played fine, but when i checked on my memory, i got a leak... This is the code that matters from it and the leak is still present... Why am i getting this leak and how do i stop it!? cheers peeps :D Global bullet_list:TList=New TList Global particle_list:TList=New TList Type particle Field x#,y# Field c#,d# Field xforce#,yforce# Field life Field maxlife Field Order Field angle Field anglespread Field damp# Field lastx,lasty Field lastdone End Type Type bullet Field from Field x#,y# Field c#,d# Field life End Type repeat For n=1 To 1024 p:particle=New particle ListAddLast particle_list,p p=Null Next For p:particle=EachIn particle_list ListRemove particle_list,p;Release p p=Null Next Print MemAlloced() flushmem Flip Cls Until KeyDown(key_escape) |
| ||
P still references the last particle. |
| ||
But p=null still gives me a memory leak? :( ohhh wait! ..wonders off for a second... [edit] Nope, still can't get it to work properly, Am I being an idiot? heh. i am usually.... ive changed the code above to reflect what i tried. |
| ||
I don't think p=null should come into it. Setting a pointer to null doesn't deallocate any memory. |
| ||
You are releasing p, then setting it to null so you are basically removing p then readding it with a value of null. As far as I can tell (docs dont explain properly) setting to null is only done with an object reference and release is done with variables. I might be wrong, but id suggest removing p=null and release p. Once you assign p to another object, flushmem should see that the object it referenced is now dead with no links. |
| ||
Change your main loop to this:Repeat For n=1 To 1024 p:particle=New particle ListAddLast particle_list,p Next For p:particle=EachIn particle_list ListRemove particle_list,p Next FlushMem Print MemAlloced() Flip Cls Until KeyDown(key_escape) |
| ||
This doesn't make sense:Release p p = Null; is a command seperator not a comment in BlitzMax! |
| ||
I don't understand why "p = Null" is allocating memory. |
| ||
Maybe because it is essentially initializing the variable. As I understand it, p = Null is the same as p = 0. Maybe that's the reason? Could be that if you aren't using Strict mode, every time BlitzMax encounters a variable it actually creates a new one. [Edit] No, just tried strict mode and it still does the same thing. Weird! |
| ||
SO no help available then? with p=null and without p=null, im getting a rather nasty memory leak. :( How do i get around this? the reason behind p=null is its the only way i can think of of solving P still references the last particle. |
| ||
Hey, found it! 'Release p' is where the memory leak is. Try removing that, and keep p = Null. No memory leak anymore...A bug? I'd say! |
| ||
bloomin eck! il give it a go... |
| ||
Woah thats odd! Well, i fixed it thanks to you guys! Once again, the Cygnus is saved by.... Blitz Community! ...ok thats crap :/ hehe |
| ||
I'm not clear what Release actually does (Yes I've read the docs). As I understand it the memory used by a type instance is freed at the next flushmem once all references to it are gone. In the inital example p still pointed to the last instance so flushmem couldn't remove it. If the loop was placed in a function - kill_all_particles() then p would likely be local to that function and destroyed automatically. So there would be no memory leak. |
| ||
Maybe because it is essentially initializing the variable. As I understand it, p = Null is the same as p = 0. Maybe that's the reason? No - all objects are Null when they are created. p=Null is effectively 'unlinking' the variable p from the object it references. Hence subsequent calls to FlushMem would delete the object previously referenced by p. |
| ||
More here: http://www.blitzbasic.com/Community/posts.php?topic=42572 |
| ||
Hi, Yes, Release seems to be killing it. Release is only really for integer handles, eg: if you've gone... Local my_image=LoadImage( blah ) 'Note: my_image is an int ...then you must "Release my_image" later to avoid a leak. If you are using object variables instead of ints, there is no real need for Release but... BlitzMax *does* let you use Release on an object variable, in which case all it does is set the variable to Null. I should NOT have done this as it looks like it's only confusing things. It also appears to be broken, judging by your demo! Anyway, you can safely remove all Releases and =Nulls from this code and there's no leak. In fact, you can pretty much remove all Releases and =Nulls from all the code I've seen posted here to date! |
| ||
Beautiful! Thanks Mark! |
| ||
But Mark, from what you said Local my_image=LoadImage( blah ) 'Note: my_image is an int ...then you must "Release my_image" later to avoid a leak. We need to release integer handles. Is there a way so we don't have to do this, so handles are automatically freed? Or maybe not allow Int handles to be returned so people have to use objects - I think that'd be better. Aaron |
| ||
Hi, I think integer handles are good for beginners, and that's why they're in there. eg... player=LoadImage( "player.png" ) ...is easier to get to grips with than... player:TImage=LoadImage( "player.png" ) Maybe not to experienced programmers, but I try to send my mind back to when I was learning stuff, and having to know both types and functions is just extra work if you're starting out - esp. with a procedural interface. In fact, you can pretty much remove all Releases and =Nulls from all the code I've seen posted here to date! Sorry - unclear again! I meant Release when used *with objects*, which a lot of people have been doing. |
| ||
Sorry - unclear again! I meant Release when used *with objects*, which a lot of people have been doing. And by objects you mean 'user defined types'? |
| ||
Thanks for the info Mark :) |
| ||
Mark, I understand that it's a lot easier for beginners, but also idea of them having to Release those things, is a little complicated too isn't it? And on top of that they need to understand the distinction between the Int handle and the Object. Just a thought. So if the int handles could be GC'd like the objects, problem solved ;) @fredborg By objects he means instances of user defined types. Aaron |