• Announcements

    • khawk

      Download the Game Design and Indie Game Marketing Freebook   07/19/17

      GameDev.net and CRC Press have teamed up to bring a free ebook of content curated from top titles published by CRC Press. The freebook, Practices of Game Design & Indie Game Marketing, includes chapters from The Art of Game Design: A Book of Lenses, A Practical Guide to Indie Game Marketing, and An Architectural Approach to Level Design. The GameDev.net FreeBook is relevant to game designers, developers, and those interested in learning more about the challenges in game development. We know game development can be a tough discipline and business, so we picked several chapters from CRC Press titles that we thought would be of interest to you, the GameDev.net audience, in your journey to design, develop, and market your next game. The free ebook is available through CRC Press by clicking here. The Curated Books The Art of Game Design: A Book of Lenses, Second Edition, by Jesse Schell Presents 100+ sets of questions, or different lenses, for viewing a game’s design, encompassing diverse fields such as psychology, architecture, music, film, software engineering, theme park design, mathematics, anthropology, and more. Written by one of the world's top game designers, this book describes the deepest and most fundamental principles of game design, demonstrating how tactics used in board, card, and athletic games also work in video games. It provides practical instruction on creating world-class games that will be played again and again. View it here. A Practical Guide to Indie Game Marketing, by Joel Dreskin Marketing is an essential but too frequently overlooked or minimized component of the release plan for indie games. A Practical Guide to Indie Game Marketing provides you with the tools needed to build visibility and sell your indie games. With special focus on those developers with small budgets and limited staff and resources, this book is packed with tangible recommendations and techniques that you can put to use immediately. As a seasoned professional of the indie game arena, author Joel Dreskin gives you insight into practical, real-world experiences of marketing numerous successful games and also provides stories of the failures. View it here. An Architectural Approach to Level Design This is one of the first books to integrate architectural and spatial design theory with the field of level design. The book presents architectural techniques and theories for level designers to use in their own work. It connects architecture and level design in different ways that address the practical elements of how designers construct space and the experiential elements of how and why humans interact with this space. Throughout the text, readers learn skills for spatial layout, evoking emotion through gamespaces, and creating better levels through architectural theory. View it here. Learn more and download the ebook by clicking here. Did you know? GameDev.net and CRC Press also recently teamed up to bring GDNet+ Members up to a 20% discount on all CRC Press books. Learn more about this and other benefits here.
Sign in to follow this  
Followers 0
CJ_COIMBRA

Massive memory leak

14 posts in this topic

I am working on a project for a long time now and wasn't paying much attention to memory issues since they didn't cause any problems so far but I believe they will at some point. There are some actions to be taken like providing smaller assets to players that don't use/have full HD compatible displays and optimize some assets, yet I would like to know how do you guys (or girls why not!) deal with memory leaks. Is there something particularly important that I should look for when tracking the leaks? Are the leaks necessarily linked to "new" usage or should I look somewhere else too? Should a massive memory leak always be obvious to detect?

 

Also there is a second point, more specific for SFML users: I am using a resource manager class that loads all assets and provide them the other classes as needed or at the game boot. The resource manager holds sf::Image's and the classes that need to drawn something holds sf::Sprite's. Now, if I have two,three,four...a thousand similar instances of this class, will the resource manager still take just the memory needed for one sf::Image used by the consumer class or each instance will take more and more memory? Does this make sense at all?

 

Thanks in advance.

0

Share this post


Link to post
Share on other sites

There's only one way to deal with leaks: Find them and fix them.

 

Leaks don't necessarily come from new/malloc statements in your own code, they could also happen indirectly if you don't call the proper cleanup methods in library code.

 

There are two methods to find leaks:

- Use a static analyzer that examines logical errors in your code.

- Run the executable using a memory profiler and watch for unreleased resources.

 

With good tools tiny leaks should be as easy to detect as massive ones.

Edited by Felix Ungman
2

Share this post


Link to post
Share on other sites

Should a massive memory leak always be obvious to detect?

Absolutely. I take it you check the memory footprint in Task manager. There's no way you could miss a massive leak this way.

 

Then again, your definition of massive leak may differ from mine...

 

 

Are the leaks necessarily linked to "new" usage or should I look somewhere else too?

In gamedev there are two major types of leaks - Memory Leaks and Resource leaks, which are caused by unreleased graphics resources (e.g. textures, RTs, VB / IB, ...). Those are best checked by DirectX debug runtime (change the setting in Control Panel and enjoy hundreds of colorful messages in Output pane of Visual Studio).

 

 

Also, if you are not using Smart Pointers and are still trying to match new/delete, there's nothing better than the experience of rolling out your own _NEW, _DELETE and going through the logs and matching it all.

 

Usually, that exercise alone is enough to persuade one it's really time to move to Smart Pointers smile.png

1

Share this post


Link to post
Share on other sites

Do you use linux (or may it)? If you do look for a program called valgrind.

 

It will give you a memory report that is very accurate and includes memory leaks and memory errors. I always validate my code with it.

 

The link for the project is here: http://valgrind.org/

1

Share this post


Link to post
Share on other sites

Also there is a second point, more specific for SFML users: I am using a resource manager class that loads all assets and provide them the other classes as needed or at the game boot. The resource manager holds sf::Image's and the classes that need to drawn something holds sf::Sprite's. Now, if I have two,three,four...a thousand similar instances of this class, will the resource manager still take just the memory needed for one sf::Image used by the consumer class or each instance will take more and more memory? Does this make sense at all?

