mirror of https://github.com/golang/go.git
cmd/compile: intrinsify runtime.getcallerpc on all link register architectures
Add a compiler intrinsic for getcallerpc on following architectures: arm mips mipsle mips64 mips64le ppc64 ppc64le s390x Change-Id: I758f3d4742fc214b206bcd07d90408622c17dbef Reviewed-on: https://go-review.googlesource.com/110835 Run-TryBot: Wei Xiao <Wei.Xiao@arm.com> TryBot-Result: Gobot Gobot <gobot@golang.org> Reviewed-by: Cherry Zhang <cherryyz@google.com>
This commit is contained in:
parent
836fe697c4
commit
20102594a0
|
|
@ -797,6 +797,10 @@ func ssaGenValue(s *gc.SSAGenState, v *ssa.Value) {
|
||||||
p.From.Name = obj.NAME_PARAM
|
p.From.Name = obj.NAME_PARAM
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = v.Reg()
|
p.To.Reg = v.Reg()
|
||||||
|
case ssa.OpARMLoweredGetCallerPC:
|
||||||
|
p := s.Prog(obj.AGETCALLERPC)
|
||||||
|
p.To.Type = obj.TYPE_REG
|
||||||
|
p.To.Reg = v.Reg()
|
||||||
case ssa.OpARMFlagEQ,
|
case ssa.OpARMFlagEQ,
|
||||||
ssa.OpARMFlagLT_ULT,
|
ssa.OpARMFlagLT_ULT,
|
||||||
ssa.OpARMFlagLT_UGT,
|
ssa.OpARMFlagLT_UGT,
|
||||||
|
|
|
||||||
|
|
@ -2830,10 +2830,11 @@ func init() {
|
||||||
},
|
},
|
||||||
all...)
|
all...)
|
||||||
|
|
||||||
addF("runtime", "getcallerpc",
|
add("runtime", "getcallerpc",
|
||||||
func(s *state, n *Node, args []*ssa.Value) *ssa.Value {
|
func(s *state, n *Node, args []*ssa.Value) *ssa.Value {
|
||||||
return s.newValue0(ssa.OpGetCallerPC, s.f.Config.Types.Uintptr)
|
return s.newValue0(ssa.OpGetCallerPC, s.f.Config.Types.Uintptr)
|
||||||
}, sys.AMD64, sys.I386, sys.ARM64)
|
},
|
||||||
|
all...)
|
||||||
|
|
||||||
add("runtime", "getcallersp",
|
add("runtime", "getcallersp",
|
||||||
func(s *state, n *Node, args []*ssa.Value) *ssa.Value {
|
func(s *state, n *Node, args []*ssa.Value) *ssa.Value {
|
||||||
|
|
|
||||||
|
|
@ -768,6 +768,10 @@ func ssaGenValue(s *gc.SSAGenState, v *ssa.Value) {
|
||||||
p.From.Name = obj.NAME_PARAM
|
p.From.Name = obj.NAME_PARAM
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = v.Reg()
|
p.To.Reg = v.Reg()
|
||||||
|
case ssa.OpMIPSLoweredGetCallerPC:
|
||||||
|
p := s.Prog(obj.AGETCALLERPC)
|
||||||
|
p.To.Type = obj.TYPE_REG
|
||||||
|
p.To.Reg = v.Reg()
|
||||||
case ssa.OpClobber:
|
case ssa.OpClobber:
|
||||||
// TODO: implement for clobberdead experiment. Nop is ok for now.
|
// TODO: implement for clobberdead experiment. Nop is ok for now.
|
||||||
default:
|
default:
|
||||||
|
|
|
||||||
|
|
@ -739,6 +739,10 @@ func ssaGenValue(s *gc.SSAGenState, v *ssa.Value) {
|
||||||
p.From.Name = obj.NAME_PARAM
|
p.From.Name = obj.NAME_PARAM
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = v.Reg()
|
p.To.Reg = v.Reg()
|
||||||
|
case ssa.OpMIPS64LoweredGetCallerPC:
|
||||||
|
p := s.Prog(obj.AGETCALLERPC)
|
||||||
|
p.To.Type = obj.TYPE_REG
|
||||||
|
p.To.Reg = v.Reg()
|
||||||
case ssa.OpClobber:
|
case ssa.OpClobber:
|
||||||
// TODO: implement for clobberdead experiment. Nop is ok for now.
|
// TODO: implement for clobberdead experiment. Nop is ok for now.
|
||||||
default:
|
default:
|
||||||
|
|
|
||||||
|
|
@ -431,6 +431,11 @@ func ssaGenValue(s *gc.SSAGenState, v *ssa.Value) {
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = v.Reg()
|
p.To.Reg = v.Reg()
|
||||||
|
|
||||||
|
case ssa.OpPPC64LoweredGetCallerPC:
|
||||||
|
p := s.Prog(obj.AGETCALLERPC)
|
||||||
|
p.To.Type = obj.TYPE_REG
|
||||||
|
p.To.Reg = v.Reg()
|
||||||
|
|
||||||
case ssa.OpPPC64LoweredRound32F, ssa.OpPPC64LoweredRound64F:
|
case ssa.OpPPC64LoweredRound32F, ssa.OpPPC64LoweredRound64F:
|
||||||
// input is already rounded
|
// input is already rounded
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -509,6 +509,10 @@ func ssaGenValue(s *gc.SSAGenState, v *ssa.Value) {
|
||||||
p.From.Name = obj.NAME_PARAM
|
p.From.Name = obj.NAME_PARAM
|
||||||
p.To.Type = obj.TYPE_REG
|
p.To.Type = obj.TYPE_REG
|
||||||
p.To.Reg = v.Reg()
|
p.To.Reg = v.Reg()
|
||||||
|
case ssa.OpS390XLoweredGetCallerPC:
|
||||||
|
p := s.Prog(obj.AGETCALLERPC)
|
||||||
|
p.To.Type = obj.TYPE_REG
|
||||||
|
p.To.Reg = v.Reg()
|
||||||
case ssa.OpS390XCALLstatic, ssa.OpS390XCALLclosure, ssa.OpS390XCALLinter:
|
case ssa.OpS390XCALLstatic, ssa.OpS390XCALLclosure, ssa.OpS390XCALLinter:
|
||||||
s.Call(v)
|
s.Call(v)
|
||||||
case ssa.OpS390XLoweredWB:
|
case ssa.OpS390XLoweredWB:
|
||||||
|
|
|
||||||
|
|
@ -365,6 +365,7 @@
|
||||||
// pseudo-ops
|
// pseudo-ops
|
||||||
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
||||||
(GetCallerSP) -> (LoweredGetCallerSP)
|
(GetCallerSP) -> (LoweredGetCallerSP)
|
||||||
|
(GetCallerPC) -> (LoweredGetCallerPC)
|
||||||
|
|
||||||
// Absorb pseudo-ops into blocks.
|
// Absorb pseudo-ops into blocks.
|
||||||
(If (Equal cc) yes no) -> (EQ cc yes no)
|
(If (Equal cc) yes no) -> (EQ cc yes no)
|
||||||
|
|
|
||||||
|
|
@ -519,6 +519,12 @@ func init() {
|
||||||
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
||||||
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
|
// LoweredGetCallerPC evaluates to the PC to which its "caller" will return.
|
||||||
|
// I.e., if f calls g "calls" getcallerpc,
|
||||||
|
// the result should be the PC within f that g will return to.
|
||||||
|
// See runtime/stubs.go for a more detailed discussion.
|
||||||
|
{name: "LoweredGetCallerPC", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
// Constant flag values. For any comparison, there are 5 possible
|
// Constant flag values. For any comparison, there are 5 possible
|
||||||
// outcomes: the three from the signed total order (<,==,>) and the
|
// outcomes: the three from the signed total order (<,==,>) and the
|
||||||
// three from the unsigned total order. The == cases overlap.
|
// three from the unsigned total order. The == cases overlap.
|
||||||
|
|
|
||||||
|
|
@ -402,6 +402,7 @@
|
||||||
// pseudo-ops
|
// pseudo-ops
|
||||||
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
||||||
(GetCallerSP) -> (LoweredGetCallerSP)
|
(GetCallerSP) -> (LoweredGetCallerSP)
|
||||||
|
(GetCallerPC) -> (LoweredGetCallerPC)
|
||||||
|
|
||||||
(If cond yes no) -> (NE cond yes no)
|
(If cond yes no) -> (NE cond yes no)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -404,6 +404,7 @@
|
||||||
// pseudo-ops
|
// pseudo-ops
|
||||||
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
||||||
(GetCallerSP) -> (LoweredGetCallerSP)
|
(GetCallerSP) -> (LoweredGetCallerSP)
|
||||||
|
(GetCallerPC) -> (LoweredGetCallerPC)
|
||||||
|
|
||||||
(If cond yes no) -> (NE cond yes no)
|
(If cond yes no) -> (NE cond yes no)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -409,6 +409,12 @@ func init() {
|
||||||
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
||||||
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
|
// LoweredGetCallerPC evaluates to the PC to which its "caller" will return.
|
||||||
|
// I.e., if f calls g "calls" getcallerpc,
|
||||||
|
// the result should be the PC within f that g will return to.
|
||||||
|
// See runtime/stubs.go for a more detailed discussion.
|
||||||
|
{name: "LoweredGetCallerPC", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
// LoweredWB invokes runtime.gcWriteBarrier. arg0=destptr, arg1=srcptr, arg2=mem, aux=runtime.gcWriteBarrier
|
// LoweredWB invokes runtime.gcWriteBarrier. arg0=destptr, arg1=srcptr, arg2=mem, aux=runtime.gcWriteBarrier
|
||||||
// It saves all GP registers if necessary,
|
// It saves all GP registers if necessary,
|
||||||
// but clobbers R31 (LR) because it's a call
|
// but clobbers R31 (LR) because it's a call
|
||||||
|
|
|
||||||
|
|
@ -379,6 +379,12 @@ func init() {
|
||||||
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
||||||
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
|
// LoweredGetCallerPC evaluates to the PC to which its "caller" will return.
|
||||||
|
// I.e., if f calls g "calls" getcallerpc,
|
||||||
|
// the result should be the PC within f that g will return to.
|
||||||
|
// See runtime/stubs.go for a more detailed discussion.
|
||||||
|
{name: "LoweredGetCallerPC", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
// LoweredWB invokes runtime.gcWriteBarrier. arg0=destptr, arg1=srcptr, arg2=mem, aux=runtime.gcWriteBarrier
|
// LoweredWB invokes runtime.gcWriteBarrier. arg0=destptr, arg1=srcptr, arg2=mem, aux=runtime.gcWriteBarrier
|
||||||
// It saves all GP registers if necessary,
|
// It saves all GP registers if necessary,
|
||||||
// but clobbers R31 (LR) because it's a call
|
// but clobbers R31 (LR) because it's a call
|
||||||
|
|
|
||||||
|
|
@ -613,6 +613,7 @@
|
||||||
// Miscellaneous
|
// Miscellaneous
|
||||||
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
||||||
(GetCallerSP) -> (LoweredGetCallerSP)
|
(GetCallerSP) -> (LoweredGetCallerSP)
|
||||||
|
(GetCallerPC) -> (LoweredGetCallerPC)
|
||||||
(IsNonNil ptr) -> (NotEqual (CMPconst [0] ptr))
|
(IsNonNil ptr) -> (NotEqual (CMPconst [0] ptr))
|
||||||
(IsInBounds idx len) -> (LessThan (CMPU idx len))
|
(IsInBounds idx len) -> (LessThan (CMPU idx len))
|
||||||
(IsSliceInBounds idx len) -> (LessEqual (CMPU idx len))
|
(IsSliceInBounds idx len) -> (LessEqual (CMPU idx len))
|
||||||
|
|
|
||||||
|
|
@ -322,6 +322,12 @@ func init() {
|
||||||
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
||||||
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
|
// LoweredGetCallerPC evaluates to the PC to which its "caller" will return.
|
||||||
|
// I.e., if f calls g "calls" getcallerpc,
|
||||||
|
// the result should be the PC within f that g will return to.
|
||||||
|
// See runtime/stubs.go for a more detailed discussion.
|
||||||
|
{name: "LoweredGetCallerPC", reg: gp01, rematerializeable: true},
|
||||||
|
|
||||||
//arg0=ptr,arg1=mem, returns void. Faults if ptr is nil.
|
//arg0=ptr,arg1=mem, returns void. Faults if ptr is nil.
|
||||||
{name: "LoweredNilCheck", argLength: 2, reg: regInfo{inputs: []regMask{gp | sp | sb}, clobbers: tmp}, clobberFlags: true, nilCheck: true, faultOnNilArg0: true},
|
{name: "LoweredNilCheck", argLength: 2, reg: regInfo{inputs: []regMask{gp | sp | sb}, clobbers: tmp}, clobberFlags: true, nilCheck: true, faultOnNilArg0: true},
|
||||||
// Round ops to block fused-multiply-add extraction.
|
// Round ops to block fused-multiply-add extraction.
|
||||||
|
|
|
||||||
|
|
@ -384,6 +384,7 @@
|
||||||
(GetG mem) -> (LoweredGetG mem)
|
(GetG mem) -> (LoweredGetG mem)
|
||||||
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
(GetClosurePtr) -> (LoweredGetClosurePtr)
|
||||||
(GetCallerSP) -> (LoweredGetCallerSP)
|
(GetCallerSP) -> (LoweredGetCallerSP)
|
||||||
|
(GetCallerPC) -> (LoweredGetCallerPC)
|
||||||
(Addr {sym} base) -> (MOVDaddr {sym} base)
|
(Addr {sym} base) -> (MOVDaddr {sym} base)
|
||||||
(ITab (Load ptr mem)) -> (MOVDload ptr mem)
|
(ITab (Load ptr mem)) -> (MOVDload ptr mem)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -451,6 +451,11 @@ func init() {
|
||||||
// arg0=ptr,arg1=mem, returns void. Faults if ptr is nil.
|
// arg0=ptr,arg1=mem, returns void. Faults if ptr is nil.
|
||||||
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
// LoweredGetCallerSP returns the SP of the caller of the current function.
|
||||||
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
{name: "LoweredGetCallerSP", reg: gp01, rematerializeable: true},
|
||||||
|
// LoweredGetCallerPC evaluates to the PC to which its "caller" will return.
|
||||||
|
// I.e., if f calls g "calls" getcallerpc,
|
||||||
|
// the result should be the PC within f that g will return to.
|
||||||
|
// See runtime/stubs.go for a more detailed discussion.
|
||||||
|
{name: "LoweredGetCallerPC", reg: gp01, rematerializeable: true},
|
||||||
{name: "LoweredNilCheck", argLength: 2, reg: regInfo{inputs: []regMask{ptrsp}}, clobberFlags: true, nilCheck: true, faultOnNilArg0: true},
|
{name: "LoweredNilCheck", argLength: 2, reg: regInfo{inputs: []regMask{ptrsp}}, clobberFlags: true, nilCheck: true, faultOnNilArg0: true},
|
||||||
// Round ops to block fused-multiply-add extraction.
|
// Round ops to block fused-multiply-add extraction.
|
||||||
{name: "LoweredRound32F", argLength: 1, reg: fp11, resultInArg0: true, zeroWidth: true},
|
{name: "LoweredRound32F", argLength: 1, reg: fp11, resultInArg0: true, zeroWidth: true},
|
||||||
|
|
|
||||||
|
|
@ -1019,6 +1019,7 @@ const (
|
||||||
OpARMLoweredMove
|
OpARMLoweredMove
|
||||||
OpARMLoweredGetClosurePtr
|
OpARMLoweredGetClosurePtr
|
||||||
OpARMLoweredGetCallerSP
|
OpARMLoweredGetCallerSP
|
||||||
|
OpARMLoweredGetCallerPC
|
||||||
OpARMFlagEQ
|
OpARMFlagEQ
|
||||||
OpARMFlagLT_ULT
|
OpARMFlagLT_ULT
|
||||||
OpARMFlagLT_UGT
|
OpARMFlagLT_UGT
|
||||||
|
|
@ -1374,6 +1375,7 @@ const (
|
||||||
OpMIPSFPFlagFalse
|
OpMIPSFPFlagFalse
|
||||||
OpMIPSLoweredGetClosurePtr
|
OpMIPSLoweredGetClosurePtr
|
||||||
OpMIPSLoweredGetCallerSP
|
OpMIPSLoweredGetCallerSP
|
||||||
|
OpMIPSLoweredGetCallerPC
|
||||||
OpMIPSLoweredWB
|
OpMIPSLoweredWB
|
||||||
|
|
||||||
OpMIPS64ADDV
|
OpMIPS64ADDV
|
||||||
|
|
@ -1486,6 +1488,7 @@ const (
|
||||||
OpMIPS64FPFlagFalse
|
OpMIPS64FPFlagFalse
|
||||||
OpMIPS64LoweredGetClosurePtr
|
OpMIPS64LoweredGetClosurePtr
|
||||||
OpMIPS64LoweredGetCallerSP
|
OpMIPS64LoweredGetCallerSP
|
||||||
|
OpMIPS64LoweredGetCallerPC
|
||||||
OpMIPS64LoweredWB
|
OpMIPS64LoweredWB
|
||||||
|
|
||||||
OpPPC64ADD
|
OpPPC64ADD
|
||||||
|
|
@ -1614,6 +1617,7 @@ const (
|
||||||
OpPPC64FGreaterEqual
|
OpPPC64FGreaterEqual
|
||||||
OpPPC64LoweredGetClosurePtr
|
OpPPC64LoweredGetClosurePtr
|
||||||
OpPPC64LoweredGetCallerSP
|
OpPPC64LoweredGetCallerSP
|
||||||
|
OpPPC64LoweredGetCallerPC
|
||||||
OpPPC64LoweredNilCheck
|
OpPPC64LoweredNilCheck
|
||||||
OpPPC64LoweredRound32F
|
OpPPC64LoweredRound32F
|
||||||
OpPPC64LoweredRound64F
|
OpPPC64LoweredRound64F
|
||||||
|
|
@ -1826,6 +1830,7 @@ const (
|
||||||
OpS390XLoweredGetG
|
OpS390XLoweredGetG
|
||||||
OpS390XLoweredGetClosurePtr
|
OpS390XLoweredGetClosurePtr
|
||||||
OpS390XLoweredGetCallerSP
|
OpS390XLoweredGetCallerSP
|
||||||
|
OpS390XLoweredGetCallerPC
|
||||||
OpS390XLoweredNilCheck
|
OpS390XLoweredNilCheck
|
||||||
OpS390XLoweredRound32F
|
OpS390XLoweredRound32F
|
||||||
OpS390XLoweredRound64F
|
OpS390XLoweredRound64F
|
||||||
|
|
@ -13314,6 +13319,16 @@ var opcodeTable = [...]opInfo{
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "LoweredGetCallerPC",
|
||||||
|
argLen: 0,
|
||||||
|
rematerializeable: true,
|
||||||
|
reg: regInfo{
|
||||||
|
outputs: []outputInfo{
|
||||||
|
{0, 21503}, // R0 R1 R2 R3 R4 R5 R6 R7 R8 R9 R12 R14
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "FlagEQ",
|
name: "FlagEQ",
|
||||||
argLen: 0,
|
argLen: 0,
|
||||||
|
|
@ -17995,6 +18010,16 @@ var opcodeTable = [...]opInfo{
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "LoweredGetCallerPC",
|
||||||
|
argLen: 0,
|
||||||
|
rematerializeable: true,
|
||||||
|
reg: regInfo{
|
||||||
|
outputs: []outputInfo{
|
||||||
|
{0, 335544318}, // R1 R2 R3 R4 R5 R6 R7 R8 R9 R10 R11 R12 R13 R14 R15 R16 R17 R18 R19 R20 R21 R22 R24 R25 R28 R31
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "LoweredWB",
|
name: "LoweredWB",
|
||||||
auxType: auxSym,
|
auxType: auxSym,
|
||||||
|
|
@ -19515,6 +19540,16 @@ var opcodeTable = [...]opInfo{
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "LoweredGetCallerPC",
|
||||||
|
argLen: 0,
|
||||||
|
rematerializeable: true,
|
||||||
|
reg: regInfo{
|
||||||
|
outputs: []outputInfo{
|
||||||
|
{0, 167772158}, // R1 R2 R3 R4 R5 R6 R7 R8 R9 R10 R11 R12 R13 R14 R15 R16 R17 R18 R19 R20 R21 R22 R24 R25 R31
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "LoweredWB",
|
name: "LoweredWB",
|
||||||
auxType: auxSym,
|
auxType: auxSym,
|
||||||
|
|
@ -21203,6 +21238,16 @@ var opcodeTable = [...]opInfo{
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "LoweredGetCallerPC",
|
||||||
|
argLen: 0,
|
||||||
|
rematerializeable: true,
|
||||||
|
reg: regInfo{
|
||||||
|
outputs: []outputInfo{
|
||||||
|
{0, 1073733624}, // R3 R4 R5 R6 R7 R8 R9 R10 R11 R12 R14 R15 R16 R17 R18 R19 R20 R21 R22 R23 R24 R25 R26 R27 R28 R29
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "LoweredNilCheck",
|
name: "LoweredNilCheck",
|
||||||
argLen: 2,
|
argLen: 2,
|
||||||
|
|
@ -24309,6 +24354,16 @@ var opcodeTable = [...]opInfo{
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
name: "LoweredGetCallerPC",
|
||||||
|
argLen: 0,
|
||||||
|
rematerializeable: true,
|
||||||
|
reg: regInfo{
|
||||||
|
outputs: []outputInfo{
|
||||||
|
{0, 21503}, // R0 R1 R2 R3 R4 R5 R6 R7 R8 R9 R12 R14
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
name: "LoweredNilCheck",
|
name: "LoweredNilCheck",
|
||||||
argLen: 2,
|
argLen: 2,
|
||||||
|
|
|
||||||
|
|
@ -551,6 +551,8 @@ func rewriteValueARM(v *Value) bool {
|
||||||
return rewriteValueARM_OpGeq8_0(v)
|
return rewriteValueARM_OpGeq8_0(v)
|
||||||
case OpGeq8U:
|
case OpGeq8U:
|
||||||
return rewriteValueARM_OpGeq8U_0(v)
|
return rewriteValueARM_OpGeq8U_0(v)
|
||||||
|
case OpGetCallerPC:
|
||||||
|
return rewriteValueARM_OpGetCallerPC_0(v)
|
||||||
case OpGetCallerSP:
|
case OpGetCallerSP:
|
||||||
return rewriteValueARM_OpGetCallerSP_0(v)
|
return rewriteValueARM_OpGetCallerSP_0(v)
|
||||||
case OpGetClosurePtr:
|
case OpGetClosurePtr:
|
||||||
|
|
@ -18584,6 +18586,15 @@ func rewriteValueARM_OpGeq8U_0(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
func rewriteValueARM_OpGetCallerPC_0(v *Value) bool {
|
||||||
|
// match: (GetCallerPC)
|
||||||
|
// cond:
|
||||||
|
// result: (LoweredGetCallerPC)
|
||||||
|
for {
|
||||||
|
v.reset(OpARMLoweredGetCallerPC)
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
func rewriteValueARM_OpGetCallerSP_0(v *Value) bool {
|
func rewriteValueARM_OpGetCallerSP_0(v *Value) bool {
|
||||||
// match: (GetCallerSP)
|
// match: (GetCallerSP)
|
||||||
// cond:
|
// cond:
|
||||||
|
|
|
||||||
|
|
@ -145,6 +145,8 @@ func rewriteValueMIPS(v *Value) bool {
|
||||||
return rewriteValueMIPS_OpGeq8_0(v)
|
return rewriteValueMIPS_OpGeq8_0(v)
|
||||||
case OpGeq8U:
|
case OpGeq8U:
|
||||||
return rewriteValueMIPS_OpGeq8U_0(v)
|
return rewriteValueMIPS_OpGeq8U_0(v)
|
||||||
|
case OpGetCallerPC:
|
||||||
|
return rewriteValueMIPS_OpGetCallerPC_0(v)
|
||||||
case OpGetCallerSP:
|
case OpGetCallerSP:
|
||||||
return rewriteValueMIPS_OpGetCallerSP_0(v)
|
return rewriteValueMIPS_OpGetCallerSP_0(v)
|
||||||
case OpGetClosurePtr:
|
case OpGetClosurePtr:
|
||||||
|
|
@ -1760,6 +1762,15 @@ func rewriteValueMIPS_OpGeq8U_0(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
func rewriteValueMIPS_OpGetCallerPC_0(v *Value) bool {
|
||||||
|
// match: (GetCallerPC)
|
||||||
|
// cond:
|
||||||
|
// result: (LoweredGetCallerPC)
|
||||||
|
for {
|
||||||
|
v.reset(OpMIPSLoweredGetCallerPC)
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
func rewriteValueMIPS_OpGetCallerSP_0(v *Value) bool {
|
func rewriteValueMIPS_OpGetCallerSP_0(v *Value) bool {
|
||||||
// match: (GetCallerSP)
|
// match: (GetCallerSP)
|
||||||
// cond:
|
// cond:
|
||||||
|
|
|
||||||
|
|
@ -169,6 +169,8 @@ func rewriteValueMIPS64(v *Value) bool {
|
||||||
return rewriteValueMIPS64_OpGeq8_0(v)
|
return rewriteValueMIPS64_OpGeq8_0(v)
|
||||||
case OpGeq8U:
|
case OpGeq8U:
|
||||||
return rewriteValueMIPS64_OpGeq8U_0(v)
|
return rewriteValueMIPS64_OpGeq8U_0(v)
|
||||||
|
case OpGetCallerPC:
|
||||||
|
return rewriteValueMIPS64_OpGetCallerPC_0(v)
|
||||||
case OpGetCallerSP:
|
case OpGetCallerSP:
|
||||||
return rewriteValueMIPS64_OpGetCallerSP_0(v)
|
return rewriteValueMIPS64_OpGetCallerSP_0(v)
|
||||||
case OpGetClosurePtr:
|
case OpGetClosurePtr:
|
||||||
|
|
@ -1931,6 +1933,15 @@ func rewriteValueMIPS64_OpGeq8U_0(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
func rewriteValueMIPS64_OpGetCallerPC_0(v *Value) bool {
|
||||||
|
// match: (GetCallerPC)
|
||||||
|
// cond:
|
||||||
|
// result: (LoweredGetCallerPC)
|
||||||
|
for {
|
||||||
|
v.reset(OpMIPS64LoweredGetCallerPC)
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
func rewriteValueMIPS64_OpGetCallerSP_0(v *Value) bool {
|
func rewriteValueMIPS64_OpGetCallerSP_0(v *Value) bool {
|
||||||
// match: (GetCallerSP)
|
// match: (GetCallerSP)
|
||||||
// cond:
|
// cond:
|
||||||
|
|
|
||||||
|
|
@ -191,6 +191,8 @@ func rewriteValuePPC64(v *Value) bool {
|
||||||
return rewriteValuePPC64_OpGeq8_0(v)
|
return rewriteValuePPC64_OpGeq8_0(v)
|
||||||
case OpGeq8U:
|
case OpGeq8U:
|
||||||
return rewriteValuePPC64_OpGeq8U_0(v)
|
return rewriteValuePPC64_OpGeq8U_0(v)
|
||||||
|
case OpGetCallerPC:
|
||||||
|
return rewriteValuePPC64_OpGetCallerPC_0(v)
|
||||||
case OpGetCallerSP:
|
case OpGetCallerSP:
|
||||||
return rewriteValuePPC64_OpGetCallerSP_0(v)
|
return rewriteValuePPC64_OpGetCallerSP_0(v)
|
||||||
case OpGetClosurePtr:
|
case OpGetClosurePtr:
|
||||||
|
|
@ -2110,6 +2112,15 @@ func rewriteValuePPC64_OpGeq8U_0(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
func rewriteValuePPC64_OpGetCallerPC_0(v *Value) bool {
|
||||||
|
// match: (GetCallerPC)
|
||||||
|
// cond:
|
||||||
|
// result: (LoweredGetCallerPC)
|
||||||
|
for {
|
||||||
|
v.reset(OpPPC64LoweredGetCallerPC)
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
func rewriteValuePPC64_OpGetCallerSP_0(v *Value) bool {
|
func rewriteValuePPC64_OpGetCallerSP_0(v *Value) bool {
|
||||||
// match: (GetCallerSP)
|
// match: (GetCallerSP)
|
||||||
// cond:
|
// cond:
|
||||||
|
|
|
||||||
|
|
@ -187,6 +187,8 @@ func rewriteValueS390X(v *Value) bool {
|
||||||
return rewriteValueS390X_OpGeq8_0(v)
|
return rewriteValueS390X_OpGeq8_0(v)
|
||||||
case OpGeq8U:
|
case OpGeq8U:
|
||||||
return rewriteValueS390X_OpGeq8U_0(v)
|
return rewriteValueS390X_OpGeq8U_0(v)
|
||||||
|
case OpGetCallerPC:
|
||||||
|
return rewriteValueS390X_OpGetCallerPC_0(v)
|
||||||
case OpGetCallerSP:
|
case OpGetCallerSP:
|
||||||
return rewriteValueS390X_OpGetCallerSP_0(v)
|
return rewriteValueS390X_OpGetCallerSP_0(v)
|
||||||
case OpGetClosurePtr:
|
case OpGetClosurePtr:
|
||||||
|
|
@ -2277,6 +2279,15 @@ func rewriteValueS390X_OpGeq8U_0(v *Value) bool {
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
func rewriteValueS390X_OpGetCallerPC_0(v *Value) bool {
|
||||||
|
// match: (GetCallerPC)
|
||||||
|
// cond:
|
||||||
|
// result: (LoweredGetCallerPC)
|
||||||
|
for {
|
||||||
|
v.reset(OpS390XLoweredGetCallerPC)
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
||||||
func rewriteValueS390X_OpGetCallerSP_0(v *Value) bool {
|
func rewriteValueS390X_OpGetCallerSP_0(v *Value) bool {
|
||||||
// match: (GetCallerSP)
|
// match: (GetCallerSP)
|
||||||
// cond:
|
// cond:
|
||||||
|
|
|
||||||
|
|
@ -643,6 +643,19 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
if p.From.Type == obj.TYPE_ADDR && p.From.Reg == REGSP && p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP {
|
if p.From.Type == obj.TYPE_ADDR && p.From.Reg == REGSP && p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP {
|
||||||
p.Spadj = int32(-p.From.Offset)
|
p.Spadj = int32(-p.From.Offset)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case obj.AGETCALLERPC:
|
||||||
|
if cursym.Leaf() {
|
||||||
|
/* MOVW LR, Rd */
|
||||||
|
p.As = AMOVW
|
||||||
|
p.From.Type = obj.TYPE_REG
|
||||||
|
p.From.Reg = REGLINK
|
||||||
|
} else {
|
||||||
|
/* MOVW (RSP), Rd */
|
||||||
|
p.As = AMOVW
|
||||||
|
p.From.Type = obj.TYPE_MEM
|
||||||
|
p.From.Reg = REGSP
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -536,6 +536,19 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
if p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP && p.From.Type == obj.TYPE_CONST {
|
if p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP && p.From.Type == obj.TYPE_CONST {
|
||||||
p.Spadj = int32(-p.From.Offset)
|
p.Spadj = int32(-p.From.Offset)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case obj.AGETCALLERPC:
|
||||||
|
if cursym.Leaf() {
|
||||||
|
/* MOV LR, Rd */
|
||||||
|
p.As = mov
|
||||||
|
p.From.Type = obj.TYPE_REG
|
||||||
|
p.From.Reg = REGLINK
|
||||||
|
} else {
|
||||||
|
/* MOV (RSP), Rd */
|
||||||
|
p.As = mov
|
||||||
|
p.From.Type = obj.TYPE_MEM
|
||||||
|
p.From.Reg = REGSP
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -781,6 +781,18 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
if p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP && p.From.Type == obj.TYPE_CONST {
|
if p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP && p.From.Type == obj.TYPE_CONST {
|
||||||
p.Spadj = int32(-p.From.Offset)
|
p.Spadj = int32(-p.From.Offset)
|
||||||
}
|
}
|
||||||
|
case obj.AGETCALLERPC:
|
||||||
|
if cursym.Leaf() {
|
||||||
|
/* MOVD LR, Rd */
|
||||||
|
p.As = AMOVD
|
||||||
|
p.From.Type = obj.TYPE_REG
|
||||||
|
p.From.Reg = REG_LR
|
||||||
|
} else {
|
||||||
|
/* MOVD (RSP), Rd */
|
||||||
|
p.As = AMOVD
|
||||||
|
p.From.Type = obj.TYPE_MEM
|
||||||
|
p.From.Reg = REGSP
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -524,6 +524,19 @@ func preprocess(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
|
||||||
if p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP && p.From.Type == obj.TYPE_CONST {
|
if p.To.Type == obj.TYPE_REG && p.To.Reg == REGSP && p.From.Type == obj.TYPE_CONST {
|
||||||
p.Spadj = int32(-p.From.Offset)
|
p.Spadj = int32(-p.From.Offset)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case obj.AGETCALLERPC:
|
||||||
|
if cursym.Leaf() {
|
||||||
|
/* MOVD LR, Rd */
|
||||||
|
p.As = AMOVD
|
||||||
|
p.From.Type = obj.TYPE_REG
|
||||||
|
p.From.Reg = REG_LR
|
||||||
|
} else {
|
||||||
|
/* MOVD (RSP), Rd */
|
||||||
|
p.As = AMOVD
|
||||||
|
p.From.Type = obj.TYPE_MEM
|
||||||
|
p.From.Reg = REGSP
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if wasSplit {
|
if wasSplit {
|
||||||
|
|
|
||||||
|
|
@ -760,11 +760,6 @@ TEXT setg<>(SB),NOSPLIT|NOFRAME,$0-0
|
||||||
MOVW g, R0
|
MOVW g, R0
|
||||||
RET
|
RET
|
||||||
|
|
||||||
TEXT runtime·getcallerpc(SB),NOSPLIT|NOFRAME,$0-4
|
|
||||||
MOVW 0(R13), R0 // LR saved by caller
|
|
||||||
MOVW R0, ret+0(FP)
|
|
||||||
RET
|
|
||||||
|
|
||||||
TEXT runtime·emptyfunc(SB),0,$0-0
|
TEXT runtime·emptyfunc(SB),0,$0-0
|
||||||
RET
|
RET
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -608,11 +608,6 @@ TEXT setg_gcc<>(SB),NOSPLIT,$0-0
|
||||||
JAL runtime·save_g(SB)
|
JAL runtime·save_g(SB)
|
||||||
RET
|
RET
|
||||||
|
|
||||||
TEXT runtime·getcallerpc(SB),NOSPLIT|NOFRAME,$0-8
|
|
||||||
MOVV 0(R29), R1 // LR saved by caller
|
|
||||||
MOVV R1, ret+0(FP)
|
|
||||||
RET
|
|
||||||
|
|
||||||
TEXT runtime·abort(SB),NOSPLIT|NOFRAME,$0-0
|
TEXT runtime·abort(SB),NOSPLIT|NOFRAME,$0-0
|
||||||
MOVW (R0), R0
|
MOVW (R0), R0
|
||||||
UNDEF
|
UNDEF
|
||||||
|
|
|
||||||
|
|
@ -611,11 +611,6 @@ TEXT setg_gcc<>(SB),NOSPLIT,$0
|
||||||
JAL runtime·save_g(SB)
|
JAL runtime·save_g(SB)
|
||||||
RET
|
RET
|
||||||
|
|
||||||
TEXT runtime·getcallerpc(SB),NOSPLIT|NOFRAME,$0-4
|
|
||||||
MOVW 0(R29), R1 // LR saved by caller
|
|
||||||
MOVW R1, ret+0(FP)
|
|
||||||
RET
|
|
||||||
|
|
||||||
TEXT runtime·abort(SB),NOSPLIT,$0-0
|
TEXT runtime·abort(SB),NOSPLIT,$0-0
|
||||||
UNDEF
|
UNDEF
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -705,11 +705,6 @@ TEXT setg_gcc<>(SB),NOSPLIT|NOFRAME,$0-0
|
||||||
MOVD R4, LR
|
MOVD R4, LR
|
||||||
RET
|
RET
|
||||||
|
|
||||||
TEXT runtime·getcallerpc(SB),NOSPLIT|NOFRAME,$0-8
|
|
||||||
MOVD 0(R1), R3 // LR saved by caller
|
|
||||||
MOVD R3, ret+0(FP)
|
|
||||||
RET
|
|
||||||
|
|
||||||
TEXT runtime·abort(SB),NOSPLIT|NOFRAME,$0-0
|
TEXT runtime·abort(SB),NOSPLIT|NOFRAME,$0-0
|
||||||
MOVW (R0), R0
|
MOVW (R0), R0
|
||||||
UNDEF
|
UNDEF
|
||||||
|
|
|
||||||
|
|
@ -725,11 +725,6 @@ TEXT setg_gcc<>(SB),NOSPLIT|NOFRAME,$0-0
|
||||||
MOVD R1, LR
|
MOVD R1, LR
|
||||||
RET
|
RET
|
||||||
|
|
||||||
TEXT runtime·getcallerpc(SB),NOSPLIT|NOFRAME,$0-8
|
|
||||||
MOVD 0(R15), R3 // LR saved by caller
|
|
||||||
MOVD R3, ret+0(FP)
|
|
||||||
RET
|
|
||||||
|
|
||||||
TEXT runtime·abort(SB),NOSPLIT|NOFRAME,$0-0
|
TEXT runtime·abort(SB),NOSPLIT|NOFRAME,$0-0
|
||||||
MOVW (R0), R0
|
MOVW (R0), R0
|
||||||
UNDEF
|
UNDEF
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue