15

I haven't been able to create a Qt GUI app that didn't have over 1K 'definitely lost' bytes in valgrind. I have experimented with this, making minimal apps that just show one QWidget, that extend QMainWindow; that just create a QApplication object without showing it or without executing it or both, but they always leak.

Trying to figure this out I have read that it's because X11 or glibc has bugs, or because valgrind gives false positives. And in one forum thread it seemed to be implied that creating a QApplication-object in the main function and returning the object's exec()-function, as is done in tutorials, is a "simplified" way to make GUIs (and not necessarily good, perhaps?).

The valgrind output does indeed mention libX11 and libglibc, and also libfontconfig. The rest of the memory losses, 5 loss records, occurs at ??? in libQtCore.so during QLibrary::setFileNameAndVersion.

If there is a more appropriate way to create GUI apps that prevents even just some of this from happening, what is it? And if any of the valgrind output is just noise, how do I create a suppression file that suppresses the right things?

EDIT: Thank you for comments and answers!
I'm not worrying about the few lost kB themselves, but it'll be easier to find my own memory leaks if I don't have to filter several screens of errors but can normally get an "OK" from valgrind. And if I'm going to suppress warnings, I'd better know what they are, right?
Interesting to see how accepted leaks can be!

Toerndev
  • 715
  • 1
  • 6
  • 21
  • Q: What's 1K, between friends ;)? – paulsm4 Dec 28 '12 at 17:44
  • 5
    Leaking 1K once is a statistic. Leaking 1K a million times is a tragedy ;) – Thomas Dec 28 '12 at 17:50
  • all the major linux distributions use GTK: why coding in Qt ? – user1849534 Dec 28 '12 at 17:55
  • Both Thomas and jstine are absolutely correct. "1k" (or "1000") bytes being reported "lost" by a tool like Valgrind is almost certainly *not* a bug, and very definitely *not* a performance issue. Provided it's only 1K per program instance (and the "loss" doesn't increase during program execution), it's probably just an "implementation artifact" - nothing to worry about. In this case, the Valgrind output *is* probably just "noise". IMHO... – paulsm4 Dec 28 '12 at 18:37
  • @Thomas looking at software like Firefox I think the opposite is true. And makes pure analogy ;). – mip Dec 28 '12 at 18:46
  • 1
    @user1849534 All Linux distros also use Qt, so reasoning in your question is a bit odd... Perhaps you meant to say something about most major Linux DEs? – hyde Dec 28 '12 at 19:13

2 Answers2

20

It is not uncommon for large-scale multi-thread-capable libraries such as QT, wxWidgets, X11, etc. to set up singleton-type objects that initialize once when a process is started and then make no attempt to effort to clean up the allocation when the process shuts down.

I can assure you that anything "leaked" from a function such as QLibrary::setFileNameAndVersion() has been left so intentionally. The bits of memory left behind by X11/glibc/fontConfig are probably not bugs either.

It could be seen as bad coding practice or etiquette, but it can also greatly simplify certain types of tasks. Operating systems these days offer a very strong guarantee for cleaning up any memory or resources left open by a process when its killed (either gracefully or by force), and if the allocation in question is very likely to be needed for the duration of the application, including shutdown procedures -- and various core components of QT would qualify -- then it can be a boon to performance to have the library set up some memory allocations as soon as it is loaded/initialized, and allow those to persist indefinitely. Among other things, this allows the memory to be present for use by any other C++ destructors that might reference that memory.

Since those allocations are only set up once, and from one point in the code, there is no risk of a meaningful memory leak. Its just memory that belongs to the process and is thus cleaned up when the process is closed by the operating system.

Conclusion: if the memory leak isn't in your code, and it doesn't appear to get significantly larger over time (and by significant these days, think megabytes), and/or is clearly orginating from first-time initialization setup code that is only ever invoked once within your app, then don't worry about it. It is probably intentional.

jstine
  • 3,234
  • 20
  • 21
  • 6
    I would also add he should google valgrind suppressions. To some extent third party libs will have mem leaks or sudo mem leaks. If you are sure its from them and not your code then just add a valgrind suppression for it. My projects have large suppression files for this... A quick google should give you a guide on how to make a suppression file for valgrind... – David Mokon Bond Dec 28 '12 at 19:22
  • 2
    Qt does 'leak' memory for reference counted objects passed through signals/slots. If you try passing a QImage reference at 60fps the extra 1k blocks soon add-up. If you pass raw pointer types it doesn't – Martin Beckett Dec 28 '12 at 22:53
  • It would be very nice if the debug versions actually did clean everything up! – paulm Dec 29 '12 at 20:48
0

One way to test this can be to run your code inside a loop, and vary the number of iterations. If the difference between allocs and frees is independent on the number of iterations, you are likely to be safe.

user877329
  • 6,717
  • 8
  • 46
  • 88