Commit f5becf42 authored by Dmitriy Vyukov's avatar Dmitriy Vyukov

runtime: add stackguard0 to G

This is part of preemptive scheduler.
stackguard0 is checked in split stack checks and can be set to StackPreempt.
stackguard is not set to StackPreempt (holds the original value).

R=golang-dev, daniel.morsing, iant
CC=golang-dev
https://golang.org/cl/9875043
parent ae43ea43
...@@ -18,6 +18,7 @@ TEXT _rt0_386(SB),7,$0 ...@@ -18,6 +18,7 @@ TEXT _rt0_386(SB),7,$0
MOVL $runtime·g0(SB), BP MOVL $runtime·g0(SB), BP
LEAL (-64*1024+104)(SP), BX LEAL (-64*1024+104)(SP), BX
MOVL BX, g_stackguard(BP) MOVL BX, g_stackguard(BP)
MOVL BX, g_stackguard0(BP)
MOVL SP, g_stackbase(BP) MOVL SP, g_stackbase(BP)
// find out information about the processor we're on // find out information about the processor we're on
...@@ -41,6 +42,10 @@ nocpuinfo: ...@@ -41,6 +42,10 @@ nocpuinfo:
MOVL BX, 4(SP) MOVL BX, 4(SP)
MOVL BP, 0(SP) MOVL BP, 0(SP)
CALL AX CALL AX
// update stackguard after _cgo_init
MOVL $runtime·g0(SB), CX
MOVL g_stackguard0(CX), AX
MOVL AX, g_stackguard(CX)
// skip runtime·ldt0setup(SB) and tls test after _cgo_init for non-windows // skip runtime·ldt0setup(SB) and tls test after _cgo_init for non-windows
CMPL runtime·iswindows(SB), $0 CMPL runtime·iswindows(SB), $0
JEQ ok JEQ ok
......
...@@ -18,6 +18,7 @@ TEXT _rt0_amd64(SB),7,$-8 ...@@ -18,6 +18,7 @@ TEXT _rt0_amd64(SB),7,$-8
MOVQ $runtime·g0(SB), DI MOVQ $runtime·g0(SB), DI
LEAQ (-64*1024+104)(SP), BX LEAQ (-64*1024+104)(SP), BX
MOVQ BX, g_stackguard(DI) MOVQ BX, g_stackguard(DI)
MOVQ BX, g_stackguard0(DI)
MOVQ SP, g_stackbase(DI) MOVQ SP, g_stackbase(DI)
// find out information about the processor we're on // find out information about the processor we're on
...@@ -39,6 +40,10 @@ nocpuinfo: ...@@ -39,6 +40,10 @@ nocpuinfo:
MOVQ DI, CX // Win64 uses CX for first parameter MOVQ DI, CX // Win64 uses CX for first parameter
MOVQ $setmg_gcc<>(SB), SI MOVQ $setmg_gcc<>(SB), SI
CALL AX CALL AX
// update stackguard after _cgo_init
MOVQ $runtime·g0(SB), CX
MOVQ g_stackguard0(CX), AX
MOVQ AX, g_stackguard(CX)
CMPL runtime·iswindows(SB), $0 CMPL runtime·iswindows(SB), $0
JEQ ok JEQ ok
......
...@@ -28,6 +28,7 @@ TEXT _rt0_arm(SB),7,$-4 ...@@ -28,6 +28,7 @@ TEXT _rt0_arm(SB),7,$-4
// create istack out of the OS stack // create istack out of the OS stack
MOVW $(-8192+104)(R13), R0 MOVW $(-8192+104)(R13), R0
MOVW R0, g_stackguard(g) // (w 104b guard) MOVW R0, g_stackguard(g) // (w 104b guard)
MOVW R0, g_stackguard0(g)
MOVW R13, g_stackbase(g) MOVW R13, g_stackbase(g)
BL runtime·emptyfunc(SB) // fault if stack check is wrong BL runtime·emptyfunc(SB) // fault if stack check is wrong
...@@ -36,6 +37,9 @@ TEXT _rt0_arm(SB),7,$-4 ...@@ -36,6 +37,9 @@ TEXT _rt0_arm(SB),7,$-4
CMP $0, R2 CMP $0, R2
MOVW.NE g, R0 // first argument of _cgo_init is g MOVW.NE g, R0 // first argument of _cgo_init is g
BL.NE (R2) // will clobber R0-R3 BL.NE (R2) // will clobber R0-R3
// update stackguard after _cgo_init
MOVW g_stackguard0(g), R0
MOVW R0, g_stackguard(g)
BL runtime·checkgoarm(SB) BL runtime·checkgoarm(SB)
BL runtime·check(SB) BL runtime·check(SB)
......
...@@ -298,6 +298,7 @@ runtime·unwindstack(G *gp, byte *sp) ...@@ -298,6 +298,7 @@ runtime·unwindstack(G *gp, byte *sp)
break; break;
gp->stackbase = (uintptr)top->stackbase; gp->stackbase = (uintptr)top->stackbase;
gp->stackguard = (uintptr)top->stackguard; gp->stackguard = (uintptr)top->stackguard;
gp->stackguard0 = gp->stackguard;
if(top->free != 0) if(top->free != 0)
runtime·stackfree(stk, top->free); runtime·stackfree(stk, top->free);
} }
......
...@@ -468,6 +468,7 @@ runtime·mstart(void) ...@@ -468,6 +468,7 @@ runtime·mstart(void)
// so other calls can reuse this stack space. // so other calls can reuse this stack space.
runtime·gosave(&m->g0->sched); runtime·gosave(&m->g0->sched);
m->g0->sched.pc = (void*)-1; // make sure it is never used m->g0->sched.pc = (void*)-1; // make sure it is never used
m->g0->stackguard = m->g0->stackguard0; // cgo sets only stackguard0, copy it to stackguard
m->seh = &seh; m->seh = &seh;
runtime·asminit(); runtime·asminit();
runtime·minit(); runtime·minit();
...@@ -615,6 +616,7 @@ runtime·needm(byte x) ...@@ -615,6 +616,7 @@ runtime·needm(byte x)
runtime·setmg(mp, mp->g0); runtime·setmg(mp, mp->g0);
g->stackbase = (uintptr)(&x + 1024); g->stackbase = (uintptr)(&x + 1024);
g->stackguard = (uintptr)(&x - 32*1024); g->stackguard = (uintptr)(&x - 32*1024);
g->stackguard0 = g->stackguard;
// On windows/386, we need to put an SEH frame (two words) // On windows/386, we need to put an SEH frame (two words)
// somewhere on the current stack. We are called // somewhere on the current stack. We are called
...@@ -979,6 +981,7 @@ execute(G *gp) ...@@ -979,6 +981,7 @@ execute(G *gp)
runtime·throw("execute: bad g status"); runtime·throw("execute: bad g status");
} }
gp->status = Grunning; gp->status = Grunning;
gp->stackguard0 = gp->stackguard;
m->p->tick++; m->p->tick++;
m->curg = gp; m->curg = gp;
gp->m = m; gp->m = m;
...@@ -1465,6 +1468,7 @@ runtime·malg(int32 stacksize) ...@@ -1465,6 +1468,7 @@ runtime·malg(int32 stacksize)
} }
newg->stack0 = (uintptr)stk; newg->stack0 = (uintptr)stk;
newg->stackguard = (uintptr)stk + StackGuard; newg->stackguard = (uintptr)stk + StackGuard;
newg->stackguard0 = newg->stackguard;
newg->stackbase = (uintptr)stk + StackSystem + stacksize - sizeof(Stktop); newg->stackbase = (uintptr)stk + StackSystem + stacksize - sizeof(Stktop);
runtime·memclr((byte*)newg->stackbase, sizeof(Stktop)); runtime·memclr((byte*)newg->stackbase, sizeof(Stktop));
} }
......
...@@ -226,7 +226,8 @@ struct GCStats ...@@ -226,7 +226,8 @@ struct GCStats
}; };
struct G struct G
{ {
uintptr stackguard; // cannot move - also known to linker, libmach, runtime/cgo // stackguard0 can be set to StackPreempt as opposed to stackguard
uintptr stackguard0; // cannot move - also known to linker, libmach, runtime/cgo
uintptr stackbase; // cannot move - also known to libmach, runtime/cgo uintptr stackbase; // cannot move - also known to libmach, runtime/cgo
Defer* defer; Defer* defer;
Panic* panic; Panic* panic;
...@@ -235,6 +236,7 @@ struct G ...@@ -235,6 +236,7 @@ struct G
uintptr gcsp; // if status==Gsyscall, gcsp = sched.sp to use during gc uintptr gcsp; // if status==Gsyscall, gcsp = sched.sp to use during gc
byte* gcpc; // if status==Gsyscall, gcpc = sched.pc to use during gc byte* gcpc; // if status==Gsyscall, gcpc = sched.pc to use during gc
uintptr gcguard; // if status==Gsyscall, gcguard = stackguard to use during gc uintptr gcguard; // if status==Gsyscall, gcguard = stackguard to use during gc
uintptr stackguard; // same as stackguard0, but not set to StackPreempt
uintptr stack0; uintptr stack0;
FuncVal* fnstart; // initial function FuncVal* fnstart; // initial function
G* alllink; // on allg G* alllink; // on allg
......
...@@ -157,6 +157,7 @@ runtime·oldstack(void) ...@@ -157,6 +157,7 @@ runtime·oldstack(void)
label = top->gobuf; label = top->gobuf;
gp->stackbase = (uintptr)top->stackbase; gp->stackbase = (uintptr)top->stackbase;
gp->stackguard = (uintptr)top->stackguard; gp->stackguard = (uintptr)top->stackguard;
gp->stackguard0 = gp->stackguard;
if(top->free != 0) if(top->free != 0)
runtime·stackfree(old, top->free); runtime·stackfree(old, top->free);
...@@ -249,6 +250,7 @@ runtime·newstack(void) ...@@ -249,6 +250,7 @@ runtime·newstack(void)
gp->stackbase = (uintptr)top; gp->stackbase = (uintptr)top;
gp->stackguard = (uintptr)stk + StackGuard; gp->stackguard = (uintptr)stk + StackGuard;
gp->stackguard0 = gp->stackguard;
sp = (byte*)top; sp = (byte*)top;
if(argsize > 0) { if(argsize > 0) {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment