From: Ian Lance Taylor Date: Sat, 29 Jul 2023 15:59:20 +0000 (-0700) Subject: sync: panic rather than throw on nil *Pool X-Git-Tag: go1.22rc1~1465 X-Git-Url: http://www.git.cypherpunks.su/?a=commitdiff_plain;h=be0e0b06ac53d3d02ea83b479790404057b6f19b;p=gostls13.git sync: panic rather than throw on nil *Pool Fixes #61651 Change-Id: I27d581719e6bf38910f9d47dcf023bbff74ddf72 Reviewed-on: https://go-review.googlesource.com/c/go/+/514037 Reviewed-by: Rob Pike Reviewed-by: Austin Clements Reviewed-by: Ian Lance Taylor Auto-Submit: Ian Lance Taylor Run-TryBot: Ian Lance Taylor TryBot-Result: Gopher Robot Run-TryBot: Ian Lance Taylor --- diff --git a/src/sync/pool.go b/src/sync/pool.go index cf01e2e189..ffab67bf19 100644 --- a/src/sync/pool.go +++ b/src/sync/pool.go @@ -196,6 +196,13 @@ func (p *Pool) getSlow(pid int) any { // returns poolLocal pool for the P and the P's id. // Caller must call runtime_procUnpin() when done with the pool. func (p *Pool) pin() (*poolLocal, int) { + // Check whether p is nil to get a panic. + // Otherwise the nil dereference happens while the m is pinned, + // causing a fatal error rather than a panic. + if p == nil { + panic("nil Pool") + } + pid := runtime_procPin() // In pinSlow we store to local and then to localSize, here we load in opposite order. // Since we've disabled preemption, GC cannot happen in between. diff --git a/src/sync/pool_test.go b/src/sync/pool_test.go index 5e38597441..1b6746dbfb 100644 --- a/src/sync/pool_test.go +++ b/src/sync/pool_test.go @@ -247,6 +247,28 @@ func testPoolDequeue(t *testing.T, d PoolDequeue) { } } +func TestNilPool(t *testing.T) { + catch := func() { + if recover() == nil { + t.Error("expected panic") + } + } + + var p *Pool + t.Run("Get", func(t *testing.T) { + defer catch() + if p.Get() != nil { + t.Error("expected empty") + } + t.Error("should have panicked already") + }) + t.Run("Put", func(t *testing.T) { + defer catch() + p.Put("a") + t.Error("should have panicked already") + }) +} + func BenchmarkPool(b *testing.B) { var p Pool b.RunParallel(func(pb *testing.PB) {