Each sf::Image(or sf::Texture primarily in 2.0) is a unique instance. If you make 100 sf::Textures and tell them all to load the same file you'll have 100 copies of the image data. What you -should- do is keep one copy of the image in your resource manager and just return references to any caller asking for the object. You could do that by using an unordered_map or something using the key as the filepath of the object, or some kind of identifier like an assetname you invention up.

Each object can easily have it's own sf::Sprite, it's supposed to be a lightweight class from what I can tell. Then you can just set it to whatever image/texture you want to immediately use.
1

Share this post


Link to post
Share on other sites

Also there is a second point, more specific for SFML users: I am using a resource manager class that loads all assets and provide them the other classes as needed or at the game boot. The resource manager holds sf::Image's and the classes that need to drawn something holds sf::Sprite's. Now, if I have two,three,four...a thousand similar instances of this class, will the resource manager still take just the memory needed for one sf::Image used by the consumer class or each instance will take more and more memory? Does this make sense at all?

 

I'm not sure if this helps, but personally I have a small class based mostly around an std::map that holds my sf::texture objects (sf::image in your case).  That's the only place that textures get loaded and they are all loaded one time at startup.  The class has a getSpriteByKey method that returns an sf::sprite with a given texture/image attached to it.  I don't create sprites until I need them (though I do try to keep them around once I have created them if I know I'll need them again where possible).

1

Share this post


Link to post
Share on other sites

Thanks for the suggestions. They´ve helped me. I think I found the problem (or the worst part of it). I have a std::vector with dynamic allocated objects being pushed under a certain condition. The problem is that when another certain condition is met, I was just popping them. So I guess I should´ve used delete before popping them? Is this correct? I think this is the problem because after commenting this relevant part of the code my memory consumption has stopped to increase.

0

Share this post


Link to post
Share on other sites

Yep, that solved the problem. There are other minor leaks to fix so I´ll assume the same solution for now.

 

edit: just a note, I wasn´t popping the objects. I was doing "erase" from std::vector. I am still doing it but now I delete them before that. I read somewhere that I should nullify AND also delete. Is this correct?

Edited by CJ_COIMBRA
0

Share this post


Link to post
Share on other sites

Yep, that solved the problem. There are other minor leaks to fix so I´ll assume the same solution for now.

 

edit: just a note, I wasn´t popping the objects. I was doing "erase" from std::vector. I am still doing it but now I delete them before that. I read somewhere that I should nullify AND also delete. Is this correct?

Erase or pop_back do the same thing essentially, destroy the object. In the case of destroying pointers you literally just destroy that one pointer to the object and the object remains floating in memory, oblivious to the fact that no other pointers or references may have access to it. Obviously a memory leak.

 

Usually you set a pointer to NULL(which is 0) so that if you later check the pointer against null, you will know if it is currently pointing to a hopefully live object, or if it was set to point to nothing, perhaps to wait for you to assign it to something else.

 

On the flipside, delete frees the actual memory the pointer is pointing to, leaving the pointer still alive but pointing to a now dead object.

 

You probably know most of this, but I was just re-iterating as a start point. You only should set a pointer to null if it is going to be alive still. pop_back or delete, frees the actual pointer, so it won't exist any longer in the container, thus you don't really need to set it to null.

 

In other words: delete any allocated objects you are done using, set the pointer to null if it isn't going to be destroyed anyway. Though you might want to set it to null as a sanity check if you do something like.. declare it at the top of a function and someone might be tempted to use it at the bottom. That obviously isn't the case with regards to container classes since you won't be inside them. You definitely want to set things like member pointers to NULL.

2

Share this post


Link to post
Share on other sites

edit: just a note, I wasn´t popping the objects. I was doing "erase" from std::vector. I am still doing it but now I delete them before that. I read somewhere that I should nullify AND also delete. Is this correct?


You must call delete otherwise the object will still exist, but you don't need to set the pointer to NULL if you call erase or delete the entire vector as the pointer will be "destroyed" anyway. Actually setting it to NULL will be a wasted instruction.
1

Share this post


Link to post
Share on other sites

So you have a vector of pointers, in violation of my rule (1) above. Why not make it a vector or objects instead?

0

Share this post


Link to post
Share on other sites

Yeah, I tried that but for some reason it wont work in my case (everything seems fine but then it crashes every time the execution reaches the point that the object is pushed into the vector), so I changed back to pointers. Perhaps it's related to the class I am trying to push into the vector. I'll look more into that later, I just started to optimize and fix things on my project and I've seen that's it's going to be a huge work.

 

By the way do you know what would be the ideal amount of memory I should recommend based on how much my application uses? I mean, we see lots of games asking for 2GB minimum and 4 GB recommended (in example) but obviously those applications don't take 2GB or 4GB to run because there are other things happening on the system. Is there a "formula" that gives you the amount you should recommend based on how much you will in fact use?

 

Thanks again!

0

Share this post


Link to post
Share on other sites

Yeah, I tried that but for some reason it wont work in my case (everything seems fine but then it crashes every time the execution reaches the point that the object is pushed into the vector), so I changed back to pointers.

 

I would say go back to objects and fix the crash. You may have some other bug and the use of pointers is just masking it.

0

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0