summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/cmd/internal/objabi/stack.go15
-rw-r--r--src/cmd/link/internal/ld/stackcheck.go2
-rw-r--r--src/internal/abi/stack.go8
-rw-r--r--src/runtime/preempt.go2
-rw-r--r--src/runtime/stack.go19
-rw-r--r--test/nosplit.go13
6 files changed, 25 insertions, 34 deletions
diff --git a/src/cmd/internal/objabi/stack.go b/src/cmd/internal/objabi/stack.go
index 5a2f641a75..7c7ff4e058 100644
--- a/src/cmd/internal/objabi/stack.go
+++ b/src/cmd/internal/objabi/stack.go
@@ -9,18 +9,9 @@ import (
"internal/buildcfg"
)
-// For the linkers. Must match Go definitions.
-
-const (
- STACKSYSTEM = 0
- StackSystem = STACKSYSTEM
-)
-
-func StackLimit(race bool) int {
- // This arithmetic must match that in runtime/stack.go:{_StackGuard,_StackLimit}.
- stackGuard := 928*stackGuardMultiplier(race) + StackSystem
- stackLimit := stackGuard - StackSystem - abi.StackSmall
- return stackLimit
+func StackNosplit(race bool) int {
+ // This arithmetic must match that in runtime/stack.go:stackNosplit.
+ return abi.StackNosplitBase * stackGuardMultiplier(race)
}
// stackGuardMultiplier returns a multiplier to apply to the default
diff --git a/src/cmd/link/internal/ld/stackcheck.go b/src/cmd/link/internal/ld/stackcheck.go
index c82dafe51e..24a96fb996 100644
--- a/src/cmd/link/internal/ld/stackcheck.go
+++ b/src/cmd/link/internal/ld/stackcheck.go
@@ -61,7 +61,7 @@ func (ctxt *Link) doStackCheck() {
// The call to morestack in every splittable function ensures
// that there are at least StackLimit bytes available below SP
// when morestack returns.
- limit := objabi.StackLimit(*flagRace) - sc.callSize
+ limit := objabi.StackNosplit(*flagRace) - sc.callSize
if buildcfg.GOARCH == "arm64" {
// Need an extra 8 bytes below SP to save FP.
limit -= 8
diff --git a/src/internal/abi/stack.go b/src/internal/abi/stack.go
index 9efd21b167..8e3327ee48 100644
--- a/src/internal/abi/stack.go
+++ b/src/internal/abi/stack.go
@@ -5,6 +5,14 @@
package abi
const (
+ // StackNosplitBase is the base maximum number of bytes that a chain of
+ // NOSPLIT functions can use.
+ //
+ // This value must be multiplied by the stack guard multiplier, so do not
+ // use it directly. See runtime/stack.go:stackNosplit and
+ // cmd/internal/objabi/stack.go:StackNosplit.
+ StackNosplitBase = 800
+
// We have three different sequences for stack bounds checks, depending on
// whether the stack frame of a function is small, big, or huge.
diff --git a/src/runtime/preempt.go b/src/runtime/preempt.go
index a575fbcf11..38114243bb 100644
--- a/src/runtime/preempt.go
+++ b/src/runtime/preempt.go
@@ -320,7 +320,7 @@ func init() {
total += funcMaxSPDelta(f)
// Add some overhead for return PCs, etc.
asyncPreemptStack = uintptr(total) + 8*goarch.PtrSize
- if asyncPreemptStack > _StackLimit {
+ if asyncPreemptStack > stackNosplit {
// We need more than the nosplit limit. This isn't
// unsafe, but it may limit asynchronous preemption.
//
diff --git a/src/runtime/stack.go b/src/runtime/stack.go
index 6d75301556..92c2ce3cbf 100644
--- a/src/runtime/stack.go
+++ b/src/runtime/stack.go
@@ -85,19 +85,18 @@ const (
_FixedStack6 = _FixedStack5 | (_FixedStack5 >> 16)
_FixedStack = _FixedStack6 + 1
+ // stackNosplit is the maximum number of bytes that a chain of NOSPLIT
+ // functions can use.
+ // This arithmetic must match that in cmd/internal/objabi/stack.go:StackNosplit.
+ stackNosplit = abi.StackNosplitBase * sys.StackGuardMultiplier
+
// The stack guard is a pointer this many bytes above the
// bottom of the stack.
//
- // The guard leaves enough room for one _StackSmall frame plus
- // a _StackLimit chain of NOSPLIT calls plus _StackSystem
- // bytes for the OS.
- // This arithmetic must match that in cmd/internal/objabi/stack.go:StackLimit.
- _StackGuard = 928*sys.StackGuardMultiplier + _StackSystem
-
- // The maximum number of bytes that a chain of NOSPLIT
- // functions can use.
+ // The guard leaves enough room for a stackNosplit chain of NOSPLIT calls
+ // plus one stackSmall frame plus stackSystem bytes for the OS.
// This arithmetic must match that in cmd/internal/objabi/stack.go:StackLimit.
- _StackLimit = _StackGuard - _StackSystem - abi.StackSmall
+ _StackGuard = stackNosplit + _StackSystem + abi.StackSmall
)
const (
@@ -1211,7 +1210,7 @@ func shrinkstack(gp *g) {
// down to the SP plus the stack guard space that ensures
// there's room for nosplit functions.
avail := gp.stack.hi - gp.stack.lo
- if used := gp.stack.hi - gp.sched.sp + _StackLimit; used >= avail/4 {
+ if used := gp.stack.hi - gp.sched.sp + stackNosplit; used >= avail/4 {
return
}
diff --git a/test/nosplit.go b/test/nosplit.go
index a695654eaf..2b1bb5492d 100644
--- a/test/nosplit.go
+++ b/test/nosplit.go
@@ -342,22 +342,15 @@ TestCases:
nosplit := m[3]
body := m[4]
- // The limit was originally 128 but is now 800 (928-128).
+ // The limit was originally 128 but is now 800.
// Instead of rewriting the test cases above, adjust
// the first nosplit frame to use up the extra bytes.
// This isn't exactly right because we could have
// nosplit -> split -> nosplit, but it's good enough.
if !adjusted && nosplit != "" {
+ const stackNosplitBase = 800 // internal/abi.StackNosplitBase
adjusted = true
- size += (928 - 128) - 128
- // Noopt builds have a larger stackguard.
- // See ../src/cmd/dist/buildruntime.go:stackGuardMultiplier
- // This increase is included in objabi.StackGuard
- for _, s := range strings.Split(os.Getenv("GO_GCFLAGS"), " ") {
- if s == "-N" {
- size += 928
- }
- }
+ size += stackNosplitBase - 128
}
if nosplit != "" {