hotspot/src/share/vm/runtime/interfaceSupport.hpp
// Change threadstate in a manner, so safepoint can detect changes.
// Time-critical: called on exit from every runtime routine
static inline void transition(JavaThread *thread, JavaThreadState from, JavaThreadState to) {
{- -------------------------------------------
(1) (assert)
---------------------------------------- -}
assert(from != _thread_in_Java, "use transition_from_java");
assert(from != _thread_in_native, "use transition_from_native");
assert((from & 1) == 0 && (to & 1) == 0, "odd numbers are transitions states");
assert(thread->thread_state() == from, "coming from wrong thread state");
{- -------------------------------------------
(1) 処理対象のスレッドの JavaThreadState を (from+1) に変更する.
なお, MP 環境の場合には
VM Thread 側への visibility (sequential consistency) を保証する必要があるので,
変更後に以下のどちらかを行っている (See: SafepointSynchronize::begin()).
* UseMembar オプションが指定されている場合:
OrderAccess::fence() でメモリバリアを張る.
* そうではない場合:
os::write_memory_serialize_page() で serialize page への書き込みを行う.
---------------------------------------- -}
// Change to transition state (assumes total store ordering! -Urs)
thread->set_thread_state((JavaThreadState)(from + 1));
// Make sure new state is seen by VM thread
if (os::is_MP()) {
if (UseMembar) {
// Force a fence between the write above and read below
OrderAccess::fence();
} else {
// store to serialize page so VM thread can do pseudo remote membar
os::write_memory_serialize_page(thread);
}
}
{- -------------------------------------------
(1) もし Safepoint が開始されていたら (= SafepointSynchronize::do_call_back() が true ならば),
SafepointSynchronize::block() を呼んでブロックする.
---------------------------------------- -}
if (SafepointSynchronize::do_call_back()) {
SafepointSynchronize::block(thread);
}
{- -------------------------------------------
(1) 処理対象のスレッドの JavaThreadState を, to 引数の値に変更する.
---------------------------------------- -}
thread->set_thread_state(to);
{- -------------------------------------------
(1) (デバッグ用の処理) (CHECK_UNHANDLED_OOPS_ONLY 時にのみ実行) (See: UnhandledOops)
unhandled oop をクリアする (? #TODO)
---------------------------------------- -}
CHECK_UNHANDLED_OOPS_ONLY(thread->clear_unhandled_oops();)
}
This document is available under the GNU GENERAL PUBLIC LICENSE Version 2.