In the previous blog (http://blog.csdn.net/raintungli/article/details/7034005) mentioned in the signal forwarding thread, Attach Listener thread is only the operation of the socket file, Does not perform such as stack analysis, or heap analysis, the real worker thread is VM thread.
(i) Start VM thread
Jint THREADS::CREATE_VM (javavminitargs* args, bool* cantryagain) {
...
Create the Vmthread
{tracetime timer ("Start vmthread", tracestartuptime);
Vmthread::create ();
thread* vmthread = Vmthread::vm_thread ();
if (!os::create_thread (Vmthread, Os::vm_thread))
vm_exit_during_initialization ("Cannot create VM thread. Out of the system resources. ");
Wait for the VM thread to become ready, and Vmthread::run to initialize
//monitors can have spurious returns, must Always check another state flag
{
mutexlocker ml (notify_lock);
Os::start_thread (vmthread);
while (vmthread->active_handles () = = NULL) {
notify_lock->wait ()
;
}
}} ...
}
We can see that the thread VM thread is started in Thread.cpp, and here we have a little bit of talk about how the JVM starts threads in Linux.
Typically, booting a thread in Linux is called
int Pthread_create (pthread_t *__thread, __const pthread_attr_t *__attr,void * (*__start_routine) (void *), void *__arg) ;
In Java, it adds Os:create_thread--Initializing threads and os:start_thread--boot threads
Let's take a look at how the JVM is doing it in Linux.
The way to see Create_thread in Os_linux.cpp
BOOL Os::create_thread (thread* thread, Threadtype thr_type, size_t stack_size) {
....
int ret = Pthread_create (&tid, &attr, (void* (*) (void*)) Java_start, thread);
....
}
Keep looking at the Java_start method.
static void *java_start (Thread *thread) {
....
handshaking with parent thread
{
Mutexlockerex ml (sync, mutex::_no_safepoint_check_flag);
Notify parent thread
osthread->set_state (initialized);
Sync->notify_all ();
Wait until Os::start_thread () while
(osthread->get_state () = = initialized) {
sync->wait (mutex::_no_ Safepoint_check_flag);
}
Call one more level start routine
thread->run ();
return 0;
}
First, the JVM sets the state of the current thread to be initialized, and then notify all the threads,
while (osthread->get_state () = = initialized) {
Sync->wait (Mutex::_no_safepoint_check_flag);
}
Keep looking at the current state of the thread is not initialized, if so, call the Sync->wait () method to wait.
Look at the Os:start_thread method os.cpp
void Os::start_thread (thread* thread) {
//guard Suspend/resume
Mutexlockerex ml (thread->sr_lock (), Mutex: : _no_safepoint_check_flag);
osthread* osthread = Thread->osthread ();
Osthread->set_state (RUNNABLE);
Pd_start_thread (thread);
This time the thread state is set to Runnable, but no notify thread
In Pd_start_thread (thread), in Os_linux.cpp
void OS::p d_start_thread (thread* thread) {
Osthread * osthread = Thread->osthread ();
ASSERT (Osthread->get_state ()!= initialized, "just checking");
monitor* sync_with_child = Osthread->startthread_lock ();
Mutexlockerex ml (sync_with_child, mutex::_no_safepoint_check_flag);
Sync_with_child->notify ();
}
This time we saw the operation of the Notify thread
This is when the thread is notify, because the thread's state is runnable, the method Java_start continues to execute, and the Thread->run () method is called
The Vmthread::run method is invoked for thread VM thread
VmThread.cpp
void Vmthread::run () {
...
This->loop ();
...
}
The loop function is invoked to handle the Vm_operation queue's level and priority processing algorithm: You can refer to another blog: http://blog.csdn.net/raintungli/article/details/6553337
(ii) Jstack running in VM thread vm_operation
Jstack processing is the attach Listener thread that was mentioned in the previous blog operation
Static Jint Thread_dump (attachoperation* op, outputstream* out) {
bool print_concurrent_locks = false;
if (op->arg (0)!= NULL && strcmp (op->arg (0), "-l") = = 0) {
print_concurrent_locks = true;
}
Thread Stacks
vm_printthreads op1 (out, print_concurrent_locks);
Vmthread::execute (&OP1);
JNI Global handles
Vm_printjni OP2 (out);
Vmthread::execute (&OP2);
Deadlock detection
vm_finddeadlocks OP3 (out);
Vmthread::execute (&OP3);
return JNI_OK;
}
Simply look at the class Vm_printthreads it inherits Vm_operation
Class Vm_printthreads:public Vm_operation {
private:
outputstream* _out;
BOOL _print_concurrent_locks;
Public:
vm_printthreads () {_out = tty; _print_concurrent_locks = printconcurrentlocks;}
Vm_printthreads (outputstream* out, bool print_concurrent_locks) {_out = out; _print_concurrent_locks = Print_ Concurrent_locks; }
vmop_type Type () const {return vmop_printthreads}
void doit ();
BOOL Doit_prologue ();
void Doit_epilogue ();
When the call to Vmthread::execute () is the vm_printthreads into the _vm_queue, to VM thread processing, to VM thread to take out the vm_operation in the queue, And call the Doit method.
In Jstack, attach listener threads produce vm_printthreads,vm_printjni,vm_finddeadlocks 3 operations, which are handed to the thread processing of VM thread.