]> Cypherpunks repositories - gostls13.git/commitdiff
cmd/compile: correct argument area size for typedmemmove/typedmemclr
authorCherry Zhang <cherryyz@google.com>
Wed, 7 Apr 2021 04:06:06 +0000 (00:06 -0400)
committerDavid Chase <drchase@google.com>
Wed, 7 Apr 2021 13:14:57 +0000 (13:14 +0000)
When the write barrier pass emits typedmemmove/typedmemclr calls,
even the arguments are in registers, we still need to leave space
for the spill slots. Count that space. Otherwise when the callee
spills arguments it may clobber locals on the caller's frame.

Change-Id: I5326943427feaf66cab7658a5bef55b3baf5d345
Reviewed-on: https://go-review.googlesource.com/c/go/+/307824
Trust: Cherry Zhang <cherryyz@google.com>
Run-TryBot: Cherry Zhang <cherryyz@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Than McIntosh <thanm@google.com>
Reviewed-by: David Chase <drchase@google.com>
src/cmd/compile/internal/ssa/writebarrier.go

index f0eceb7abe82b923872cadcab4382be095ef3eec..d6af3578d0a5e01a0ac320bc38cebc482240b91e 100644 (file)
@@ -494,36 +494,36 @@ func wbcall(pos src.XPos, b *Block, fn, typ *obj.LSym, ptr, val, mem, sp, sb *Va
        if typ != nil { // for typedmemmove
                taddr := b.NewValue1A(pos, OpAddr, b.Func.Config.Types.Uintptr, typ, sb)
                argTypes = append(argTypes, b.Func.Config.Types.Uintptr)
+               off = round(off, taddr.Type.Alignment())
                if inRegs {
                        wbargs = append(wbargs, taddr)
                } else {
-                       off = round(off, taddr.Type.Alignment())
                        arg := b.NewValue1I(pos, OpOffPtr, taddr.Type.PtrTo(), off, sp)
                        mem = b.NewValue3A(pos, OpStore, types.TypeMem, ptr.Type, arg, taddr, mem)
-                       off += taddr.Type.Size()
                }
+               off += taddr.Type.Size()
        }
 
        argTypes = append(argTypes, ptr.Type)
+       off = round(off, ptr.Type.Alignment())
        if inRegs {
                wbargs = append(wbargs, ptr)
        } else {
-               off = round(off, ptr.Type.Alignment())
                arg := b.NewValue1I(pos, OpOffPtr, ptr.Type.PtrTo(), off, sp)
                mem = b.NewValue3A(pos, OpStore, types.TypeMem, ptr.Type, arg, ptr, mem)
-               off += ptr.Type.Size()
        }
+       off += ptr.Type.Size()
 
        if val != nil {
                argTypes = append(argTypes, val.Type)
+               off = round(off, val.Type.Alignment())
                if inRegs {
                        wbargs = append(wbargs, val)
                } else {
-                       off = round(off, val.Type.Alignment())
                        arg := b.NewValue1I(pos, OpOffPtr, val.Type.PtrTo(), off, sp)
                        mem = b.NewValue3A(pos, OpStore, types.TypeMem, val.Type, arg, val, mem)
-                       off += val.Type.Size()
                }
+               off += val.Type.Size()
        }
        off = round(off, config.PtrSize)
        wbargs = append(wbargs, mem)