线程(一)OpenJDK 17 中线程启动的完整流程用C++ 源码详解

1. 线程创建入口(JNI 层)

当 Java 层调用 Thread.start() 时,JVM 通过 JNI 进入 JVM_StartThread 函数:

JVM_ENTRY(void, JVM_StartThread(JNIEnv* env, jobject jthread))
  // 1. 检查线程状态,防止重复启动
  if (java_lang_Thread::thread(jthread) != NULL) {
    throw_illegal_thread_state = true; // 已启动则抛异常
  } else {
    // 2. 创建 JavaThread 对象,分配栈大小
    size_t sz = (size > 0) ? (size_t)size : 0;
    native_thread = new JavaThread(&thread_entry, sz); 
    // 3. 绑定 Java 线程对象与 Native 线程
    native_thread->prepare(jthread);
  }
  // 4. 启动线程
  Thread::start(native_thread);
JVM_END
  • 关键点:

    • 通过 JavaThread 封装线程信息,包括栈大小和入口函数 thread_entry

    • prepare() 方法将 Java 层的 Thread 对象与 JavaThread 关联。


2. 操作系统线程启动(POSIX 线程)

通过 pthread_create 创建操作系统线程:

int ret = pthread_create(&tid, &attr, thread_native_entry, thread);
  • 入口函数 thread_native_entry

    • 栈初始化:记录栈基址和大小,随机化栈空间(非 GLIBC 环境)以优化缓存。

    • 线程状态同步:使用 Monitor 通知父线程初始化完成,并等待唤醒。

    • 执行主逻辑:调用 thread->call_run(),最终进入 JavaThread::run()


3. JVM 线程主逻辑(JavaThread::run)

void JavaThread::run() {
  initialize_tlab(); // 初始化线程本地分配缓冲区
  _stack_overflow_state.create_stack_guard_pages(); // 栈溢出保护
  ThreadStateTransition::transition(this, _thread_new, _thread_in_vm); // 状态转换
  set_active_handles(JNIHandleBlock::allocate_block()); // 分配 JNI 句柄块
  thread_main_inner(); // 进入实际执行逻辑
}
  • 关键操作:

    • TLAB 初始化:提升对象分配效率。

    • 安全点同步:通过状态转换确保线程进入安全点。

    • 调用 thread_main_inner:最终执行 Java 代码。


4. 执行 Java 层 run() 方法

void JavaThread::thread_main_inner() {
  if (!has_pending_exception()) {
    this->entry_point()(this, this); // 调用 thread_entry
  }
}

static void thread_entry(JavaThread* thread, TRAPS) {
  JavaCalls::call_virtual(&result, obj, vmClasses::Thread_klass(),
                          vmSymbols::run_method_name(), THREAD);
}
  • 最终跳转:通过 JavaCalls 调用 Java Thread 对象的 run() 方法,实现从 Native 到 Java 的过渡。


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值