Leaking without auto release pool


#1

I had problems with a few string leaking without an auto release pool during static initialization and firing up some threads.

If I add an auto release pool to juce_posix_SharedCode.h, setCurrentThreadName like this:

void Thread::setCurrentThreadName (const String& name)
{
#if JUCE_IOS || (JUCE_MAC && defined (MAC_OS_X_VERSION_10_5) && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5)
JUCE_AUTORELEASEPOOL
[[NSThread currentThread] setName: juceStringToNS (name)];
#elif JUCE_LINUX
prctl (PR_SET_NAME, name.toUTF8().getAddress(), 0, 0, 0);
#endif
}

the problem goes away. Does it make sense to apply this change to Juce?


#2

Ok… I will add that. But: I’d certainly warn against creating threads in a static constructor - remember that all the cocoa stuff is obj-C, which has no concept of static constructors, so there could be any number of nasty, obscure problems that could arise when you’ve got C++ and obj-C all trying to use each other before either one may be fully initialised. You might get away with it, but it’s not something I’d feel safe doing myself.


#3

Hmm…what’s a static constructor?

Also, my understanding is that setCurrentThreadName() is only for debug builds. At least, that’s the situation on MSVC, where it sends a signal to the attached debugger. Do people want release distributions to have embedded thread names? I.e. “CopyProtectionThread”?


#4

My remarks about static initialization were confusing. Though it happened for me with static initialization, the real issue here is, that during setThreadName an auto released string is used which is not obvious. I can imagine many cases were this is the first call in a threads run method, before an auto release pool is established. Often someone with an C++ background would not even think about establishing an auto release pool at all in a threads run method.


#5

Ok, a “statically constructed object’s constructor”… But you know what I mean!

There’s probably no other time when you’d actually need to create a pool manually, because any code that you run inside any event callback or juce-supplied thread will already have a pool on the stack. So really, this problem only arose because the compiler-generated startup code that called your static object’s constructor wasn’t obj-C savvy so didn’t provide one.