RFR(XS): VM times out in VM_HandshakeAllThreads::doit() with RunThese30M
Daniel D. Daugherty
daniel.daugherty at oracle.com
Wed Aug 15 20:02:18 UTC 2018
On 8/15/18 7:12 AM, Robbin Ehn wrote:
> Hi David, truncated:
>
> On 2018-08-15 12:40, David Holmes wrote:
>> The context in which this is executed is not at all clear so
>> assessing the suitability of the fix is also not clear. IIRC a thread
>> can only be resumed at a safepoint so if the above code executes in
>> the VMThread then it can't be racing with a resume and the
>> Threads_lock holding seems unnecessary wrt. this action. ??
>
> The context is, VM thread calls this method to figure out if he can
> executed the handshake on behalf of the thread in question.
>
> JavaThread::java_resume which does the notify on SR lock, says:
>
> // We need to guarantee the Threads_lock here, since resumes are not
> // allowed during safepoint synchronization
> // Can only resume from an external suspension
> void JavaThread::java_resume() {
>
> And if you look at java_suspend_self() after getting the notification
> I see nothing that would keep it from continue executing e.g. java
> code. It can be here with state _thread_in_Java since we skip the
> proper transitions, thus not even needing todo a transition to
> continue execute java code.
>
> Is there something I'm missing?
External Java thread suspend can come in from a couple of places:
- JVM/TI SuspendThread() and SuspendThreadList()
- JVM_SuspendThread() which is used by java.lang.Thread.suspend()
External Java thread resume can come in from a a couple of places:
- JVM/TI ResumeThread() and ResumeThreadList()
- JVM_ResumeThread() which is used by java.lang.Thread.resume()
JavaThread::java_resume() has this:
assert_locked_or_safepoint(Threads_lock);
The two places that call JavaThread::java_resume() have this:
MutexLocker ml(Threads_lock);
before the call.
So if HandshakeState::vmthread_can_process_handshake() is only
called by the VMThread while at a safepoint, then the target
JavaThread cannot be externally resumed while that function is
running so this new check:
+ return SafepointSynchronize::safepoint_safe(target,
target->thread_state()) ||
+ target->is_ext_suspended();
is okay because that externally suspended thread is also safepoint safe.
This assert:
+ assert(Threads_lock->owned_by_self(), "Not holding Threads_lock.");
doesn't quite match your intent. If
HandshakeState::vmthread_can_process_handshake()
should only be called by the VMThread at a safepoint, then a different
check would be better:
assert(SafepointSynchronize::is_at_safepoint() &&
Thread::current()->is_VM_thread(),
"must be VMThread at a safepoint");
Perhaps this for your comment:
// SafepointSynchronize::safepoint_safe() does not consider an externally
// suspended thread to be safe. However, if we are at a safepoint, then
// the externally suspended thread cannot be resumed so it is safe.
Dan
>
> Thanks, Robbin
>
>>
>> Thanks,
>> David
>>
More information about the hotspot-runtime-dev
mailing list