mirror of
https://github.com/protocolbuffers/protobuf-go.git
synced 2024-12-29 12:17:48 +00:00
8a744307e3
messageInfo() looks like this: func (ms *messageState) messageInfo() *MessageInfo { mi := ms.LoadMessageInfo() if mi == nil { panic("invalid nil message info; this suggests memory corruption due to a race or shallow copy on the message struct") } return mi } func (ms *messageState) LoadMessageInfo() *MessageInfo { return (*MessageInfo)(atomic.LoadPointer((*unsafe.Pointer)(unsafe.Pointer(&ms.atomicMessageInfo)))) } Which is an atomic load and a predictable branch. On x86, this 64-bit load is just a MOV. On other platforms, like ARM64, there's actual atomics involved (LDAR). Meaning, it's cheap, but not free. Eliminate redundant copies of this (Common Subexpression Elimination). The newly added benchmarks improve by (geomean) 2.5%: $ benchstat pre post | head -10 goarch: amd64 cpu: AMD Ryzen Threadripper PRO 3995WX 64-Cores │ pre │ post │ │ sec/op │ sec/op vs base │ Extension/Has/None-12 106.4n ± 2% 104.0n ± 2% -2.21% (p=0.020 n=10) Extension/Has/Set-12 116.4n ± 1% 114.4n ± 2% -1.76% (p=0.017 n=10) Extension/Get/None-12 184.2n ± 1% 181.0n ± 1% -1.68% (p=0.003 n=10) Extension/Get/Set-12 144.5n ± 3% 140.7n ± 2% -2.63% (p=0.041 n=10) Extension/Set-12 227.2n ± 2% 218.6n ± 2% -3.81% (p=0.000 n=10) geomean 149.6n 145.9n -2.42% I didn't test on ARM64, but the difference should be larger due to the reduced atomics. Change-Id: I8eebeb6f753425b743368a7f5c7be4d48537e5c3 Reviewed-on: https://go-review.googlesource.com/c/protobuf/+/575036 Reviewed-by: Michael Stapelberg <stapelberg@google.com> LUCI-TryBot-Result: Go LUCI <golang-scoped@luci-project-accounts.iam.gserviceaccount.com> Reviewed-by: Damien Neil <dneil@google.com> Commit-Queue: Nicolas Hillegeer <aktau@google.com> Auto-Submit: Nicolas Hillegeer <aktau@google.com> |
||
---|---|---|
.. | ||
micro | ||
bench_test.go | ||
download_benchdata.bash |