openjdk9 on Freebsd

David Holmes david.holmes at oracle.com
Fri Mar 18 04:02:29 UTC 2016


Thomas writes:
> Hi Brian,
>
>
>> The next patches where less straightforward.  When running java I was
>> getting a ton of messages like:
>> Thread 832744400 has exited with leftover thread-specific data after 4
>> destructor iterations
>> After doing a lot of digging and debugging on Linux, I found the code path
>> for Linux was identical for Freebsd and the cleanup destructor was being
>> executed 4 times just like Freebsd, the difference being that Freebsd would
>> print out this benign warning while Linux would just ignore it.  The
>> problem is that all threads that are created and initialize TLS current
>> thread data, must clean them up by explicitly setting the TLS current
>> thread to null.  I’ve come up with two approaches to accomplish this.
>>
>> clean up TLS current thread at end of ::run functions similar to how it's
>> done in openjdk8.
>>
>> http://brian.timestudybuddy.com/webrev/hotspot__clear_thread_current/webrev/
>> clear current thread before exiting java_start to avoid warnings from
>> leftover pthread_setspecific data
>>
>> http://brian.timestudybuddy.com/webrev/hotspot__clear_thread_current_alt/webrev/
>>
>>
>>
> I do not think this is a real leak. From what I remember of how the glibc
> implements TLS, setting the TLS slot value to NULL would not in itself
> delete anything. In VM, this slot keeps the pointer to the current Thread*,
> which is correctly deleted at the end of the thread (void
> JavaThread::thread_main_inner()).
>
> Digging further, I found the pthread key destructor
> "restore_thread_pointer(void* p)" in threadLocalStorage_posix.cpp:
>
> // Restore the thread pointer if the destructor is called. This is in case
> // someone from JNI code sets up a destructor with pthread_key_create to run
> // detachCurrentThread on thread death. Unless we restore the thread
> pointer we
> // will hang or crash. When detachCurrentThread is called the key will be
> set
> // to null and we will not be called again. If detachCurrentThread is never
> // called we could loop forever depending on the pthread implementation.
> extern "C" void restore_thread_pointer(void* p) {
>   ThreadLocalStorage::set_thread((Thread*) p);
> }
>
> So, it seems we even reset deliberately the thread pointer to a non-NULL
> value. The comment claims that we reset the Thread* value in case there is
> another user-provided destructor which runs afterwards and which
> does detachCurrentThread () which would require Thread::current() to work.
> But there a details I do not understand:
>
> - At this point, should the Thread* object not already be deallocated, so
> this would be a dangling pointer anyway?
>
> - Also, according to Posix, this is unspecified. Doc on
> pthread_setspecific() states: "Calling pthread_setspecific() from a
> thread-specific data destructor routine may result either in lost storage
> (after at least PTHREAD_DESTRUCTOR_ITERATIONS attempts at destruction) or
> in an infinite loop."
>
> - In jdk8, we did reset the slot value to NULL before Thread exit. So, in
> this case detachCurrentThread() from a pthread_key destructor should not
> have worked at all.
>
> Could someone from Oracle maybe shed light on this?

Please see the following discussion and bug report:

http://mail.openjdk.java.net/pipermail/hotspot-runtime-dev/2014-February/010759.html

Note I don't follow this list so please include me directly in any 
follow-ups if needed.

Thanks,
David


More information about the bsd-port-dev mailing list