Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Go 1.26 リリースパーティ
Search
sivchari
February 26, 2026
170
0
Share
Go 1.26 リリースパーティ
sivchari
February 26, 2026
More Decks by sivchari
See All by sivchari
govalid ~ Type-safe validation tool ~
sivchari
0
99
Go1.25 リリースパーティ ~ nil pointer bug ~
sivchari
0
98
Google Developer Group - DevFest Tokyo 2025
sivchari
0
99
Who tests the Tests ?
sivchari
0
110
静的解析 x Kubernetes API Conventions = Kube API Linter ~ ベストプラクティスに準拠したカスタムリソースの作り方と運用 ~
sivchari
0
170
What's GOCACHEPROG ?
sivchari
1
530
gh_extensionsによる快適なOSS生活.pdf
sivchari
0
130
Visualization Go scheduler by gosched-simulator
sivchari
1
600
protoc pluginのはじめかた
sivchari
0
130
Featured
See All Featured
Building a A Zero-Code AI SEO Workflow
portentint
PRO
0
470
Are puppies a ranking factor?
jonoalderson
1
3.3k
The Art of Programming - Codeland 2020
erikaheidi
57
14k
Leveraging LLMs for student feedback in introductory data science courses - posit::conf(2025)
minecr
1
240
Mobile First: as difficult as doing things right
swwweet
225
10k
エンジニアに許された特別な時間の終わり
watany
106
240k
Templates, Plugins, & Blocks: Oh My! Creating the theme that thinks of everything
marktimemedia
31
2.8k
30 Presentation Tips
portentint
PRO
1
280
What’s in a name? Adding method to the madness
productmarketing
PRO
24
4k
WCS-LA-2024
lcolladotor
0
550
Marketing Yourself as an Engineer | Alaka | Gurzu
gurzu
0
180
What Being in a Rock Band Can Teach Us About Real World SEO
427marketing
0
220
Transcript
Go 1.26 リリースパーティ goroutine leak profileについて The Go gopher was
designed by Renee French
もくじ • goroutine leak profileとは • goroutine leakの検出方法 • goroutine
leakを検出できないケース • まとめ
自己紹介 渋谷拓真 Go Conference メインオーガナイザー OSS ◦ Kubernetes メンテナー ◦
Argo CD メンテナー Kubernetes 2025 Contributor Award 3Dプリンターにハマってます
goroutine leak profileとは
goroutine leak profileとは Go 1.26で追加された新しい pprof profile • CL#688335 •
ブロックされており復帰不可能な goroutineを検出する • GCの到達可能性を利用する • 1.26ではGOEXPERIMENTで、1.27からはデフォルトになる予定
goroutine leak profileとは GOEXPERIMENT=goroutineleakprofile go build -o myapp • net/http/pprof
• runtime/pprof goroutine 123 [chan send] (leaked): main.leaky.func1() /path/to/main.go:25 +0x1c created by main.leaky in goroutine 1 /path/to/main.go:24 +0x2c
goroutine leakの検出方法
goroutine leak profileの検出方法 内部でgoroutineleak profileがリクエストされた時にトリガーされる net/httpでもruntime/pprofでも(&Profile).WriteToが呼ばれる var goroutineLeakProfile = &Profile{
name: "goroutineleak", count: runtime_goroutineleakcount, write: writeGoroutineLeak, }
writeGoroutineLeak リーク検出用の GCをトリガーする関数を呼ぶ runtime_goroutineLeakGC() //golinkename runtime_goroutineLeakGC runtime.goroutineLeakGC func runtime_goroutineLeakGC()
runtime_goroutineLeakGC goroutineLeakを確認するチェックをつける func goroutineLeakGC() { work.goroutineLeak.pending.Store(true) for work.goroutineLeak.pending.Load() { GC()
} }
なぜGCに組み込むのか リーク検出は特定の goroutineを操作できない状態 • GCは到達不可能なオブジェクトを削除する • GCのマークを活用することで到達可能性を検出できる
しかしそのまま使いまわせない Goは内部でallgsという変数から全ての goroutineに到達できてしまう • waiting(*sudog)を使用してブロッキングかどうかは確認できてしまう • ブロッキングでも参照できてしまいリークかどうかわからなくなる allgs → blocking
g → sudog → c → blocking channel
maybeTraceablePtrの導入 リーク検出時の GCでは追跡を行わないようにポインタを nilにする • nilのため以降の GCで追跡対象に含めないようにする • リーク検出後にマークして追跡対象に戻すため回収されてしまうリスクは 回避している
gcPrepareMarkToots goroutine leakを検出する場合はソートして先頭実行可能・末尾ブロック中 に並べ替える if work.goroutineLeak.enabled { work.stackRoots, work.nMaybeRunnableStackRoots =
allGsSnapshotSortedForGC() } else { work.stackRoots = allGsSnapshot() work.nMaybeRunnableStackRoots = len(work.stackRoots) }
findGoroutineLeaks マーク完了後に Eventually Runnableでなければリークとみなす if findMaybeRunnableGoroutines() { return false }
for i := work.nMaybeRunnableStackRoots; i < work.nStackRoots; i++ { gp := work.stackRoots[i] casgstatus(gp, _Gwaiting, _Gleaked) shadePrimitivesOnLeak(gp) }
Eventually Runnableとは 実行可能な sudogのchannelがマークされている • 実行可能な goroutineがアクセスできる • リークを疑われていたがリークではないと考える
Eventually Runnableとは 実行可能な sudogのchannelがマークされている • 実行可能な goroutineがアクセスできる • リークを疑われていたがリークではないと考える
findGoroutineLeaks sharedPrimitivesOnLeakでリーク対象もマーキングして回収防止 if findMaybeRunnableGoroutines() { return false } for i
:= work.nMaybeRunnableStackRoots; i < work.nStackRoots; i++ { gp := work.stackRoots[i] casgstatus(gp, _Gwaiting, _Gleaked) shadePrimitivesOnLeak(gp) }
goroutine leakを検出できないケース
一部ケースは検出できない 銀の弾丸ではない • グローバル変数に定義されている • グローバルはマークされてしまう ◦ Eventually Runnableと判定 var
ch = make(chan int) func leaky() { go func() { ch <- 42 }() }
一部ケースは検出できない 銀の弾丸ではない • ローカル変数で使用されている • fがforで実行されて runnable ◦ Eventually Runnableと判定
• forのなかでchのselectがあったら ◦ waitingとなり検出される func leaky() { ch := make(chan int) go f(ch) go func() { ch <- 42 }() } func f(ch chan int) { for {} }
まとめ
まとめ • Go1.26からgoroutine leakを検出できるようになった • GCの持つ到達可能性の追跡を活用している • uberのgoleakと併用して lekaを防止しよう!
ありがとうございました!
おしらせ