From edc3452f4aba40ef97961ca43f0ffb60f1e30e9c Mon Sep 17 00:00:00 2001 From: Russ Cox Date: Thu, 19 Nov 2015 15:51:39 -0500 Subject: [release-branch.go1.5] runtime: make asmcgocall work without a g MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Solaris needs to make system calls without a g, and Solaris uses asmcgocall to make system calls. I know, I know. I hope this makes CL 16915, fixing #12277, work on Solaris. Change-Id: If988dfd37f418b302da9c7096f598e5113ecea87 Reviewed-on: https://go-review.googlesource.com/17072 Reviewed-by: Ian Lance Taylor Reviewed-by: Aram Hăvărneanu Run-TryBot: Russ Cox Reviewed-on: https://go-review.googlesource.com/17129 --- src/runtime/asm_amd64.s | 27 ++++++++++++++++++++++++++- 1 file changed, 26 insertions(+), 1 deletion(-) diff --git a/src/runtime/asm_amd64.s b/src/runtime/asm_amd64.s index 3b4ca4d012..980b1ca3e6 100644 --- a/src/runtime/asm_amd64.s +++ b/src/runtime/asm_amd64.s @@ -661,6 +661,8 @@ TEXT ·asmcgocall(SB),NOSPLIT,$0-20 // come in on the m->g0 stack already. get_tls(CX) MOVQ g(CX), R8 + CMPQ R8, $0 + JEQ nosave MOVQ g_m(R8), R8 MOVQ m_g0(R8), SI MOVQ g(CX), DI @@ -670,11 +672,11 @@ TEXT ·asmcgocall(SB),NOSPLIT,$0-20 CMPQ SI, DI JEQ nosave + // Switch to system stack. MOVQ m_g0(R8), SI CALL gosave<>(SB) MOVQ SI, g(CX) MOVQ (g_sched+gobuf_sp)(SI), SP -nosave: // Now on a scheduling stack (a pthread-created stack). // Make sure we have enough room for 4 stack-backed fast-call @@ -700,6 +702,29 @@ nosave: MOVL AX, ret+16(FP) RET +nosave: + // Running on a system stack, perhaps even without a g. + // Having no g can happen during thread creation or thread teardown + // (see needm/dropm on Solaris, for example). + // This code is like the above sequence but without saving/restoring g + // and without worrying about the stack moving out from under us + // (because we're on a system stack, not a goroutine stack). + // The above code could be used directly if already on a system stack, + // but then the only path through this code would be a rare case on Solaris. + // Using this code for all "already on system stack" calls exercises it more, + // which should help keep it correct. + SUBQ $64, SP + ANDQ $~15, SP + MOVQ $0, 48(SP) // where above code stores g, in case someone looks during debugging + MOVQ DX, 40(SP) // save original stack pointer + MOVQ BX, DI // DI = first argument in AMD64 ABI + MOVQ BX, CX // CX = first argument in Win64 + CALL AX + MOVQ 40(SP), SI // restore original stack pointer + MOVQ SI, SP + MOVL AX, ret+16(FP) + RET + // cgocallback(void (*fn)(void*), void *frame, uintptr framesize) // Turn the fn into a Go func (by taking its address) and call // cgocallback_gofunc. -- cgit v1.2.3-54-g00ecf