Hotspot源码解析-第十二章-OS线程绑定

12.2 OS线程绑定

12.2.1 os_linux.cpp

12.2.1.1 create_main_thread

这个函数的入口函数是thread.cpp->set_as_starting_thread()

bool os::create_main_thread(JavaThread* thread) {
  // 断言判断,主线程必须是当前线程,否则抛出异常退出
  assert(os::Linux::_main_thread == pthread_self(), "should be called inside main thread");
  return create_attached_thread(thread);
}

bool os::create_attached_thread(JavaThread* thread) {
#ifdef ASSERT
    thread->verify_not_published(); // 验证线程还没发布出去,Threads_lock锁的持有者还是当前线程
#endif

  // 创建并分配 OSThread 对象,看`章节12.2.1.1.1`
  OSThread* osthread = new OSThread(NULL, NULL);

  if (osthread == NULL) {
    return false;
  }

  // Store pthread info into the OSThread
  // 内核级的线程唯一id
  osthread->set_thread_id(os::Linux::gettid());
  // 函数库级的pthread id,也可以称为线程id,每个进程有多个线程,不同的进程之间,线程id可能相同,但是内核级的线程id是唯一的,不会相同
  osthread->set_pthread_id(::pthread_self()); // 当前线程的pthread id

  // 初始化浮点计算单元
  os::Linux::init_thread_fpu_state();

  // 初始化线程状态为 RUNNABLE
  osthread->set_state(RUNNABLE);
  // 将OSThread绑定到JavaThread中
  thread->set_osthread(osthread);

  if (UseNUMA) {
    int lgrp_id = os::numa_get_group_id();
    if (lgrp_id != -1) {
      thread->set_lgrp_id(lgrp_id);
    }
  }

  if (os::is_primordial_thread()) {

    JavaThread *jt = (JavaThread *)thread;
    // 获取线程栈的黄页区基址,细节看`章节12.3 线程栈保护区`的介绍
    address addr = jt->stack_yellow_zone_base();
    assert(addr != NULL, "initialization problem?");
    assert(jt->stack_available(addr) > 0, "stack guard should not be enabled");
   // 扩展线程栈空间(保护区)
    osthread->set_expanding_stack();
    os::Linux::manually_expand_stack(jt, addr);
    osthread->clear_expanding_stack();
  }

  // 初始化线程的信号屏蔽号
  os::Linux::hotspot_sigmask(thread);

  return true;
}
12.2.1.1.1 创建OSThread
OSThread::OSThread(OSThreadStartFunc start_proc, void* start_parm) {
  pd_initialize(); // 调用函数OSThread::pd_initialize完成os线程的初始化
  set_start_proc(start_proc);
  set_start_parm(start_parm);
  set_interrupted(false);
}

// 这个函数在osThread_linux.cpp源码中
void OSThread::pd_initialize() {
  assert(this != NULL, "check");
  _thread_id        = 0;  // 内核级线程id置为0
  _pthread_id       = 0;  // 对应pthread id,用在函数库中
  _siginfo = NULL;
  _ucontext = NULL;
  _expanding_stack = 0;
  _alt_sig_stack = NULL;

  sigemptyset(&_caller_sigmask); // 将信号集置空
  // 线程启动锁定义
  _startThread_lock = new Monitor(Mutex::event, "startThread_lock", true);
  assert(_startThread_lock !=NULL, "check");
}

你可能感兴趣的:(Java虚拟机,java)