]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/compile: use better line numbers for write barriers
authorKeith Randall <khr@golang.org>
Mon, 21 Aug 2023 21:10:24 +0000 (14:10 -0700)
committerKeith Randall <khr@golang.org>
Tue, 22 Aug 2023 15:11:33 +0000 (15:11 +0000)
When the write barrier does several pointer writes under one
write barrier flag check, the line numbers aren't really correct.

The writes inside the write barrier have a confusing set of positions.
The loads of the old values are given the line number of the
corresponding store instruction, but the stores into the write buffer
are given the line number of the first store. Instead, give them all
line numbers corresponding to the store instruction.

The writes at the merge point, which are the original writes and the
only ones that happen when the barrier is off, are currently all given
the line number of the first write. Instead give them their original
line number.

Change-Id: Id64820b707f45f07b0978f8d03c97900fdc4bc0b
Reviewed-on: https://go-review.googlesource.com/c/go/+/521499
Reviewed-by: Keith Randall <khr@google.com>
TryBot-Result: Gopher Robot <gobot@golang.org>
Reviewed-by: David Chase <drchase@google.com>
Run-TryBot: Keith Randall <khr@golang.org>

src/cmd/compile/internal/ssa/writebarrier.go

index bd9e0b826829a8f39e8cb3fed4bb0ede837d0c13..64c95662f8adbd12d75485dadf67bc8ac2cda940 100644 (file)
@@ -353,7 +353,7 @@ func writebarrier(f *Func) {
                memThen := mem
                var curCall *Value
                var curPtr *Value
-               addEntry := func(v *Value) {
+               addEntry := func(pos src.XPos, v *Value) {
                        if curCall == nil || curCall.AuxInt == maxEntries {
                                t := types.NewTuple(types.Types[types.TUINTPTR].PtrTo(), types.TypeMem)
                                curCall = bThen.NewValue1(pos, OpWB, t, memThen)
@@ -394,7 +394,7 @@ func writebarrier(f *Func) {
                        val := w.Args[1]
                        if !srcs.contains(val.ID) && needWBsrc(val) {
                                srcs.add(val.ID)
-                               addEntry(val)
+                               addEntry(pos, val)
                        }
                        if !dsts.contains(ptr.ID) && needWBdst(ptr, w.Args[2], zeroes) {
                                dsts.add(ptr.ID)
@@ -407,7 +407,7 @@ func writebarrier(f *Func) {
                                // combine the read and the write.
                                oldVal := bThen.NewValue2(pos, OpLoad, types.Types[types.TUINTPTR], ptr, memThen)
                                // Save old value to write buffer.
-                               addEntry(oldVal)
+                               addEntry(pos, oldVal)
                        }
                        f.fe.Func().SetWBPos(pos)
                        nWBops--
@@ -449,6 +449,7 @@ func writebarrier(f *Func) {
 
                // Do raw stores after merge point.
                for _, w := range stores {
+                       pos := w.Pos
                        switch w.Op {
                        case OpStoreWB:
                                ptr := w.Args[0]