当前位置: 首页 > news >正文

Golang中的runtime.LockOSThread 和 runtime.UnlockOSThread

在runtime中有`runtime.LockOSThread 和 runtime.UnlockOSThread 两个函数,这两个函数有什么作用呢?我们看一下标准库中对它们的解释。

runtime.LockOSThread

// LockOSThread wires the calling goroutine to its current operating system thread.
// The calling goroutine will always execute in that thread,
// and no other goroutine will execute in it,
// until the calling goroutine has made as many calls to
// UnlockOSThread as to LockOSThread.
// If the calling goroutine exits without unlocking the thread,
// the thread will be terminated.
//
// All init functions are run on the startup thread. Calling LockOSThread
// from an init function will cause the main function to be invoked on
// that thread.
//
// A goroutine should call LockOSThread before calling OS services or
// non-Go library functions that depend on per-thread state.

调用 LockOSThread绑定 当前 goroutine 到当前 操作系统线程``,此 goroutine 将始终在此线程执行,其它 goroutine 则无法在此线程中得到执行,直到当前调用线程执行了 UnlockOSThread 为止(也就是说指定一个goroutine 独占 一个系统线程);

如果调用者goroutine 在未解锁线程(UnlockOSThread)之前直接退出,则当前线程将直接被终止(也就是说线程被直接销毁)。

我们知道在golang中创建的线程正常情况下是无法被销毁的,但通过这种hack用法则可以将其销毁,参考《极端情况下收缩 Go 的线程数》

所有 init函数 都运行在启动线程。如果在一个 init函数 中调用了 LockOSThread 则导致 main 函数被执行在当前线程。

goroutine应该在调用依赖于每个线程状态的 OS服务 或 非Go库函数 之前调用 LockOSThread

总结

LockOSThread 是用来对 goroutine 与系统线程的关系进行绑定,起到独占系统线程的使用,带来的影响是会导致其它 goroutine 无法在当前系统线程中得到执行(goroutine的调度机制),除非调用 UnlockOSThread

嵌套调用

另外还有一种情况是 嵌套调用 LockOSThreadUnlockOSThred 的情况。即当前 goroutine 里调用了LockOSThread, 同时又创建了一个新的goroutine的情况,官方对此进行了解释 https://tip.golang.org/doc/go1.10#runtime 。子协程是不会继承父协程的 LockOSThread 特性的。

runtime.UnlockOSThread

// UnlockOSThread undoes an earlier call to LockOSThread.
// If this drops the number of active LockOSThread calls on the
// calling goroutine to zero, it unwires the calling goroutine from
// its fixed operating system thread.
// If there are no active LockOSThread calls, this is a no-op.
//
// Before calling UnlockOSThread, the caller must ensure that the OS
// thread is suitable for running other goroutines. If the caller made
// any permanent changes to the state of the thread that would affect
// other goroutines, it should not call this function and thus leave
// the goroutine locked to the OS thread until the goroutine (and
// hence the thread) exits.

UnlockOSThread 用于取消对 LockOSThread 的调用。

如果将调用 goroutine 的活跃 LockOSThread 调用数减为零,它从其固定的操作系统线程中取消调用 goroutine。即如果多次调用 LockOSThread,则必须将 UnlockOSThread 调用相同的次数才能解锁线程。

如果没有活跃的 LockOSThread 调用,则这是一个空操作。

在调用 UnlockOSThread 之前,调用者要确保当前线程适合运行其它goroutine。如果调用者对线程的状态做了任何永久性的更改,这将影响其他goroutine,那么它不应该调用此函数,从而使goroutine锁定到OS线程,直到goroutine(以及线程)退出,此时系统线程直接被销毁。

总结

UnlockOSThread 是对 LockOSThread 的反向操作,即解锁。用户可能在 LockOSThread 期间对操作系统线程进行了修改,所以有可能不再适合其它goroutine在当前系统线程运行,这种情况下就不再需要调用 UnlockOSThread,而是直接等待goroutine执行完毕自动退出。

参考资料

  • https://tip.golang.org/doc/go1.10#runtime
  • https://stackoverflow.com/questions/25361831/benefits-of-runtime-lockosthread-in-golang
  • http://xiaorui.cc/archives/5320
  • 极端情况下收缩 Go 的线程数


喜欢的朋友记得点赞、收藏、关注哦!!!

相关文章:

  • RabbitMQ通信模式(Simplest)Python示例
  • 百度飞桨OCR(PP-OCRv4_server_det|PP-OCRv4_server_rec_doc)文本识别-Java项目实践
  • Python函数——万字详解
  • 算法题(150):拼数
  • 用Python将 PDF 中的表格提取为 Excel/CSV
  • OpenCV计算机视觉实战(6)——经典计算机视觉算法
  • Python60日基础学习打卡D30
  • LangChain多模态智能体:文生图、识图、RAG问答与小说生成全攻略
  • Apidog MCP服务器,连接API规范和AI编码助手的桥梁
  • Linux环境搭载
  • 使用MCP驱动IDA pro分析样本
  • MongoDB的管道聚合
  • 物联网之使用Vertx实现HTTP/WebSocket最佳实践
  • WordPress搜索引擎优化的最佳重定向插件:入门指南
  • 146. LRU 缓存
  • C++字符串处理:`std::string`和`std::string_view`的区别与使用
  • R 语言科研绘图第 49 期 --- 热力图-相关性
  • Geotools中关于坐标转换纬度超限问题
  • vue2、vue3项目打包生成txt文件-自动记录打包日期:git版本、当前分支、提交人姓名、提交日期、提交描述等信息 和 前端项目的版本号json文件
  • 物联网数据湖架构
  • 这位中国电影早期的全能奇才,90年前唱响国歌
  • 证监会副主席李明:近期将出台深化科创板、创业板改革政策措施
  • 去年上海全市博物馆接待观众约4087万人次,同比增31.9%
  • 受贿1.29亿余元,黑龙江省原副省长王一新被判无期
  • 女子七年后才知银行卡被盗刷18万元,警方抓获其前男友
  • 长沙查处疑似非法代孕:有人企图跳窗,有女子被麻醉躺手术台