1
0
mirror of https://github.com/golang/go synced 2024-10-05 11:41:22 -06:00
go/src/runtime/asm_386.s

2287 lines
43 KiB
ArmAsm
Raw Normal View History

// Copyright 2009 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
#include "zasm_GOOS_GOARCH.h"
#include "funcdata.h"
#include "textflag.h"
TEXT runtime·rt0_go(SB),NOSPLIT,$0
// copy arguments forward on an even stack
MOVL argc+0(FP), AX
MOVL argv+4(FP), BX
SUBL $128, SP // plenty of scratch
ANDL $~15, SP
MOVL AX, 120(SP) // save argc, argv away
MOVL BX, 124(SP)
// set default stack bounds.
// _cgo_init may update stackguard.
MOVL $runtime·g0(SB), BP
LEAL (-64*1024+104)(SP), BX
MOVL BX, g_stackguard0(BP)
MOVL BX, g_stackguard1(BP)
MOVL BX, (g_stack+stack_lo)(BP)
MOVL SP, (g_stack+stack_hi)(BP)
// find out information about the processor we're on
MOVL $0, AX
CPUID
CMPL AX, $0
JE nocpuinfo
MOVL $1, AX
CPUID
MOVL CX, runtime·cpuid_ecx(SB)
MOVL DX, runtime·cpuid_edx(SB)
nocpuinfo:
// if there is an _cgo_init, call it to let it
// initialize and to set up GS. if not,
// we set up GS ourselves.
MOVL _cgo_init(SB), AX
TESTL AX, AX
JZ needtls
2014-06-26 09:54:39 -06:00
MOVL $setg_gcc<>(SB), BX
MOVL BX, 4(SP)
MOVL BP, 0(SP)
CALL AX
// update stackguard after _cgo_init
MOVL $runtime·g0(SB), CX
MOVL (g_stack+stack_lo)(CX), AX
ADDL $const_StackGuard, AX
MOVL AX, g_stackguard0(CX)
MOVL AX, g_stackguard1(CX)
// skip runtime·ldt0setup(SB) and tls test after _cgo_init for non-windows
CMPL runtime·iswindows(SB), $0
JEQ ok
needtls:
// skip runtime·ldt0setup(SB) and tls test on Plan 9 in all cases
CMPL runtime·isplan9(SB), $1
JEQ ok
// set up %gs
CALL runtime·ldt0setup(SB)
// store through it, to make sure it works
get_tls(BX)
MOVL $0x123, g(BX)
MOVL runtime·tls0(SB), AX
CMPL AX, $0x123
JEQ ok
MOVL AX, 0 // abort
ok:
// set up m and g "registers"
get_tls(BX)
LEAL runtime·g0(SB), CX
MOVL CX, g(BX)
LEAL runtime·m0(SB), AX
// save m->g0 = g0
MOVL CX, m_g0(AX)
2014-06-26 09:54:39 -06:00
// save g0->m = m0
MOVL AX, g_m(CX)
CALL runtime·emptyfunc(SB) // fault if stack check is wrong
// convention is D is always cleared
CLD
CALL runtime·check(SB)
// saved argc, argv
MOVL 120(SP), AX
MOVL AX, 0(SP)
MOVL 124(SP), AX
MOVL AX, 4(SP)
CALL runtime·args(SB)
CALL runtime·osinit(SB)
CALL runtime·schedinit(SB)
// create a new goroutine to start program
PUSHL $runtime·main·f(SB) // entry
PUSHL $0 // arg size
CALL runtime·newproc(SB)
POPL AX
POPL AX
// start this M
CALL runtime·mstart(SB)
INT $3
RET
DATA runtime·main·f+0(SB)/4,$runtime·main(SB)
GLOBL runtime·main·f(SB),RODATA,$4
TEXT runtime·breakpoint(SB),NOSPLIT,$0-0
INT $3
RET
TEXT runtime·asminit(SB),NOSPLIT,$0-0
// Linux and MinGW start the FPU in extended double precision.
// Other operating systems use double precision.
// Change to double precision to match them,
// and to match other hardware that only has double.
PUSHL $0x27F
FLDCW 0(SP)
POPL AX
RET
/*
* go-routine
*/
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// void gosave(Gobuf*)
// save state in Gobuf; setjmp
TEXT runtime·gosave(SB), NOSPLIT, $0-4
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL buf+0(FP), AX // gobuf
LEAL buf+0(FP), BX // caller's SP
MOVL BX, gobuf_sp(AX)
MOVL 0(SP), BX // caller's PC
MOVL BX, gobuf_pc(AX)
MOVL $0, gobuf_ret(AX)
MOVL $0, gobuf_ctxt(AX)
get_tls(CX)
MOVL g(CX), BX
MOVL BX, gobuf_g(AX)
RET
// void gogo(Gobuf*)
// restore state from Gobuf; longjmp
TEXT runtime·gogo(SB), NOSPLIT, $0-4
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL buf+0(FP), BX // gobuf
MOVL gobuf_g(BX), DX
MOVL 0(DX), CX // make sure g != nil
get_tls(CX)
MOVL DX, g(CX)
MOVL gobuf_sp(BX), SP // restore SP
MOVL gobuf_ret(BX), AX
MOVL gobuf_ctxt(BX), DX
MOVL $0, gobuf_sp(BX) // clear to help garbage collector
MOVL $0, gobuf_ret(BX)
MOVL $0, gobuf_ctxt(BX)
MOVL gobuf_pc(BX), BX
JMP BX
// func mcall(fn func(*g))
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// Switch to m->g0's stack, call fn(g).
runtime: stack split + garbage collection bug The g->sched.sp saved stack pointer and the g->stackbase and g->stackguard stack bounds can change even while "the world is stopped", because a goroutine has to call functions (and therefore might split its stack) when exiting a system call to check whether the world is stopped (and if so, wait until the world continues). That means the garbage collector cannot access those values safely (without a race) for goroutines executing system calls. Instead, save a consistent triple in g->gcsp, g->gcstack, g->gcguard during entersyscall and have the garbage collector refer to those. The old code was occasionally seeing (because of the race) an sp and stk that did not correspond to each other, so that stk - sp was not the number of stack bytes following sp. In that case, if sp < stk then the call scanblock(sp, stk - sp) scanned too many bytes (anything between the two pointers, which pointed into different allocation blocks). If sp > stk then stk - sp wrapped around. On 32-bit, stk - sp is a uintptr (uint32) converted to int64 in the call to scanblock, so a large (~4G) but positive number. Scanblock would try to scan that many bytes and eventually fault accessing unmapped memory. On 64-bit, stk - sp is a uintptr (uint64) promoted to int64 in the call to scanblock, so a negative number. Scanblock would not scan anything, possibly causing in-use blocks to be freed. In short, 32-bit platforms would have seen either ineffective garbage collection or crashes during garbage collection, while 64-bit platforms would have seen either ineffective or incorrect garbage collection. You can see the invalid arguments to scanblock in the stack traces in issue 1620. Fixes #1620. Fixes #1746. R=iant, r CC=golang-dev https://golang.org/cl/4437075
2011-04-27 21:21:12 -06:00
// Fn must never return. It should gogo(&g->sched)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// to keep running g.
TEXT runtime·mcall(SB), NOSPLIT, $0-4
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL fn+0(FP), DI
get_tls(CX)
MOVL g(CX), AX // save state in g->sched
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL 0(SP), BX // caller's PC
MOVL BX, (g_sched+gobuf_pc)(AX)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
LEAL fn+0(FP), BX // caller's SP
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL BX, (g_sched+gobuf_sp)(AX)
MOVL AX, (g_sched+gobuf_g)(AX)
// switch to m->g0 & its stack, call fn
2014-06-26 09:54:39 -06:00
MOVL g(CX), BX
MOVL g_m(BX), BX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL m_g0(BX), SI
CMPL SI, AX // if g == m->g0 call badmcall
JNE 3(PC)
MOVL $runtime·badmcall(SB), AX
JMP AX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL SI, g(CX) // g = m->g0
MOVL (g_sched+gobuf_sp)(SI), SP // sp = m->g0->sched.sp
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
PUSHL AX
MOVL DI, DX
MOVL 0(DI), DI
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
CALL DI
POPL AX
MOVL $runtime·badmcall2(SB), AX
JMP AX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
RET
// switchtoM is a dummy routine that onM leaves at the bottom
// of the G stack. We need to distinguish the routine that
// lives at the bottom of the G stack from the one that lives
// at the top of the M stack because the one at the top of
// the M stack terminates the stack walk (see topofstack()).
TEXT runtime·switchtoM(SB), NOSPLIT, $0-0
RET
// func onM_signalok(fn func())
TEXT runtime·onM_signalok(SB), NOSPLIT, $0-4
get_tls(CX)
MOVL g(CX), AX // AX = g
MOVL g_m(AX), BX // BX = m
MOVL m_gsignal(BX), DX // DX = gsignal
CMPL AX, DX
JEQ ongsignal
JMP runtime·onM(SB)
ongsignal:
MOVL fn+0(FP), DI // DI = fn
MOVL DI, DX
MOVL 0(DI), DI
CALL DI
RET
// func onM(fn func())
TEXT runtime·onM(SB), NOSPLIT, $0-4
MOVL fn+0(FP), DI // DI = fn
get_tls(CX)
MOVL g(CX), AX // AX = g
MOVL g_m(AX), BX // BX = m
runtime: reject onM calls from gsignal stack The implementation and use patterns of onM assume that they run on either the m->curg or m->g0 stack. Calling onM from m->gsignal has two problems: (1) When not on g0, onM switches to g0 and then "back" to curg. If we didn't start at curg, bad things happen. (2) The use of scalararg/ptrarg to pass C arguments and results assumes that there is only one onM call at a time. If a gsignal starts running, it may have interrupted the setup/teardown of the args for an onM on the curg or g0 stack. Using scalararg/ptrarg itself would smash those. We can fix (1) by remembering what g was running before the switch. We can fix (2) by requiring that uses of onM that might happen on a signal handling stack must save the old scalararg/ptrarg and restore them after the call, instead of zeroing them. The only sane way to do this is to introduce a separate onM_signalsafe that omits the signal check, and then if you see a call to onM_signalsafe you know the surrounding code must preserve the old scalararg/ptrarg values. (The implementation would be that onM_signalsafe just calls fn if on the signal stack or else jumps to onM. It's not necessary to have two whole copies of the function.) (2) is not a problem if the caller and callee are both Go and a closure is used instead of the scalararg/ptrarg slots. For now, I think we can avoid calling onM from code executing on gsignal stacks, so just reject it. In the long term, (2) goes away (as do the scalararg/ptrarg slots) once everything is in Go, and at that point fixing (1) would be trivial and maybe worth doing just for regularity. LGTM=iant R=golang-codereviews, iant CC=dvyukov, golang-codereviews, khr, r https://golang.org/cl/135400043
2014-09-03 22:10:10 -06:00
MOVL m_g0(BX), DX // DX = g0
CMPL AX, DX
JEQ onm
runtime: reject onM calls from gsignal stack The implementation and use patterns of onM assume that they run on either the m->curg or m->g0 stack. Calling onM from m->gsignal has two problems: (1) When not on g0, onM switches to g0 and then "back" to curg. If we didn't start at curg, bad things happen. (2) The use of scalararg/ptrarg to pass C arguments and results assumes that there is only one onM call at a time. If a gsignal starts running, it may have interrupted the setup/teardown of the args for an onM on the curg or g0 stack. Using scalararg/ptrarg itself would smash those. We can fix (1) by remembering what g was running before the switch. We can fix (2) by requiring that uses of onM that might happen on a signal handling stack must save the old scalararg/ptrarg and restore them after the call, instead of zeroing them. The only sane way to do this is to introduce a separate onM_signalsafe that omits the signal check, and then if you see a call to onM_signalsafe you know the surrounding code must preserve the old scalararg/ptrarg values. (The implementation would be that onM_signalsafe just calls fn if on the signal stack or else jumps to onM. It's not necessary to have two whole copies of the function.) (2) is not a problem if the caller and callee are both Go and a closure is used instead of the scalararg/ptrarg slots. For now, I think we can avoid calling onM from code executing on gsignal stacks, so just reject it. In the long term, (2) goes away (as do the scalararg/ptrarg slots) once everything is in Go, and at that point fixing (1) would be trivial and maybe worth doing just for regularity. LGTM=iant R=golang-codereviews, iant CC=dvyukov, golang-codereviews, khr, r https://golang.org/cl/135400043
2014-09-03 22:10:10 -06:00
MOVL m_curg(BX), BP
CMPL AX, BP
JEQ oncurg
// Not g0, not curg. Must be gsignal, but that's not allowed.
// Hide call from linker nosplit analysis.
MOVL $runtime·badonm(SB), AX
CALL AX
oncurg:
// save our state in g->sched. Pretend to
// be switchtoM if the G stack is scanned.
MOVL $runtime·switchtoM(SB), (g_sched+gobuf_pc)(AX)
MOVL SP, (g_sched+gobuf_sp)(AX)
MOVL AX, (g_sched+gobuf_g)(AX)
// switch to g0
MOVL DX, g(CX)
MOVL (g_sched+gobuf_sp)(DX), BX
// make it look like mstart called onM on g0, to stop traceback
SUBL $4, BX
MOVL $runtime·mstart(SB), DX
MOVL DX, 0(BX)
MOVL BX, SP
// call target function
MOVL DI, DX
MOVL 0(DI), DI
CALL DI
// switch back to g
get_tls(CX)
MOVL g(CX), AX
MOVL g_m(AX), BX
MOVL m_curg(BX), AX
MOVL AX, g(CX)
MOVL (g_sched+gobuf_sp)(AX), SP
MOVL $0, (g_sched+gobuf_sp)(AX)
RET
onm:
// already on m stack, just call directly
MOVL DI, DX
MOVL 0(DI), DI
CALL DI
RET
/*
* support for morestack
*/
// Called during function prolog when more stack is needed.
//
// The traceback routines see morestack on a g0 as being
// the top of a stack (for example, morestack calling newstack
// calling the scheduler calling newm calling gc), so we must
// record an argument size. For that purpose, it has no arguments.
TEXT runtime·morestack(SB),NOSPLIT,$0-0
// Cannot grow scheduler stack (m->g0).
get_tls(CX)
2014-06-26 09:54:39 -06:00
MOVL g(CX), BX
MOVL g_m(BX), BX
MOVL m_g0(BX), SI
CMPL g(CX), SI
JNE 2(PC)
INT $3
// Cannot grow signal stack.
MOVL m_gsignal(BX), SI
CMPL g(CX), SI
JNE 2(PC)
INT $3
// Called from f.
// Set m->morebuf to f's caller.
MOVL 4(SP), DI // f's caller's PC
MOVL DI, (m_morebuf+gobuf_pc)(BX)
LEAL 8(SP), CX // f's caller's SP
MOVL CX, (m_morebuf+gobuf_sp)(BX)
get_tls(CX)
MOVL g(CX), SI
MOVL SI, (m_morebuf+gobuf_g)(BX)
runtime: record proper goroutine state during stack split Until now, the goroutine state has been scattered during the execution of newstack and oldstack. It's all there, and those routines know how to get back to a working goroutine, but other pieces of the system, like stack traces, do not. If something does interrupt the newstack or oldstack execution, the rest of the system can't understand the goroutine. For example, if newstack decides there is an overflow and calls throw, the stack tracer wouldn't dump the goroutine correctly. For newstack to save a useful state snapshot, it needs to be able to rewind the PC in the function that triggered the split back to the beginning of the function. (The PC is a few instructions in, just after the call to morestack.) To make that possible, we change the prologues to insert a jmp back to the beginning of the function after the call to morestack. That is, the prologue used to be roughly: TEXT myfunc check for split jmpcond nosplit call morestack nosplit: sub $xxx, sp Now an extra instruction is inserted after the call: TEXT myfunc start: check for split jmpcond nosplit call morestack jmp start nosplit: sub $xxx, sp The jmp is not executed directly. It is decoded and simulated by runtime.rewindmorestack to discover the beginning of the function, and then the call to morestack returns directly to the start label instead of to the jump instruction. So logically the jmp is still executed, just not by the cpu. The prologue thus repeats in the case of a function that needs a stack split, but against the cost of the split itself, the extra few instructions are noise. The repeated prologue has the nice effect of making a stack split double-check that the new stack is big enough: if morestack happens to return on a too-small stack, we'll now notice before corruption happens. The ability for newstack to rewind to the beginning of the function should help preemption too. If newstack decides that it was called for preemption instead of a stack split, it now has the goroutine state correctly paused if rescheduling is needed, and when the goroutine can run again, it can return to the start label on its original stack and re-execute the split check. Here is an example of a split stack overflow showing the full trace, without any special cases in the stack printer. (This one was triggered by making the split check incorrect.) runtime: newstack framesize=0x0 argsize=0x18 sp=0x6aebd0 stack=[0x6b0000, 0x6b0fa0] morebuf={pc:0x69f5b sp:0x6aebd8 lr:0x0} sched={pc:0x68880 sp:0x6aebd0 lr:0x0 ctxt:0x34e700} runtime: split stack overflow: 0x6aebd0 < 0x6b0000 fatal error: runtime: split stack overflow goroutine 1 [stack split]: runtime.mallocgc(0x290, 0x100000000, 0x1) /Users/rsc/g/go/src/pkg/runtime/zmalloc_darwin_amd64.c:21 fp=0x6aebd8 runtime.new() /Users/rsc/g/go/src/pkg/runtime/zmalloc_darwin_amd64.c:682 +0x5b fp=0x6aec08 go/build.(*Context).Import(0x5ae340, 0xc210030c71, 0xa, 0xc2100b4380, 0x1b, ...) /Users/rsc/g/go/src/pkg/go/build/build.go:424 +0x3a fp=0x6b00a0 main.loadImport(0xc210030c71, 0xa, 0xc2100b4380, 0x1b, 0xc2100b42c0, ...) /Users/rsc/g/go/src/cmd/go/pkg.go:249 +0x371 fp=0x6b01a8 main.(*Package).load(0xc21017c800, 0xc2100b42c0, 0xc2101828c0, 0x0, 0x0, ...) /Users/rsc/g/go/src/cmd/go/pkg.go:431 +0x2801 fp=0x6b0c98 main.loadPackage(0x369040, 0x7, 0xc2100b42c0, 0x0) /Users/rsc/g/go/src/cmd/go/pkg.go:709 +0x857 fp=0x6b0f80 ----- stack segment boundary ----- main.(*builder).action(0xc2100902a0, 0x0, 0x0, 0xc2100e6c00, 0xc2100e5750, ...) /Users/rsc/g/go/src/cmd/go/build.go:539 +0x437 fp=0x6b14a0 main.(*builder).action(0xc2100902a0, 0x0, 0x0, 0xc21015b400, 0x2, ...) /Users/rsc/g/go/src/cmd/go/build.go:528 +0x1d2 fp=0x6b1658 main.(*builder).test(0xc2100902a0, 0xc210092000, 0x0, 0x0, 0xc21008ff60, ...) /Users/rsc/g/go/src/cmd/go/test.go:622 +0x1b53 fp=0x6b1f68 ----- stack segment boundary ----- main.runTest(0x5a6b20, 0xc21000a020, 0x2, 0x2) /Users/rsc/g/go/src/cmd/go/test.go:366 +0xd09 fp=0x6a5cf0 main.main() /Users/rsc/g/go/src/cmd/go/main.go:161 +0x4f9 fp=0x6a5f78 runtime.main() /Users/rsc/g/go/src/pkg/runtime/proc.c:183 +0x92 fp=0x6a5fa0 runtime.goexit() /Users/rsc/g/go/src/pkg/runtime/proc.c:1266 fp=0x6a5fa8 And here is a seg fault during oldstack: SIGSEGV: segmentation violation PC=0x1b2a6 runtime.oldstack() /Users/rsc/g/go/src/pkg/runtime/stack.c:159 +0x76 runtime.lessstack() /Users/rsc/g/go/src/pkg/runtime/asm_amd64.s:270 +0x22 goroutine 1 [stack unsplit]: fmt.(*pp).printArg(0x2102e64e0, 0xe5c80, 0x2102c9220, 0x73, 0x0, ...) /Users/rsc/g/go/src/pkg/fmt/print.go:818 +0x3d3 fp=0x221031e6f8 fmt.(*pp).doPrintf(0x2102e64e0, 0x12fb20, 0x2, 0x221031eb98, 0x1, ...) /Users/rsc/g/go/src/pkg/fmt/print.go:1183 +0x15cb fp=0x221031eaf0 fmt.Sprintf(0x12fb20, 0x2, 0x221031eb98, 0x1, 0x1, ...) /Users/rsc/g/go/src/pkg/fmt/print.go:234 +0x67 fp=0x221031eb40 flag.(*stringValue).String(0x2102c9210, 0x1, 0x0) /Users/rsc/g/go/src/pkg/flag/flag.go:180 +0xb3 fp=0x221031ebb0 flag.(*FlagSet).Var(0x2102f6000, 0x293d38, 0x2102c9210, 0x143490, 0xa, ...) /Users/rsc/g/go/src/pkg/flag/flag.go:633 +0x40 fp=0x221031eca0 flag.(*FlagSet).StringVar(0x2102f6000, 0x2102c9210, 0x143490, 0xa, 0x12fa60, ...) /Users/rsc/g/go/src/pkg/flag/flag.go:550 +0x91 fp=0x221031ece8 flag.(*FlagSet).String(0x2102f6000, 0x143490, 0xa, 0x12fa60, 0x0, ...) /Users/rsc/g/go/src/pkg/flag/flag.go:563 +0x87 fp=0x221031ed38 flag.String(0x143490, 0xa, 0x12fa60, 0x0, 0x161950, ...) /Users/rsc/g/go/src/pkg/flag/flag.go:570 +0x6b fp=0x221031ed80 testing.init() /Users/rsc/g/go/src/pkg/testing/testing.go:-531 +0xbb fp=0x221031edc0 strings_test.init() /Users/rsc/g/go/src/pkg/strings/strings_test.go:1115 +0x62 fp=0x221031ef70 main.init() strings/_test/_testmain.go:90 +0x3d fp=0x221031ef78 runtime.main() /Users/rsc/g/go/src/pkg/runtime/proc.c:180 +0x8a fp=0x221031efa0 runtime.goexit() /Users/rsc/g/go/src/pkg/runtime/proc.c:1269 fp=0x221031efa8 goroutine 2 [runnable]: runtime.MHeap_Scavenger() /Users/rsc/g/go/src/pkg/runtime/mheap.c:438 runtime.goexit() /Users/rsc/g/go/src/pkg/runtime/proc.c:1269 created by runtime.main /Users/rsc/g/go/src/pkg/runtime/proc.c:166 rax 0x23ccc0 rbx 0x23ccc0 rcx 0x0 rdx 0x38 rdi 0x2102c0170 rsi 0x221032cfe0 rbp 0x221032cfa0 rsp 0x7fff5fbff5b0 r8 0x2102c0120 r9 0x221032cfa0 r10 0x221032c000 r11 0x104ce8 r12 0xe5c80 r13 0x1be82baac718 r14 0x13091135f7d69200 r15 0x0 rip 0x1b2a6 rflags 0x10246 cs 0x2b fs 0x0 gs 0x0 Fixes #5723. R=r, dvyukov, go.peter.90, dave, iant CC=golang-dev https://golang.org/cl/10360048
2013-06-27 09:32:01 -06:00
// Set g->sched to context in f.
MOVL 0(SP), AX // f's PC
MOVL AX, (g_sched+gobuf_pc)(SI)
MOVL SI, (g_sched+gobuf_g)(SI)
LEAL 4(SP), AX // f's SP
MOVL AX, (g_sched+gobuf_sp)(SI)
MOVL DX, (g_sched+gobuf_ctxt)(SI)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// Call newstack on m->g0's stack.
MOVL m_g0(BX), BP
MOVL BP, g(CX)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL (g_sched+gobuf_sp)(BP), AX
MOVL -4(AX), BX // fault if CALL would, before smashing SP
MOVL AX, SP
CALL runtime·newstack(SB)
MOVL $0, 0x1003 // crash if newstack returns
RET
TEXT runtime·morestack_noctxt(SB),NOSPLIT,$0-0
MOVL $0, DX
JMP runtime·morestack(SB)
// reflectcall: call a function with the given argument list
// func call(f *FuncVal, arg *byte, argsize, retoffset uint32).
// we don't have variable-sized frames, so we use a small number
// of constant-sized-frame functions to encode a few bits of size in the pc.
// Caution: ugly multiline assembly macros in your future!
#define DISPATCH(NAME,MAXSIZE) \
CMPL CX, $MAXSIZE; \
JA 3(PC); \
MOVL $NAME(SB), AX; \
JMP AX
// Note: can't just "JMP NAME(SB)" - bad inlining results.
TEXT ·reflectcall(SB), NOSPLIT, $0-16
MOVL argsize+8(FP), CX
DISPATCH(runtime·call16, 16)
DISPATCH(runtime·call32, 32)
DISPATCH(runtime·call64, 64)
DISPATCH(runtime·call128, 128)
DISPATCH(runtime·call256, 256)
DISPATCH(runtime·call512, 512)
DISPATCH(runtime·call1024, 1024)
DISPATCH(runtime·call2048, 2048)
DISPATCH(runtime·call4096, 4096)
DISPATCH(runtime·call8192, 8192)
DISPATCH(runtime·call16384, 16384)
DISPATCH(runtime·call32768, 32768)
DISPATCH(runtime·call65536, 65536)
DISPATCH(runtime·call131072, 131072)
DISPATCH(runtime·call262144, 262144)
DISPATCH(runtime·call524288, 524288)
DISPATCH(runtime·call1048576, 1048576)
DISPATCH(runtime·call2097152, 2097152)
DISPATCH(runtime·call4194304, 4194304)
DISPATCH(runtime·call8388608, 8388608)
DISPATCH(runtime·call16777216, 16777216)
DISPATCH(runtime·call33554432, 33554432)
DISPATCH(runtime·call67108864, 67108864)
DISPATCH(runtime·call134217728, 134217728)
DISPATCH(runtime·call268435456, 268435456)
DISPATCH(runtime·call536870912, 536870912)
DISPATCH(runtime·call1073741824, 1073741824)
MOVL $runtime·badreflectcall(SB), AX
JMP AX
#define CALLFN(NAME,MAXSIZE) \
TEXT NAME(SB), WRAPPER, $MAXSIZE-16; \
NO_LOCAL_POINTERS; \
/* copy arguments to stack */ \
MOVL argptr+4(FP), SI; \
MOVL argsize+8(FP), CX; \
MOVL SP, DI; \
REP;MOVSB; \
/* call function */ \
MOVL f+0(FP), DX; \
all: nacl import round 2 These previously reviewed CLs are present in this CL. --- changeset: 18445:436bb084caed user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:50:34 2013 -0500 description: runtime: assembly and system calls for Native Client x86-64 See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡adg https://golang.org/cl/15760044 --- changeset: 18448:90bd871b5994 user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:51:36 2013 -0500 description: runtime: amd64p32 and Native Client assembly bootstrap See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡khr https://golang.org/cl/15820043 --- changeset: 18449:b011c3dc687e user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:51:58 2013 -0500 description: math: amd64p32 assembly routines These routines only manipulate float64 values, so the amd64 and amd64p32 can share assembly. The large number of files is symptomatic of a problem with package path: it is a Go package structured like a C library. But that will need to wait for another day. See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡bradfitz https://golang.org/cl/15870043 --- changeset: 18450:43234f082eec user: Russ Cox <rsc@golang.org> date: Mon Nov 11 10:03:19 2013 -0500 description: syscall: networking for Native Client See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡rsc https://golang.org/cl/15780043 --- changeset: 18451:9c8d1d890aaa user: Russ Cox <rsc@golang.org> date: Mon Nov 11 10:03:34 2013 -0500 description: runtime: assembly and system calls for Native Client x86-32 See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡rsc https://golang.org/cl/15800043 --- changeset: 18452:f90b1dd9228f user: Russ Cox <rsc@golang.org> date: Mon Nov 11 11:04:09 2013 -0500 description: runtime: fix frame size for linux/amd64 runtime.raise R≡rsc https://golang.org/cl/24480043 --- changeset: 18445:436bb084caed user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:50:34 2013 -0500 description: runtime: assembly and system calls for Native Client x86-64 See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡adg https://golang.org/cl/15760044 --- changeset: 18455:53b06799a938 user: Russ Cox <rsc@golang.org> date: Mon Nov 11 23:29:52 2013 -0500 description: cmd/gc: add -nolocalimports flag R≡dsymonds https://golang.org/cl/24990043 --- changeset: 18456:24f64e1eaa8a user: Russ Cox <rsc@golang.org> date: Tue Nov 12 22:06:29 2013 -0500 description: runtime: add comments for playback write R≡adg https://golang.org/cl/25190043 --- changeset: 18457:d1f615bbb6e4 user: Russ Cox <rsc@golang.org> date: Wed Nov 13 17:03:52 2013 -0500 description: runtime: write only to NaCl stdout, never to NaCl stderr NaCl writes some other messages on standard error that we would like to be able to squelch. R≡adg https://golang.org/cl/26240044 --- changeset: 18458:1f01be1a1dc2 tag: tip user: Russ Cox <rsc@golang.org> date: Wed Nov 13 19:45:16 2013 -0500 description: runtime: remove apparent debugging dreg Setting timens to 0 turns off fake time. TBR≡adg https://golang.org/cl/26400043 LGTM=bradfitz R=dave, bradfitz CC=golang-codereviews https://golang.org/cl/68730043
2014-02-25 15:00:08 -07:00
MOVL (DX), AX; \
PCDATA $PCDATA_StackMapIndex, $0; \
all: nacl import round 2 These previously reviewed CLs are present in this CL. --- changeset: 18445:436bb084caed user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:50:34 2013 -0500 description: runtime: assembly and system calls for Native Client x86-64 See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡adg https://golang.org/cl/15760044 --- changeset: 18448:90bd871b5994 user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:51:36 2013 -0500 description: runtime: amd64p32 and Native Client assembly bootstrap See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡khr https://golang.org/cl/15820043 --- changeset: 18449:b011c3dc687e user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:51:58 2013 -0500 description: math: amd64p32 assembly routines These routines only manipulate float64 values, so the amd64 and amd64p32 can share assembly. The large number of files is symptomatic of a problem with package path: it is a Go package structured like a C library. But that will need to wait for another day. See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡bradfitz https://golang.org/cl/15870043 --- changeset: 18450:43234f082eec user: Russ Cox <rsc@golang.org> date: Mon Nov 11 10:03:19 2013 -0500 description: syscall: networking for Native Client See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡rsc https://golang.org/cl/15780043 --- changeset: 18451:9c8d1d890aaa user: Russ Cox <rsc@golang.org> date: Mon Nov 11 10:03:34 2013 -0500 description: runtime: assembly and system calls for Native Client x86-32 See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡rsc https://golang.org/cl/15800043 --- changeset: 18452:f90b1dd9228f user: Russ Cox <rsc@golang.org> date: Mon Nov 11 11:04:09 2013 -0500 description: runtime: fix frame size for linux/amd64 runtime.raise R≡rsc https://golang.org/cl/24480043 --- changeset: 18445:436bb084caed user: Russ Cox <rsc@golang.org> date: Mon Nov 11 09:50:34 2013 -0500 description: runtime: assembly and system calls for Native Client x86-64 See golang.org/s/go13nacl for design overview. This CL is publicly visible but not CC'ed to golang-dev, to avoid distracting from the preparation of the Go 1.2 release. This CL and the others will be checked into my rsc-go13nacl clone repo for now, and I will send CLs against the main repo early in the Go 1.3 development. R≡adg https://golang.org/cl/15760044 --- changeset: 18455:53b06799a938 user: Russ Cox <rsc@golang.org> date: Mon Nov 11 23:29:52 2013 -0500 description: cmd/gc: add -nolocalimports flag R≡dsymonds https://golang.org/cl/24990043 --- changeset: 18456:24f64e1eaa8a user: Russ Cox <rsc@golang.org> date: Tue Nov 12 22:06:29 2013 -0500 description: runtime: add comments for playback write R≡adg https://golang.org/cl/25190043 --- changeset: 18457:d1f615bbb6e4 user: Russ Cox <rsc@golang.org> date: Wed Nov 13 17:03:52 2013 -0500 description: runtime: write only to NaCl stdout, never to NaCl stderr NaCl writes some other messages on standard error that we would like to be able to squelch. R≡adg https://golang.org/cl/26240044 --- changeset: 18458:1f01be1a1dc2 tag: tip user: Russ Cox <rsc@golang.org> date: Wed Nov 13 19:45:16 2013 -0500 description: runtime: remove apparent debugging dreg Setting timens to 0 turns off fake time. TBR≡adg https://golang.org/cl/26400043 LGTM=bradfitz R=dave, bradfitz CC=golang-codereviews https://golang.org/cl/68730043
2014-02-25 15:00:08 -07:00
CALL AX; \
/* copy return values back */ \
MOVL argptr+4(FP), DI; \
MOVL argsize+8(FP), CX; \
reflect, runtime: fix crash in GC due to reflect.call + precise GC Given type Outer struct { *Inner ... } the compiler generates the implementation of (*Outer).M dispatching to the embedded Inner. The implementation is logically: func (p *Outer) M() { (p.Inner).M() } but since the only change here is the replacement of one pointer receiver with another, the actual generated code overwrites the original receiver with the p.Inner pointer and then jumps to the M method expecting the *Inner receiver. During reflect.Value.Call, we create an argument frame and the associated data structures to describe it to the garbage collector, populate the frame, call reflect.call to run a function call using that frame, and then copy the results back out of the frame. The reflect.call function does a memmove of the frame structure onto the stack (to set up the inputs), runs the call, and the memmoves the stack back to the frame structure (to preserve the outputs). Originally reflect.call did not distinguish inputs from outputs: both memmoves were for the full stack frame. However, in the case where the called function was one of these wrappers, the rewritten receiver is almost certainly a different type than the original receiver. This is not a problem on the stack, where we use the program counter to determine the type information and understand that during (*Outer).M the receiver is an *Outer while during (*Inner).M the receiver in the same memory word is now an *Inner. But in the statically typed argument frame created by reflect, the receiver is always an *Outer. Copying the modified receiver pointer off the stack into the frame will store an *Inner there, and then if a garbage collection happens to scan that argument frame before it is discarded, it will scan the *Inner memory as if it were an *Outer. If the two have different memory layouts, the collection will intepret the memory incorrectly. Fix by only copying back the results. Fixes #7725. LGTM=khr R=khr CC=dave, golang-codereviews https://golang.org/cl/85180043
2014-04-08 09:11:35 -06:00
MOVL retoffset+12(FP), BX; \
MOVL SP, SI; \
reflect, runtime: fix crash in GC due to reflect.call + precise GC Given type Outer struct { *Inner ... } the compiler generates the implementation of (*Outer).M dispatching to the embedded Inner. The implementation is logically: func (p *Outer) M() { (p.Inner).M() } but since the only change here is the replacement of one pointer receiver with another, the actual generated code overwrites the original receiver with the p.Inner pointer and then jumps to the M method expecting the *Inner receiver. During reflect.Value.Call, we create an argument frame and the associated data structures to describe it to the garbage collector, populate the frame, call reflect.call to run a function call using that frame, and then copy the results back out of the frame. The reflect.call function does a memmove of the frame structure onto the stack (to set up the inputs), runs the call, and the memmoves the stack back to the frame structure (to preserve the outputs). Originally reflect.call did not distinguish inputs from outputs: both memmoves were for the full stack frame. However, in the case where the called function was one of these wrappers, the rewritten receiver is almost certainly a different type than the original receiver. This is not a problem on the stack, where we use the program counter to determine the type information and understand that during (*Outer).M the receiver is an *Outer while during (*Inner).M the receiver in the same memory word is now an *Inner. But in the statically typed argument frame created by reflect, the receiver is always an *Outer. Copying the modified receiver pointer off the stack into the frame will store an *Inner there, and then if a garbage collection happens to scan that argument frame before it is discarded, it will scan the *Inner memory as if it were an *Outer. If the two have different memory layouts, the collection will intepret the memory incorrectly. Fix by only copying back the results. Fixes #7725. LGTM=khr R=khr CC=dave, golang-codereviews https://golang.org/cl/85180043
2014-04-08 09:11:35 -06:00
ADDL BX, DI; \
ADDL BX, SI; \
SUBL BX, CX; \
REP;MOVSB; \
RET
CALLFN(·call16, 16)
CALLFN(·call32, 32)
CALLFN(·call64, 64)
CALLFN(·call128, 128)
CALLFN(·call256, 256)
CALLFN(·call512, 512)
CALLFN(·call1024, 1024)
CALLFN(·call2048, 2048)
CALLFN(·call4096, 4096)
CALLFN(·call8192, 8192)
CALLFN(·call16384, 16384)
CALLFN(·call32768, 32768)
CALLFN(·call65536, 65536)
CALLFN(·call131072, 131072)
CALLFN(·call262144, 262144)
CALLFN(·call524288, 524288)
CALLFN(·call1048576, 1048576)
CALLFN(·call2097152, 2097152)
CALLFN(·call4194304, 4194304)
CALLFN(·call8388608, 8388608)
CALLFN(·call16777216, 16777216)
CALLFN(·call33554432, 33554432)
CALLFN(·call67108864, 67108864)
CALLFN(·call134217728, 134217728)
CALLFN(·call268435456, 268435456)
CALLFN(·call536870912, 536870912)
CALLFN(·call1073741824, 1073741824)
// bool cas(int32 *val, int32 old, int32 new)
// Atomically:
// if(*val == old){
// *val = new;
// return 1;
// }else
// return 0;
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·cas(SB), NOSPLIT, $0-13
MOVL ptr+0(FP), BX
MOVL old+4(FP), AX
MOVL new+8(FP), CX
LOCK
CMPXCHGL CX, 0(BX)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
JZ 4(PC)
MOVL $0, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVB AX, ret+12(FP)
RET
MOVL $1, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVB AX, ret+12(FP)
RET
TEXT runtime·casuintptr(SB), NOSPLIT, $0-13
JMP runtime·cas(SB)
TEXT runtime·atomicloaduintptr(SB), NOSPLIT, $0-8
JMP runtime·atomicload(SB)
TEXT runtime·atomicloaduint(SB), NOSPLIT, $0-8
JMP runtime·atomicload(SB)
TEXT runtime·atomicstoreuintptr(SB), NOSPLIT, $0-8
JMP runtime·atomicstore(SB)
// bool runtime·cas64(uint64 *val, uint64 old, uint64 new)
// Atomically:
// if(*val == *old){
// *val = new;
// return 1;
// } else {
// return 0;
// }
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·cas64(SB), NOSPLIT, $0-21
MOVL ptr+0(FP), BP
MOVL old_lo+4(FP), AX
MOVL old_hi+8(FP), DX
MOVL new_lo+12(FP), BX
MOVL new_hi+16(FP), CX
LOCK
CMPXCHG8B 0(BP)
JNZ cas64_fail
MOVL $1, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVB AX, ret+20(FP)
RET
cas64_fail:
MOVL $0, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVB AX, ret+20(FP)
RET
// bool casp(void **p, void *old, void *new)
// Atomically:
// if(*p == old){
// *p = new;
// return 1;
// }else
// return 0;
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·casp(SB), NOSPLIT, $0-13
MOVL ptr+0(FP), BX
MOVL old+4(FP), AX
MOVL new+8(FP), CX
LOCK
CMPXCHGL CX, 0(BX)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
JZ 4(PC)
MOVL $0, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVB AX, ret+12(FP)
RET
MOVL $1, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVB AX, ret+12(FP)
RET
// uint32 xadd(uint32 volatile *val, int32 delta)
// Atomically:
// *val += delta;
// return *val;
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·xadd(SB), NOSPLIT, $0-12
MOVL ptr+0(FP), BX
MOVL delta+4(FP), AX
MOVL AX, CX
LOCK
XADDL AX, 0(BX)
ADDL CX, AX
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret+8(FP)
RET
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·xchg(SB), NOSPLIT, $0-12
MOVL ptr+0(FP), BX
MOVL new+4(FP), AX
runtime: improve Linux mutex The implementation is hybrid active/passive spin/blocking mutex. The design minimizes amount of context switches and futex calls. The idea is that all critical sections in runtime are intentially small, so pure blocking mutex behaves badly causing a lot of context switches, thread parking/unparking and kernel calls. Note that some synthetic benchmarks become somewhat slower, that's due to increased contention on other data structures, it should not affect programs that do any real work. On 2 x Intel E5620, 8 HT cores, 2.4GHz benchmark old ns/op new ns/op delta BenchmarkSelectContended 521.00 503.00 -3.45% BenchmarkSelectContended-2 661.00 320.00 -51.59% BenchmarkSelectContended-4 1139.00 629.00 -44.78% BenchmarkSelectContended-8 2870.00 878.00 -69.41% BenchmarkSelectContended-16 5276.00 818.00 -84.50% BenchmarkChanContended 112.00 103.00 -8.04% BenchmarkChanContended-2 631.00 174.00 -72.42% BenchmarkChanContended-4 682.00 272.00 -60.12% BenchmarkChanContended-8 1601.00 520.00 -67.52% BenchmarkChanContended-16 3100.00 372.00 -88.00% BenchmarkChanSync 253.00 239.00 -5.53% BenchmarkChanSync-2 5030.00 4648.00 -7.59% BenchmarkChanSync-4 4826.00 4694.00 -2.74% BenchmarkChanSync-8 4778.00 4713.00 -1.36% BenchmarkChanSync-16 5289.00 4710.00 -10.95% BenchmarkChanProdCons0 273.00 254.00 -6.96% BenchmarkChanProdCons0-2 599.00 400.00 -33.22% BenchmarkChanProdCons0-4 1168.00 659.00 -43.58% BenchmarkChanProdCons0-8 2831.00 1057.00 -62.66% BenchmarkChanProdCons0-16 4197.00 1037.00 -75.29% BenchmarkChanProdCons10 150.00 140.00 -6.67% BenchmarkChanProdCons10-2 607.00 268.00 -55.85% BenchmarkChanProdCons10-4 1137.00 404.00 -64.47% BenchmarkChanProdCons10-8 2115.00 828.00 -60.85% BenchmarkChanProdCons10-16 4283.00 855.00 -80.04% BenchmarkChanProdCons100 117.00 110.00 -5.98% BenchmarkChanProdCons100-2 558.00 218.00 -60.93% BenchmarkChanProdCons100-4 722.00 287.00 -60.25% BenchmarkChanProdCons100-8 1840.00 431.00 -76.58% BenchmarkChanProdCons100-16 3394.00 448.00 -86.80% BenchmarkChanProdConsWork0 2014.00 1996.00 -0.89% BenchmarkChanProdConsWork0-2 1207.00 1127.00 -6.63% BenchmarkChanProdConsWork0-4 1913.00 611.00 -68.06% BenchmarkChanProdConsWork0-8 3016.00 949.00 -68.53% BenchmarkChanProdConsWork0-16 4320.00 1154.00 -73.29% BenchmarkChanProdConsWork10 1906.00 1897.00 -0.47% BenchmarkChanProdConsWork10-2 1123.00 1033.00 -8.01% BenchmarkChanProdConsWork10-4 1076.00 571.00 -46.93% BenchmarkChanProdConsWork10-8 2748.00 1096.00 -60.12% BenchmarkChanProdConsWork10-16 4600.00 1105.00 -75.98% BenchmarkChanProdConsWork100 1884.00 1852.00 -1.70% BenchmarkChanProdConsWork100-2 1235.00 1146.00 -7.21% BenchmarkChanProdConsWork100-4 1217.00 619.00 -49.14% BenchmarkChanProdConsWork100-8 1534.00 509.00 -66.82% BenchmarkChanProdConsWork100-16 4126.00 918.00 -77.75% BenchmarkSyscall 34.40 33.30 -3.20% BenchmarkSyscall-2 160.00 121.00 -24.38% BenchmarkSyscall-4 131.00 136.00 +3.82% BenchmarkSyscall-8 139.00 131.00 -5.76% BenchmarkSyscall-16 161.00 168.00 +4.35% BenchmarkSyscallWork 950.00 950.00 +0.00% BenchmarkSyscallWork-2 481.00 480.00 -0.21% BenchmarkSyscallWork-4 268.00 270.00 +0.75% BenchmarkSyscallWork-8 156.00 169.00 +8.33% BenchmarkSyscallWork-16 188.00 184.00 -2.13% BenchmarkSemaSyntNonblock 36.40 35.60 -2.20% BenchmarkSemaSyntNonblock-2 81.40 45.10 -44.59% BenchmarkSemaSyntNonblock-4 126.00 108.00 -14.29% BenchmarkSemaSyntNonblock-8 112.00 112.00 +0.00% BenchmarkSemaSyntNonblock-16 110.00 112.00 +1.82% BenchmarkSemaSyntBlock 35.30 35.30 +0.00% BenchmarkSemaSyntBlock-2 118.00 124.00 +5.08% BenchmarkSemaSyntBlock-4 105.00 108.00 +2.86% BenchmarkSemaSyntBlock-8 101.00 111.00 +9.90% BenchmarkSemaSyntBlock-16 112.00 118.00 +5.36% BenchmarkSemaWorkNonblock 810.00 811.00 +0.12% BenchmarkSemaWorkNonblock-2 476.00 414.00 -13.03% BenchmarkSemaWorkNonblock-4 238.00 228.00 -4.20% BenchmarkSemaWorkNonblock-8 140.00 126.00 -10.00% BenchmarkSemaWorkNonblock-16 117.00 116.00 -0.85% BenchmarkSemaWorkBlock 810.00 811.00 +0.12% BenchmarkSemaWorkBlock-2 454.00 466.00 +2.64% BenchmarkSemaWorkBlock-4 243.00 241.00 -0.82% BenchmarkSemaWorkBlock-8 145.00 137.00 -5.52% BenchmarkSemaWorkBlock-16 132.00 123.00 -6.82% BenchmarkContendedSemaphore 123.00 102.00 -17.07% BenchmarkContendedSemaphore-2 34.80 34.90 +0.29% BenchmarkContendedSemaphore-4 34.70 34.80 +0.29% BenchmarkContendedSemaphore-8 34.70 34.70 +0.00% BenchmarkContendedSemaphore-16 34.80 34.70 -0.29% BenchmarkMutex 26.80 26.00 -2.99% BenchmarkMutex-2 108.00 45.20 -58.15% BenchmarkMutex-4 103.00 127.00 +23.30% BenchmarkMutex-8 109.00 147.00 +34.86% BenchmarkMutex-16 102.00 152.00 +49.02% BenchmarkMutexSlack 27.00 26.90 -0.37% BenchmarkMutexSlack-2 149.00 165.00 +10.74% BenchmarkMutexSlack-4 121.00 209.00 +72.73% BenchmarkMutexSlack-8 101.00 158.00 +56.44% BenchmarkMutexSlack-16 97.00 129.00 +32.99% BenchmarkMutexWork 792.00 794.00 +0.25% BenchmarkMutexWork-2 407.00 409.00 +0.49% BenchmarkMutexWork-4 220.00 209.00 -5.00% BenchmarkMutexWork-8 267.00 160.00 -40.07% BenchmarkMutexWork-16 315.00 300.00 -4.76% BenchmarkMutexWorkSlack 792.00 793.00 +0.13% BenchmarkMutexWorkSlack-2 406.00 404.00 -0.49% BenchmarkMutexWorkSlack-4 225.00 212.00 -5.78% BenchmarkMutexWorkSlack-8 268.00 136.00 -49.25% BenchmarkMutexWorkSlack-16 300.00 300.00 +0.00% BenchmarkRWMutexWrite100 27.10 27.00 -0.37% BenchmarkRWMutexWrite100-2 33.10 40.80 +23.26% BenchmarkRWMutexWrite100-4 113.00 88.10 -22.04% BenchmarkRWMutexWrite100-8 119.00 95.30 -19.92% BenchmarkRWMutexWrite100-16 148.00 109.00 -26.35% BenchmarkRWMutexWrite10 29.60 29.40 -0.68% BenchmarkRWMutexWrite10-2 111.00 61.40 -44.68% BenchmarkRWMutexWrite10-4 270.00 208.00 -22.96% BenchmarkRWMutexWrite10-8 204.00 185.00 -9.31% BenchmarkRWMutexWrite10-16 261.00 190.00 -27.20% BenchmarkRWMutexWorkWrite100 1040.00 1036.00 -0.38% BenchmarkRWMutexWorkWrite100-2 593.00 580.00 -2.19% BenchmarkRWMutexWorkWrite100-4 470.00 365.00 -22.34% BenchmarkRWMutexWorkWrite100-8 468.00 289.00 -38.25% BenchmarkRWMutexWorkWrite100-16 604.00 374.00 -38.08% BenchmarkRWMutexWorkWrite10 951.00 951.00 +0.00% BenchmarkRWMutexWorkWrite10-2 1001.00 928.00 -7.29% BenchmarkRWMutexWorkWrite10-4 1555.00 1006.00 -35.31% BenchmarkRWMutexWorkWrite10-8 2085.00 1171.00 -43.84% BenchmarkRWMutexWorkWrite10-16 2082.00 1614.00 -22.48% R=rsc, iant, msolo, fw, iant CC=golang-dev https://golang.org/cl/4711045
2011-07-29 10:44:06 -06:00
XCHGL AX, 0(BX)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret+8(FP)
runtime: improve Linux mutex The implementation is hybrid active/passive spin/blocking mutex. The design minimizes amount of context switches and futex calls. The idea is that all critical sections in runtime are intentially small, so pure blocking mutex behaves badly causing a lot of context switches, thread parking/unparking and kernel calls. Note that some synthetic benchmarks become somewhat slower, that's due to increased contention on other data structures, it should not affect programs that do any real work. On 2 x Intel E5620, 8 HT cores, 2.4GHz benchmark old ns/op new ns/op delta BenchmarkSelectContended 521.00 503.00 -3.45% BenchmarkSelectContended-2 661.00 320.00 -51.59% BenchmarkSelectContended-4 1139.00 629.00 -44.78% BenchmarkSelectContended-8 2870.00 878.00 -69.41% BenchmarkSelectContended-16 5276.00 818.00 -84.50% BenchmarkChanContended 112.00 103.00 -8.04% BenchmarkChanContended-2 631.00 174.00 -72.42% BenchmarkChanContended-4 682.00 272.00 -60.12% BenchmarkChanContended-8 1601.00 520.00 -67.52% BenchmarkChanContended-16 3100.00 372.00 -88.00% BenchmarkChanSync 253.00 239.00 -5.53% BenchmarkChanSync-2 5030.00 4648.00 -7.59% BenchmarkChanSync-4 4826.00 4694.00 -2.74% BenchmarkChanSync-8 4778.00 4713.00 -1.36% BenchmarkChanSync-16 5289.00 4710.00 -10.95% BenchmarkChanProdCons0 273.00 254.00 -6.96% BenchmarkChanProdCons0-2 599.00 400.00 -33.22% BenchmarkChanProdCons0-4 1168.00 659.00 -43.58% BenchmarkChanProdCons0-8 2831.00 1057.00 -62.66% BenchmarkChanProdCons0-16 4197.00 1037.00 -75.29% BenchmarkChanProdCons10 150.00 140.00 -6.67% BenchmarkChanProdCons10-2 607.00 268.00 -55.85% BenchmarkChanProdCons10-4 1137.00 404.00 -64.47% BenchmarkChanProdCons10-8 2115.00 828.00 -60.85% BenchmarkChanProdCons10-16 4283.00 855.00 -80.04% BenchmarkChanProdCons100 117.00 110.00 -5.98% BenchmarkChanProdCons100-2 558.00 218.00 -60.93% BenchmarkChanProdCons100-4 722.00 287.00 -60.25% BenchmarkChanProdCons100-8 1840.00 431.00 -76.58% BenchmarkChanProdCons100-16 3394.00 448.00 -86.80% BenchmarkChanProdConsWork0 2014.00 1996.00 -0.89% BenchmarkChanProdConsWork0-2 1207.00 1127.00 -6.63% BenchmarkChanProdConsWork0-4 1913.00 611.00 -68.06% BenchmarkChanProdConsWork0-8 3016.00 949.00 -68.53% BenchmarkChanProdConsWork0-16 4320.00 1154.00 -73.29% BenchmarkChanProdConsWork10 1906.00 1897.00 -0.47% BenchmarkChanProdConsWork10-2 1123.00 1033.00 -8.01% BenchmarkChanProdConsWork10-4 1076.00 571.00 -46.93% BenchmarkChanProdConsWork10-8 2748.00 1096.00 -60.12% BenchmarkChanProdConsWork10-16 4600.00 1105.00 -75.98% BenchmarkChanProdConsWork100 1884.00 1852.00 -1.70% BenchmarkChanProdConsWork100-2 1235.00 1146.00 -7.21% BenchmarkChanProdConsWork100-4 1217.00 619.00 -49.14% BenchmarkChanProdConsWork100-8 1534.00 509.00 -66.82% BenchmarkChanProdConsWork100-16 4126.00 918.00 -77.75% BenchmarkSyscall 34.40 33.30 -3.20% BenchmarkSyscall-2 160.00 121.00 -24.38% BenchmarkSyscall-4 131.00 136.00 +3.82% BenchmarkSyscall-8 139.00 131.00 -5.76% BenchmarkSyscall-16 161.00 168.00 +4.35% BenchmarkSyscallWork 950.00 950.00 +0.00% BenchmarkSyscallWork-2 481.00 480.00 -0.21% BenchmarkSyscallWork-4 268.00 270.00 +0.75% BenchmarkSyscallWork-8 156.00 169.00 +8.33% BenchmarkSyscallWork-16 188.00 184.00 -2.13% BenchmarkSemaSyntNonblock 36.40 35.60 -2.20% BenchmarkSemaSyntNonblock-2 81.40 45.10 -44.59% BenchmarkSemaSyntNonblock-4 126.00 108.00 -14.29% BenchmarkSemaSyntNonblock-8 112.00 112.00 +0.00% BenchmarkSemaSyntNonblock-16 110.00 112.00 +1.82% BenchmarkSemaSyntBlock 35.30 35.30 +0.00% BenchmarkSemaSyntBlock-2 118.00 124.00 +5.08% BenchmarkSemaSyntBlock-4 105.00 108.00 +2.86% BenchmarkSemaSyntBlock-8 101.00 111.00 +9.90% BenchmarkSemaSyntBlock-16 112.00 118.00 +5.36% BenchmarkSemaWorkNonblock 810.00 811.00 +0.12% BenchmarkSemaWorkNonblock-2 476.00 414.00 -13.03% BenchmarkSemaWorkNonblock-4 238.00 228.00 -4.20% BenchmarkSemaWorkNonblock-8 140.00 126.00 -10.00% BenchmarkSemaWorkNonblock-16 117.00 116.00 -0.85% BenchmarkSemaWorkBlock 810.00 811.00 +0.12% BenchmarkSemaWorkBlock-2 454.00 466.00 +2.64% BenchmarkSemaWorkBlock-4 243.00 241.00 -0.82% BenchmarkSemaWorkBlock-8 145.00 137.00 -5.52% BenchmarkSemaWorkBlock-16 132.00 123.00 -6.82% BenchmarkContendedSemaphore 123.00 102.00 -17.07% BenchmarkContendedSemaphore-2 34.80 34.90 +0.29% BenchmarkContendedSemaphore-4 34.70 34.80 +0.29% BenchmarkContendedSemaphore-8 34.70 34.70 +0.00% BenchmarkContendedSemaphore-16 34.80 34.70 -0.29% BenchmarkMutex 26.80 26.00 -2.99% BenchmarkMutex-2 108.00 45.20 -58.15% BenchmarkMutex-4 103.00 127.00 +23.30% BenchmarkMutex-8 109.00 147.00 +34.86% BenchmarkMutex-16 102.00 152.00 +49.02% BenchmarkMutexSlack 27.00 26.90 -0.37% BenchmarkMutexSlack-2 149.00 165.00 +10.74% BenchmarkMutexSlack-4 121.00 209.00 +72.73% BenchmarkMutexSlack-8 101.00 158.00 +56.44% BenchmarkMutexSlack-16 97.00 129.00 +32.99% BenchmarkMutexWork 792.00 794.00 +0.25% BenchmarkMutexWork-2 407.00 409.00 +0.49% BenchmarkMutexWork-4 220.00 209.00 -5.00% BenchmarkMutexWork-8 267.00 160.00 -40.07% BenchmarkMutexWork-16 315.00 300.00 -4.76% BenchmarkMutexWorkSlack 792.00 793.00 +0.13% BenchmarkMutexWorkSlack-2 406.00 404.00 -0.49% BenchmarkMutexWorkSlack-4 225.00 212.00 -5.78% BenchmarkMutexWorkSlack-8 268.00 136.00 -49.25% BenchmarkMutexWorkSlack-16 300.00 300.00 +0.00% BenchmarkRWMutexWrite100 27.10 27.00 -0.37% BenchmarkRWMutexWrite100-2 33.10 40.80 +23.26% BenchmarkRWMutexWrite100-4 113.00 88.10 -22.04% BenchmarkRWMutexWrite100-8 119.00 95.30 -19.92% BenchmarkRWMutexWrite100-16 148.00 109.00 -26.35% BenchmarkRWMutexWrite10 29.60 29.40 -0.68% BenchmarkRWMutexWrite10-2 111.00 61.40 -44.68% BenchmarkRWMutexWrite10-4 270.00 208.00 -22.96% BenchmarkRWMutexWrite10-8 204.00 185.00 -9.31% BenchmarkRWMutexWrite10-16 261.00 190.00 -27.20% BenchmarkRWMutexWorkWrite100 1040.00 1036.00 -0.38% BenchmarkRWMutexWorkWrite100-2 593.00 580.00 -2.19% BenchmarkRWMutexWorkWrite100-4 470.00 365.00 -22.34% BenchmarkRWMutexWorkWrite100-8 468.00 289.00 -38.25% BenchmarkRWMutexWorkWrite100-16 604.00 374.00 -38.08% BenchmarkRWMutexWorkWrite10 951.00 951.00 +0.00% BenchmarkRWMutexWorkWrite10-2 1001.00 928.00 -7.29% BenchmarkRWMutexWorkWrite10-4 1555.00 1006.00 -35.31% BenchmarkRWMutexWorkWrite10-8 2085.00 1171.00 -43.84% BenchmarkRWMutexWorkWrite10-16 2082.00 1614.00 -22.48% R=rsc, iant, msolo, fw, iant CC=golang-dev https://golang.org/cl/4711045
2011-07-29 10:44:06 -06:00
RET
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·xchgp(SB), NOSPLIT, $0-12
MOVL ptr+0(FP), BX
MOVL new+4(FP), AX
XCHGL AX, 0(BX)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret+8(FP)
RET
TEXT runtime·xchguintptr(SB), NOSPLIT, $0-12
JMP runtime·xchg(SB)
TEXT runtime·procyield(SB),NOSPLIT,$0-0
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL cycles+0(FP), AX
runtime: improve Linux mutex The implementation is hybrid active/passive spin/blocking mutex. The design minimizes amount of context switches and futex calls. The idea is that all critical sections in runtime are intentially small, so pure blocking mutex behaves badly causing a lot of context switches, thread parking/unparking and kernel calls. Note that some synthetic benchmarks become somewhat slower, that's due to increased contention on other data structures, it should not affect programs that do any real work. On 2 x Intel E5620, 8 HT cores, 2.4GHz benchmark old ns/op new ns/op delta BenchmarkSelectContended 521.00 503.00 -3.45% BenchmarkSelectContended-2 661.00 320.00 -51.59% BenchmarkSelectContended-4 1139.00 629.00 -44.78% BenchmarkSelectContended-8 2870.00 878.00 -69.41% BenchmarkSelectContended-16 5276.00 818.00 -84.50% BenchmarkChanContended 112.00 103.00 -8.04% BenchmarkChanContended-2 631.00 174.00 -72.42% BenchmarkChanContended-4 682.00 272.00 -60.12% BenchmarkChanContended-8 1601.00 520.00 -67.52% BenchmarkChanContended-16 3100.00 372.00 -88.00% BenchmarkChanSync 253.00 239.00 -5.53% BenchmarkChanSync-2 5030.00 4648.00 -7.59% BenchmarkChanSync-4 4826.00 4694.00 -2.74% BenchmarkChanSync-8 4778.00 4713.00 -1.36% BenchmarkChanSync-16 5289.00 4710.00 -10.95% BenchmarkChanProdCons0 273.00 254.00 -6.96% BenchmarkChanProdCons0-2 599.00 400.00 -33.22% BenchmarkChanProdCons0-4 1168.00 659.00 -43.58% BenchmarkChanProdCons0-8 2831.00 1057.00 -62.66% BenchmarkChanProdCons0-16 4197.00 1037.00 -75.29% BenchmarkChanProdCons10 150.00 140.00 -6.67% BenchmarkChanProdCons10-2 607.00 268.00 -55.85% BenchmarkChanProdCons10-4 1137.00 404.00 -64.47% BenchmarkChanProdCons10-8 2115.00 828.00 -60.85% BenchmarkChanProdCons10-16 4283.00 855.00 -80.04% BenchmarkChanProdCons100 117.00 110.00 -5.98% BenchmarkChanProdCons100-2 558.00 218.00 -60.93% BenchmarkChanProdCons100-4 722.00 287.00 -60.25% BenchmarkChanProdCons100-8 1840.00 431.00 -76.58% BenchmarkChanProdCons100-16 3394.00 448.00 -86.80% BenchmarkChanProdConsWork0 2014.00 1996.00 -0.89% BenchmarkChanProdConsWork0-2 1207.00 1127.00 -6.63% BenchmarkChanProdConsWork0-4 1913.00 611.00 -68.06% BenchmarkChanProdConsWork0-8 3016.00 949.00 -68.53% BenchmarkChanProdConsWork0-16 4320.00 1154.00 -73.29% BenchmarkChanProdConsWork10 1906.00 1897.00 -0.47% BenchmarkChanProdConsWork10-2 1123.00 1033.00 -8.01% BenchmarkChanProdConsWork10-4 1076.00 571.00 -46.93% BenchmarkChanProdConsWork10-8 2748.00 1096.00 -60.12% BenchmarkChanProdConsWork10-16 4600.00 1105.00 -75.98% BenchmarkChanProdConsWork100 1884.00 1852.00 -1.70% BenchmarkChanProdConsWork100-2 1235.00 1146.00 -7.21% BenchmarkChanProdConsWork100-4 1217.00 619.00 -49.14% BenchmarkChanProdConsWork100-8 1534.00 509.00 -66.82% BenchmarkChanProdConsWork100-16 4126.00 918.00 -77.75% BenchmarkSyscall 34.40 33.30 -3.20% BenchmarkSyscall-2 160.00 121.00 -24.38% BenchmarkSyscall-4 131.00 136.00 +3.82% BenchmarkSyscall-8 139.00 131.00 -5.76% BenchmarkSyscall-16 161.00 168.00 +4.35% BenchmarkSyscallWork 950.00 950.00 +0.00% BenchmarkSyscallWork-2 481.00 480.00 -0.21% BenchmarkSyscallWork-4 268.00 270.00 +0.75% BenchmarkSyscallWork-8 156.00 169.00 +8.33% BenchmarkSyscallWork-16 188.00 184.00 -2.13% BenchmarkSemaSyntNonblock 36.40 35.60 -2.20% BenchmarkSemaSyntNonblock-2 81.40 45.10 -44.59% BenchmarkSemaSyntNonblock-4 126.00 108.00 -14.29% BenchmarkSemaSyntNonblock-8 112.00 112.00 +0.00% BenchmarkSemaSyntNonblock-16 110.00 112.00 +1.82% BenchmarkSemaSyntBlock 35.30 35.30 +0.00% BenchmarkSemaSyntBlock-2 118.00 124.00 +5.08% BenchmarkSemaSyntBlock-4 105.00 108.00 +2.86% BenchmarkSemaSyntBlock-8 101.00 111.00 +9.90% BenchmarkSemaSyntBlock-16 112.00 118.00 +5.36% BenchmarkSemaWorkNonblock 810.00 811.00 +0.12% BenchmarkSemaWorkNonblock-2 476.00 414.00 -13.03% BenchmarkSemaWorkNonblock-4 238.00 228.00 -4.20% BenchmarkSemaWorkNonblock-8 140.00 126.00 -10.00% BenchmarkSemaWorkNonblock-16 117.00 116.00 -0.85% BenchmarkSemaWorkBlock 810.00 811.00 +0.12% BenchmarkSemaWorkBlock-2 454.00 466.00 +2.64% BenchmarkSemaWorkBlock-4 243.00 241.00 -0.82% BenchmarkSemaWorkBlock-8 145.00 137.00 -5.52% BenchmarkSemaWorkBlock-16 132.00 123.00 -6.82% BenchmarkContendedSemaphore 123.00 102.00 -17.07% BenchmarkContendedSemaphore-2 34.80 34.90 +0.29% BenchmarkContendedSemaphore-4 34.70 34.80 +0.29% BenchmarkContendedSemaphore-8 34.70 34.70 +0.00% BenchmarkContendedSemaphore-16 34.80 34.70 -0.29% BenchmarkMutex 26.80 26.00 -2.99% BenchmarkMutex-2 108.00 45.20 -58.15% BenchmarkMutex-4 103.00 127.00 +23.30% BenchmarkMutex-8 109.00 147.00 +34.86% BenchmarkMutex-16 102.00 152.00 +49.02% BenchmarkMutexSlack 27.00 26.90 -0.37% BenchmarkMutexSlack-2 149.00 165.00 +10.74% BenchmarkMutexSlack-4 121.00 209.00 +72.73% BenchmarkMutexSlack-8 101.00 158.00 +56.44% BenchmarkMutexSlack-16 97.00 129.00 +32.99% BenchmarkMutexWork 792.00 794.00 +0.25% BenchmarkMutexWork-2 407.00 409.00 +0.49% BenchmarkMutexWork-4 220.00 209.00 -5.00% BenchmarkMutexWork-8 267.00 160.00 -40.07% BenchmarkMutexWork-16 315.00 300.00 -4.76% BenchmarkMutexWorkSlack 792.00 793.00 +0.13% BenchmarkMutexWorkSlack-2 406.00 404.00 -0.49% BenchmarkMutexWorkSlack-4 225.00 212.00 -5.78% BenchmarkMutexWorkSlack-8 268.00 136.00 -49.25% BenchmarkMutexWorkSlack-16 300.00 300.00 +0.00% BenchmarkRWMutexWrite100 27.10 27.00 -0.37% BenchmarkRWMutexWrite100-2 33.10 40.80 +23.26% BenchmarkRWMutexWrite100-4 113.00 88.10 -22.04% BenchmarkRWMutexWrite100-8 119.00 95.30 -19.92% BenchmarkRWMutexWrite100-16 148.00 109.00 -26.35% BenchmarkRWMutexWrite10 29.60 29.40 -0.68% BenchmarkRWMutexWrite10-2 111.00 61.40 -44.68% BenchmarkRWMutexWrite10-4 270.00 208.00 -22.96% BenchmarkRWMutexWrite10-8 204.00 185.00 -9.31% BenchmarkRWMutexWrite10-16 261.00 190.00 -27.20% BenchmarkRWMutexWorkWrite100 1040.00 1036.00 -0.38% BenchmarkRWMutexWorkWrite100-2 593.00 580.00 -2.19% BenchmarkRWMutexWorkWrite100-4 470.00 365.00 -22.34% BenchmarkRWMutexWorkWrite100-8 468.00 289.00 -38.25% BenchmarkRWMutexWorkWrite100-16 604.00 374.00 -38.08% BenchmarkRWMutexWorkWrite10 951.00 951.00 +0.00% BenchmarkRWMutexWorkWrite10-2 1001.00 928.00 -7.29% BenchmarkRWMutexWorkWrite10-4 1555.00 1006.00 -35.31% BenchmarkRWMutexWorkWrite10-8 2085.00 1171.00 -43.84% BenchmarkRWMutexWorkWrite10-16 2082.00 1614.00 -22.48% R=rsc, iant, msolo, fw, iant CC=golang-dev https://golang.org/cl/4711045
2011-07-29 10:44:06 -06:00
again:
PAUSE
SUBL $1, AX
JNZ again
RET
TEXT runtime·atomicstorep(SB), NOSPLIT, $0-8
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL ptr+0(FP), BX
MOVL val+4(FP), AX
XCHGL AX, 0(BX)
RET
TEXT runtime·atomicstore(SB), NOSPLIT, $0-8
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL ptr+0(FP), BX
MOVL val+4(FP), AX
XCHGL AX, 0(BX)
RET
// uint64 atomicload64(uint64 volatile* addr);
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·atomicload64(SB), NOSPLIT, $0-12
MOVL ptr+0(FP), AX
LEAL ret_lo+4(FP), BX
// MOVQ (%EAX), %MM0
BYTE $0x0f; BYTE $0x6f; BYTE $0x00
// MOVQ %MM0, 0(%EBX)
BYTE $0x0f; BYTE $0x7f; BYTE $0x03
// EMMS
BYTE $0x0F; BYTE $0x77
RET
// void runtime·atomicstore64(uint64 volatile* addr, uint64 v);
TEXT runtime·atomicstore64(SB), NOSPLIT, $0-12
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL ptr+0(FP), AX
// MOVQ and EMMS were introduced on the Pentium MMX.
// MOVQ 0x8(%ESP), %MM0
BYTE $0x0f; BYTE $0x6f; BYTE $0x44; BYTE $0x24; BYTE $0x08
// MOVQ %MM0, (%EAX)
BYTE $0x0f; BYTE $0x7f; BYTE $0x00
// EMMS
BYTE $0x0F; BYTE $0x77
// This is essentially a no-op, but it provides required memory fencing.
// It can be replaced with MFENCE, but MFENCE was introduced only on the Pentium4 (SSE2).
MOVL $0, AX
LOCK
XADDL AX, (SP)
RET
// void runtime·atomicor8(byte volatile*, byte);
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·atomicor8(SB), NOSPLIT, $0-5
MOVL ptr+0(FP), AX
MOVB val+4(FP), BX
LOCK
ORB BX, (AX)
RET
// void jmpdefer(fn, sp);
// called from deferreturn.
// 1. pop the caller
// 2. sub 5 bytes from the callers return
// 3. jmp to the argument
TEXT runtime·jmpdefer(SB), NOSPLIT, $0-8
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL fv+0(FP), DX // fn
MOVL argp+4(FP), BX // caller sp
LEAL -4(BX), SP // caller sp after CALL
SUBL $5, (SP) // return to CALL again
MOVL 0(DX), BX
JMP BX // but first run the deferred function
// Save state of caller into g->sched.
TEXT gosave<>(SB),NOSPLIT,$0
PUSHL AX
PUSHL BX
get_tls(BX)
MOVL g(BX), BX
LEAL arg+0(FP), AX
MOVL AX, (g_sched+gobuf_sp)(BX)
MOVL -4(AX), AX
MOVL AX, (g_sched+gobuf_pc)(BX)
MOVL $0, (g_sched+gobuf_ret)(BX)
MOVL $0, (g_sched+gobuf_ctxt)(BX)
POPL BX
POPL AX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
RET
// asmcgocall(void(*fn)(void*), void *arg)
// Call fn(arg) on the scheduler stack,
// aligned appropriately for the gcc ABI.
// See cgocall.c for more details.
TEXT ·asmcgocall(SB),NOSPLIT,$0-8
MOVL fn+0(FP), AX
MOVL arg+4(FP), BX
CALL asmcgocall<>(SB)
RET
TEXT ·asmcgocall_errno(SB),NOSPLIT,$0-12
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL fn+0(FP), AX
MOVL arg+4(FP), BX
CALL asmcgocall<>(SB)
MOVL AX, ret+8(FP)
RET
TEXT asmcgocall<>(SB),NOSPLIT,$0-0
// fn in AX, arg in BX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL SP, DX
// Figure out if we need to switch to m->g0 stack.
// We get called to create new OS threads too, and those
// come in on the m->g0 stack already.
get_tls(CX)
2014-06-26 09:54:39 -06:00
MOVL g(CX), BP
MOVL g_m(BP), BP
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL m_g0(BP), SI
MOVL g(CX), DI
CMPL SI, DI
JEQ 4(PC)
CALL gosave<>(SB)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL SI, g(CX)
MOVL (g_sched+gobuf_sp)(SI), SP
// Now on a scheduling stack (a pthread-created stack).
SUBL $32, SP
ANDL $~15, SP // alignment, perhaps unnecessary
MOVL DI, 8(SP) // save g
MOVL (g_stack+stack_hi)(DI), DI
SUBL DX, DI
MOVL DI, 4(SP) // save depth in stack (can't just save SP, as stack might be copied during a callback)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL BX, 0(SP) // first argument in x86-32 ABI
CALL AX
// Restore registers, g, stack pointer.
get_tls(CX)
MOVL 8(SP), DI
MOVL (g_stack+stack_hi)(DI), SI
SUBL 4(SP), SI
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL DI, g(CX)
MOVL SI, SP
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
RET
// cgocallback(void (*fn)(void*), void *frame, uintptr framesize)
// Turn the fn into a Go func (by taking its address) and call
// cgocallback_gofunc.
TEXT runtime·cgocallback(SB),NOSPLIT,$12-12
LEAL fn+0(FP), AX
MOVL AX, 0(SP)
MOVL frame+4(FP), AX
MOVL AX, 4(SP)
MOVL framesize+8(FP), AX
MOVL AX, 8(SP)
MOVL $runtime·cgocallback_gofunc(SB), AX
CALL AX
RET
// cgocallback_gofunc(FuncVal*, void *frame, uintptr framesize)
// See cgocall.c for more details.
TEXT ·cgocallback_gofunc(SB),NOSPLIT,$12-12
NO_LOCAL_POINTERS
2014-06-26 09:54:39 -06:00
// If g is nil, Go did not create the current thread.
// Call needm to obtain one for temporary use.
// In this case, we're running on the thread stack, so there's
// lots of space, but the linker doesn't know. Hide the call from
// the linker analysis by using an indirect call through AX.
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
get_tls(CX)
#ifdef GOOS_windows
MOVL $0, BP
CMPL CX, $0
2014-06-26 09:54:39 -06:00
JEQ 2(PC) // TODO
#endif
2014-06-26 09:54:39 -06:00
MOVL g(CX), BP
CMPL BP, $0
2014-06-26 09:54:39 -06:00
JEQ needm
MOVL g_m(BP), BP
MOVL BP, DX // saved copy of oldm
JMP havem
needm:
2014-06-26 09:54:39 -06:00
MOVL $0, 0(SP)
MOVL $runtime·needm(SB), AX
CALL AX
MOVL 0(SP), DX
get_tls(CX)
2014-06-26 09:54:39 -06:00
MOVL g(CX), BP
MOVL g_m(BP), BP
// Set m->sched.sp = SP, so that if a panic happens
// during the function we are about to execute, it will
// have a valid SP to run on the g0 stack.
// The next few lines (after the havem label)
// will save this SP onto the stack and then write
// the same SP back to m->sched.sp. That seems redundant,
// but if an unrecovered panic happens, unwindm will
// restore the g->sched.sp from the stack location
// and then onM will try to use it. If we don't set it here,
// that restored SP will be uninitialized (typically 0) and
// will not be usable.
MOVL m_g0(BP), SI
MOVL SP, (g_sched+gobuf_sp)(SI)
havem:
// Now there's a valid m, and we're running on its m->g0.
// Save current m->g0->sched.sp on stack and then set it to SP.
// Save current sp in m->g0->sched.sp in preparation for
// switch back to m->curg stack.
// NOTE: unwindm knows that the saved g->sched.sp is at 0(SP).
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL m_g0(BP), SI
MOVL (g_sched+gobuf_sp)(SI), AX
MOVL AX, 0(SP)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL SP, (g_sched+gobuf_sp)(SI)
// Switch to m->curg stack and call runtime.cgocallbackg.
// Because we are taking over the execution of m->curg
// but *not* resuming what had been running, we need to
// save that information (m->curg->sched) so we can restore it.
// We can restore m->curg->sched.sp easily, because calling
// runtime.cgocallbackg leaves SP unchanged upon return.
// To save m->curg->sched.pc, we push it onto the stack.
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// This has the added benefit that it looks to the traceback
// routine like cgocallbackg is going to return to that
// PC (because the frame we allocate below has the same
// size as cgocallback_gofunc's frame declared above)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// so that the traceback will seamlessly trace back into
// the earlier calls.
//
// In the new goroutine, 0(SP) holds the saved oldm (DX) register.
// 4(SP) and 8(SP) are unused.
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL m_curg(BP), SI
MOVL SI, g(CX)
MOVL (g_sched+gobuf_sp)(SI), DI // prepare stack as DI
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL (g_sched+gobuf_pc)(SI), BP
MOVL BP, -4(DI)
LEAL -(4+12)(DI), SP
MOVL DX, 0(SP)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
CALL runtime·cgocallbackg(SB)
MOVL 0(SP), DX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// Restore g->sched (== m->curg->sched) from saved values.
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
get_tls(CX)
MOVL g(CX), SI
MOVL 12(SP), BP
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL BP, (g_sched+gobuf_pc)(SI)
LEAL (12+4)(SP), DI
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL DI, (g_sched+gobuf_sp)(SI)
// Switch back to m->g0's stack and restore m->g0->sched.sp.
// (Unlike m->curg, the g0 goroutine never uses sched.pc,
// so we do not have to restore it.)
2014-06-26 09:54:39 -06:00
MOVL g(CX), BP
MOVL g_m(BP), BP
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
MOVL m_g0(BP), SI
MOVL SI, g(CX)
MOVL (g_sched+gobuf_sp)(SI), SP
MOVL 0(SP), AX
MOVL AX, (g_sched+gobuf_sp)(SI)
// If the m on entry was nil, we called needm above to borrow an m
// for the duration of the call. Since the call is over, return it with dropm.
CMPL DX, $0
JNE 3(PC)
MOVL $runtime·dropm(SB), AX
CALL AX
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
// Done!
RET
2014-06-26 09:54:39 -06:00
// void setg(G*); set g. for use by needm.
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·setg(SB), NOSPLIT, $0-4
2014-06-26 09:54:39 -06:00
MOVL gg+0(FP), BX
#ifdef GOOS_windows
2014-06-26 09:54:39 -06:00
CMPL BX, $0
JNE settls
MOVL $0, 0x14(FS)
RET
settls:
2014-06-26 09:54:39 -06:00
MOVL g_m(BX), AX
LEAL m_tls(AX), AX
MOVL AX, 0x14(FS)
#endif
get_tls(CX)
MOVL BX, g(CX)
RET
2014-06-26 09:54:39 -06:00
// void setg_gcc(G*); set g. for use by gcc
TEXT setg_gcc<>(SB), NOSPLIT, $0
get_tls(AX)
2014-06-26 09:54:39 -06:00
MOVL gg+0(FP), DX
MOVL DX, g(AX)
RET
// check that SP is in range [g->stack.lo, g->stack.hi)
TEXT runtime·stackcheck(SB), NOSPLIT, $0-0
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
get_tls(CX)
MOVL g(CX), AX
CMPL (g_stack+stack_hi)(AX), SP
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
JHI 2(PC)
INT $3
CMPL SP, (g_stack+stack_lo)(AX)
runtime: scheduler, cgo reorganization * Change use of m->g0 stack (aka scheduler stack). * Provide runtime.mcall(f) to invoke f() on m->g0 stack. * Replace scheduler loop entry with runtime.mcall(schedule). Runtime.mcall eliminates the need for fake scheduler states that exist just to run a bit of code on the m->g0 stack (Grecovery, Gstackalloc). The elimination of the scheduler as a loop that stops and starts using gosave and gogo fixes a bad interaction with the way cgo uses the m->g0 stack. Cgo runs external (gcc-compiled) C functions on that stack, and then when calling back into Go, it sets m->g0->sched.sp below the added call frames, so that other uses of m->g0's stack will not interfere with those frames. Unfortunately, gogo (longjmp) back to the scheduler loop at this point would end up running scheduler with the lower sp, which no longer points at a valid stack frame for a call to scheduler. If scheduler then wrote any function call arguments or local variables to where it expected the stack frame to be, it would overwrite other data on the stack. I realized this possibility while debugging a problem with calling complex Go code in a Go -> C -> Go cgo callback. This wasn't the bug I was looking for, it turns out, but I believe it is a real bug nonetheless. Switching to runtime.mcall, which only adds new frames to the stack and never jumps into functions running in existing ones, fixes this bug. * Move cgo-related code out of proc.c into cgocall.c. * Add very large comment describing cgo call sequences. * Simpilify, regularize cgo function implementations and names. * Add test suite as misc/cgo/test. Now the Go -> C path calls cgocall, which calls asmcgocall, and the C -> Go path calls cgocallback, which calls cgocallbackg. The shuffling, which affects mainly the callback case, moves most of the callback implementation to cgocallback running on the m->curg stack (not the m->g0 scheduler stack) and only while accounted for with $GOMAXPROCS (between calls to exitsyscall and entersyscall). The previous callback code did not block in startcgocallback's approximation to exitsyscall, so if, say, the garbage collector were running, it would still barge in and start doing things like call malloc. Similarly endcgocallback's approximation of entersyscall did not call matchmg to kick off new OS threads when necessary, which caused the bug in issue 1560. Fixes #1560. R=iant CC=golang-dev https://golang.org/cl/4253054
2011-03-07 08:37:42 -07:00
JHI 2(PC)
INT $3
RET
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·getcallerpc(SB),NOSPLIT,$0-8
MOVL argp+0(FP),AX // addr of first arg
MOVL -4(AX),AX // get calling pc
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret+4(FP)
RET
TEXT runtime·gogetcallerpc(SB),NOSPLIT,$0-8
MOVL p+0(FP),AX // addr of first arg
MOVL -4(AX),AX // get calling pc
MOVL AX, ret+4(FP)
RET
TEXT runtime·setcallerpc(SB),NOSPLIT,$0-8
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL argp+0(FP),AX // addr of first arg
MOVL pc+4(FP), BX
MOVL BX, -4(AX) // set calling pc
RET
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·getcallersp(SB), NOSPLIT, $0-8
MOVL argp+0(FP), AX
MOVL AX, ret+4(FP)
RET
// func gogetcallersp(p unsafe.Pointer) uintptr
TEXT runtime·gogetcallersp(SB),NOSPLIT,$0-8
MOVL p+0(FP),AX // addr of first arg
MOVL AX, ret+4(FP)
RET
// int64 runtime·cputicks(void), so really
// void runtime·cputicks(int64 *ticks)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
TEXT runtime·cputicks(SB),NOSPLIT,$0-8
RDTSC
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret_lo+0(FP)
MOVL DX, ret_hi+4(FP)
RET
TEXT runtime·ldt0setup(SB),NOSPLIT,$16-0
// set up ldt 7 to point at tls0
// ldt 1 would be fine on Linux, but on OS X, 7 is as low as we can go.
// the entry number is just a hint. setldt will set up GS with what it used.
MOVL $7, 0(SP)
LEAL runtime·tls0(SB), AX
MOVL AX, 4(SP)
MOVL $32, 8(SP) // sizeof(tls array)
CALL runtime·setldt(SB)
RET
TEXT runtime·emptyfunc(SB),0,$0-0
RET
TEXT runtime·abort(SB),NOSPLIT,$0-0
INT $0x3
// hash function using AES hardware instructions
TEXT runtime·aeshash(SB),NOSPLIT,$0-16
MOVL p+0(FP), AX // ptr to data
MOVL s+4(FP), CX // size
JMP runtime·aeshashbody(SB)
TEXT runtime·aeshashstr(SB),NOSPLIT,$0-16
MOVL p+0(FP), AX // ptr to string object
// s+4(FP) is ignored, it is always sizeof(String)
MOVL 4(AX), CX // length of string
MOVL (AX), AX // string data
JMP runtime·aeshashbody(SB)
// AX: data
// CX: length
TEXT runtime·aeshashbody(SB),NOSPLIT,$0-16
MOVL h+8(FP), X0 // seed to low 32 bits of xmm0
PINSRD $1, CX, X0 // size to next 32 bits of xmm0
MOVO runtime·aeskeysched+0(SB), X2
MOVO runtime·aeskeysched+16(SB), X3
CMPL CX, $16
JB aessmall
aesloop:
CMPL CX, $16
JBE aesloopend
MOVOU (AX), X1
AESENC X2, X0
AESENC X1, X0
SUBL $16, CX
ADDL $16, AX
JMP aesloop
// 1-16 bytes remaining
aesloopend:
// This load may overlap with the previous load above.
// We'll hash some bytes twice, but that's ok.
MOVOU -16(AX)(CX*1), X1
JMP partial
// 0-15 bytes
aessmall:
TESTL CX, CX
JE finalize // 0 bytes
CMPB AX, $0xf0
JA highpartial
// 16 bytes loaded at this address won't cross
// a page boundary, so we can load it directly.
MOVOU (AX), X1
ADDL CX, CX
PAND masks<>(SB)(CX*8), X1
JMP partial
highpartial:
// address ends in 1111xxxx. Might be up against
// a page boundary, so load ending at last byte.
// Then shift bytes down using pshufb.
MOVOU -16(AX)(CX*1), X1
ADDL CX, CX
PSHUFB shifts<>(SB)(CX*8), X1
partial:
// incorporate partial block into hash
AESENC X3, X0
AESENC X1, X0
finalize:
// finalize hash
AESENC X2, X0
AESENC X3, X0
AESENC X2, X0
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL X0, ret+12(FP)
RET
TEXT runtime·aeshash32(SB),NOSPLIT,$0-16
MOVL p+0(FP), AX // ptr to data
// s+4(FP) is ignored, it is always sizeof(int32)
MOVL h+8(FP), X0 // seed
PINSRD $1, (AX), X0 // data
AESENC runtime·aeskeysched+0(SB), X0
AESENC runtime·aeskeysched+16(SB), X0
AESENC runtime·aeskeysched+0(SB), X0
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL X0, ret+12(FP)
RET
TEXT runtime·aeshash64(SB),NOSPLIT,$0-16
MOVL p+0(FP), AX // ptr to data
// s+4(FP) is ignored, it is always sizeof(int64)
MOVQ (AX), X0 // data
PINSRD $2, h+8(FP), X0 // seed
AESENC runtime·aeskeysched+0(SB), X0
AESENC runtime·aeskeysched+16(SB), X0
AESENC runtime·aeskeysched+0(SB), X0
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL X0, ret+12(FP)
RET
// simple mask to get rid of data in the high part of the register.
DATA masks<>+0x00(SB)/4, $0x00000000
DATA masks<>+0x04(SB)/4, $0x00000000
DATA masks<>+0x08(SB)/4, $0x00000000
DATA masks<>+0x0c(SB)/4, $0x00000000
DATA masks<>+0x10(SB)/4, $0x000000ff
DATA masks<>+0x14(SB)/4, $0x00000000
DATA masks<>+0x18(SB)/4, $0x00000000
DATA masks<>+0x1c(SB)/4, $0x00000000
DATA masks<>+0x20(SB)/4, $0x0000ffff
DATA masks<>+0x24(SB)/4, $0x00000000
DATA masks<>+0x28(SB)/4, $0x00000000
DATA masks<>+0x2c(SB)/4, $0x00000000
DATA masks<>+0x30(SB)/4, $0x00ffffff
DATA masks<>+0x34(SB)/4, $0x00000000
DATA masks<>+0x38(SB)/4, $0x00000000
DATA masks<>+0x3c(SB)/4, $0x00000000
DATA masks<>+0x40(SB)/4, $0xffffffff
DATA masks<>+0x44(SB)/4, $0x00000000
DATA masks<>+0x48(SB)/4, $0x00000000
DATA masks<>+0x4c(SB)/4, $0x00000000
DATA masks<>+0x50(SB)/4, $0xffffffff
DATA masks<>+0x54(SB)/4, $0x000000ff
DATA masks<>+0x58(SB)/4, $0x00000000
DATA masks<>+0x5c(SB)/4, $0x00000000
DATA masks<>+0x60(SB)/4, $0xffffffff
DATA masks<>+0x64(SB)/4, $0x0000ffff
DATA masks<>+0x68(SB)/4, $0x00000000
DATA masks<>+0x6c(SB)/4, $0x00000000
DATA masks<>+0x70(SB)/4, $0xffffffff
DATA masks<>+0x74(SB)/4, $0x00ffffff
DATA masks<>+0x78(SB)/4, $0x00000000
DATA masks<>+0x7c(SB)/4, $0x00000000
DATA masks<>+0x80(SB)/4, $0xffffffff
DATA masks<>+0x84(SB)/4, $0xffffffff
DATA masks<>+0x88(SB)/4, $0x00000000
DATA masks<>+0x8c(SB)/4, $0x00000000
DATA masks<>+0x90(SB)/4, $0xffffffff
DATA masks<>+0x94(SB)/4, $0xffffffff
DATA masks<>+0x98(SB)/4, $0x000000ff
DATA masks<>+0x9c(SB)/4, $0x00000000
DATA masks<>+0xa0(SB)/4, $0xffffffff
DATA masks<>+0xa4(SB)/4, $0xffffffff
DATA masks<>+0xa8(SB)/4, $0x0000ffff
DATA masks<>+0xac(SB)/4, $0x00000000
DATA masks<>+0xb0(SB)/4, $0xffffffff
DATA masks<>+0xb4(SB)/4, $0xffffffff
DATA masks<>+0xb8(SB)/4, $0x00ffffff
DATA masks<>+0xbc(SB)/4, $0x00000000
DATA masks<>+0xc0(SB)/4, $0xffffffff
DATA masks<>+0xc4(SB)/4, $0xffffffff
DATA masks<>+0xc8(SB)/4, $0xffffffff
DATA masks<>+0xcc(SB)/4, $0x00000000
DATA masks<>+0xd0(SB)/4, $0xffffffff
DATA masks<>+0xd4(SB)/4, $0xffffffff
DATA masks<>+0xd8(SB)/4, $0xffffffff
DATA masks<>+0xdc(SB)/4, $0x000000ff
DATA masks<>+0xe0(SB)/4, $0xffffffff
DATA masks<>+0xe4(SB)/4, $0xffffffff
DATA masks<>+0xe8(SB)/4, $0xffffffff
DATA masks<>+0xec(SB)/4, $0x0000ffff
DATA masks<>+0xf0(SB)/4, $0xffffffff
DATA masks<>+0xf4(SB)/4, $0xffffffff
DATA masks<>+0xf8(SB)/4, $0xffffffff
DATA masks<>+0xfc(SB)/4, $0x00ffffff
GLOBL masks<>(SB),RODATA,$256
// these are arguments to pshufb. They move data down from
// the high bytes of the register to the low bytes of the register.
// index is how many bytes to move.
DATA shifts<>+0x00(SB)/4, $0x00000000
DATA shifts<>+0x04(SB)/4, $0x00000000
DATA shifts<>+0x08(SB)/4, $0x00000000
DATA shifts<>+0x0c(SB)/4, $0x00000000
DATA shifts<>+0x10(SB)/4, $0xffffff0f
DATA shifts<>+0x14(SB)/4, $0xffffffff
DATA shifts<>+0x18(SB)/4, $0xffffffff
DATA shifts<>+0x1c(SB)/4, $0xffffffff
DATA shifts<>+0x20(SB)/4, $0xffff0f0e
DATA shifts<>+0x24(SB)/4, $0xffffffff
DATA shifts<>+0x28(SB)/4, $0xffffffff
DATA shifts<>+0x2c(SB)/4, $0xffffffff
DATA shifts<>+0x30(SB)/4, $0xff0f0e0d
DATA shifts<>+0x34(SB)/4, $0xffffffff
DATA shifts<>+0x38(SB)/4, $0xffffffff
DATA shifts<>+0x3c(SB)/4, $0xffffffff
DATA shifts<>+0x40(SB)/4, $0x0f0e0d0c
DATA shifts<>+0x44(SB)/4, $0xffffffff
DATA shifts<>+0x48(SB)/4, $0xffffffff
DATA shifts<>+0x4c(SB)/4, $0xffffffff
DATA shifts<>+0x50(SB)/4, $0x0e0d0c0b
DATA shifts<>+0x54(SB)/4, $0xffffff0f
DATA shifts<>+0x58(SB)/4, $0xffffffff
DATA shifts<>+0x5c(SB)/4, $0xffffffff
DATA shifts<>+0x60(SB)/4, $0x0d0c0b0a
DATA shifts<>+0x64(SB)/4, $0xffff0f0e
DATA shifts<>+0x68(SB)/4, $0xffffffff
DATA shifts<>+0x6c(SB)/4, $0xffffffff
DATA shifts<>+0x70(SB)/4, $0x0c0b0a09
DATA shifts<>+0x74(SB)/4, $0xff0f0e0d
DATA shifts<>+0x78(SB)/4, $0xffffffff
DATA shifts<>+0x7c(SB)/4, $0xffffffff
DATA shifts<>+0x80(SB)/4, $0x0b0a0908
DATA shifts<>+0x84(SB)/4, $0x0f0e0d0c
DATA shifts<>+0x88(SB)/4, $0xffffffff
DATA shifts<>+0x8c(SB)/4, $0xffffffff
DATA shifts<>+0x90(SB)/4, $0x0a090807
DATA shifts<>+0x94(SB)/4, $0x0e0d0c0b
DATA shifts<>+0x98(SB)/4, $0xffffff0f
DATA shifts<>+0x9c(SB)/4, $0xffffffff
DATA shifts<>+0xa0(SB)/4, $0x09080706
DATA shifts<>+0xa4(SB)/4, $0x0d0c0b0a
DATA shifts<>+0xa8(SB)/4, $0xffff0f0e
DATA shifts<>+0xac(SB)/4, $0xffffffff
DATA shifts<>+0xb0(SB)/4, $0x08070605
DATA shifts<>+0xb4(SB)/4, $0x0c0b0a09
DATA shifts<>+0xb8(SB)/4, $0xff0f0e0d
DATA shifts<>+0xbc(SB)/4, $0xffffffff
DATA shifts<>+0xc0(SB)/4, $0x07060504
DATA shifts<>+0xc4(SB)/4, $0x0b0a0908
DATA shifts<>+0xc8(SB)/4, $0x0f0e0d0c
DATA shifts<>+0xcc(SB)/4, $0xffffffff
DATA shifts<>+0xd0(SB)/4, $0x06050403
DATA shifts<>+0xd4(SB)/4, $0x0a090807
DATA shifts<>+0xd8(SB)/4, $0x0e0d0c0b
DATA shifts<>+0xdc(SB)/4, $0xffffff0f
DATA shifts<>+0xe0(SB)/4, $0x05040302
DATA shifts<>+0xe4(SB)/4, $0x09080706
DATA shifts<>+0xe8(SB)/4, $0x0d0c0b0a
DATA shifts<>+0xec(SB)/4, $0xffff0f0e
DATA shifts<>+0xf0(SB)/4, $0x04030201
DATA shifts<>+0xf4(SB)/4, $0x08070605
DATA shifts<>+0xf8(SB)/4, $0x0c0b0a09
DATA shifts<>+0xfc(SB)/4, $0xff0f0e0d
GLOBL shifts<>(SB),RODATA,$256
TEXT runtime·memeq(SB),NOSPLIT,$0-13
MOVL a+0(FP), SI
MOVL b+4(FP), DI
MOVL size+8(FP), BX
CALL runtime·memeqbody(SB)
MOVB AX, ret+12(FP)
RET
// eqstring tests whether two strings are equal.
// See runtime_test.go:eqstring_generic for
// equivalent Go code.
TEXT runtime·eqstring(SB),NOSPLIT,$0-17
MOVL s1len+4(FP), AX
MOVL s2len+12(FP), BX
CMPL AX, BX
JNE different
MOVL s1str+0(FP), SI
MOVL s2str+8(FP), DI
CMPL SI, DI
JEQ same
CALL runtime·memeqbody(SB)
MOVB AX, v+16(FP)
RET
same:
MOVB $1, v+16(FP)
RET
different:
MOVB $0, v+16(FP)
RET
TEXT bytes·Equal(SB),NOSPLIT,$0-25
MOVL a_len+4(FP), BX
MOVL b_len+16(FP), CX
XORL AX, AX
CMPL BX, CX
JNE eqret
MOVL a+0(FP), SI
MOVL b+12(FP), DI
CALL runtime·memeqbody(SB)
eqret:
MOVB AX, ret+24(FP)
RET
// a in SI
// b in DI
// count in BX
TEXT runtime·memeqbody(SB),NOSPLIT,$0-0
XORL AX, AX
CMPL BX, $4
JB small
// 64 bytes at a time using xmm registers
hugeloop:
CMPL BX, $64
JB bigloop
TESTL $0x4000000, runtime·cpuid_edx(SB) // check for sse2
JE bigloop
MOVOU (SI), X0
MOVOU (DI), X1
MOVOU 16(SI), X2
MOVOU 16(DI), X3
MOVOU 32(SI), X4
MOVOU 32(DI), X5
MOVOU 48(SI), X6
MOVOU 48(DI), X7
PCMPEQB X1, X0
PCMPEQB X3, X2
PCMPEQB X5, X4
PCMPEQB X7, X6
PAND X2, X0
PAND X6, X4
PAND X4, X0
PMOVMSKB X0, DX
ADDL $64, SI
ADDL $64, DI
SUBL $64, BX
CMPL DX, $0xffff
JEQ hugeloop
RET
// 4 bytes at a time using 32-bit register
bigloop:
CMPL BX, $4
JBE leftover
MOVL (SI), CX
MOVL (DI), DX
ADDL $4, SI
ADDL $4, DI
SUBL $4, BX
CMPL CX, DX
JEQ bigloop
RET
// remaining 0-4 bytes
leftover:
MOVL -4(SI)(BX*1), CX
MOVL -4(DI)(BX*1), DX
CMPL CX, DX
SETEQ AX
RET
small:
CMPL BX, $0
JEQ equal
LEAL 0(BX*8), CX
NEGL CX
MOVL SI, DX
CMPB DX, $0xfc
JA si_high
// load at SI won't cross a page boundary.
MOVL (SI), SI
JMP si_finish
si_high:
// address ends in 111111xx. Load up to bytes we want, move to correct position.
MOVL -4(SI)(BX*1), SI
SHRL CX, SI
si_finish:
// same for DI.
MOVL DI, DX
CMPB DX, $0xfc
JA di_high
MOVL (DI), DI
JMP di_finish
di_high:
MOVL -4(DI)(BX*1), DI
SHRL CX, DI
di_finish:
SUBL SI, DI
SHLL CX, DI
equal:
SETEQ AX
RET
TEXT runtime·cmpstring(SB),NOSPLIT,$0-20
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL s1_base+0(FP), SI
MOVL s1_len+4(FP), BX
MOVL s2_base+8(FP), DI
MOVL s2_len+12(FP), DX
CALL runtime·cmpbody(SB)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret+16(FP)
RET
TEXT runtime·cmpbytes(SB),NOSPLIT,$0-28
MOVL s1+0(FP), SI
MOVL s1+4(FP), BX
MOVL s2+12(FP), DI
MOVL s2+16(FP), DX
CALL runtime·cmpbody(SB)
cmd/cc, runtime: convert C compilers to use Go calling convention To date, the C compilers and Go compilers differed only in how values were returned from functions. This made it difficult to call Go from C or C from Go if return values were involved. It also made assembly called from Go and assembly called from C different. This CL changes the C compiler to use the Go conventions, passing results on the stack, after the arguments. [Exception: this does not apply to C ... functions, because you can't know where on the stack the arguments end.] By doing this, the CL makes it possible to rewrite C functions into Go one at a time, without worrying about which languages call that function or which languages it calls. This CL also updates all the assembly files in package runtime to use the new conventions. Argument references of the form 40(SP) have been rewritten to the form name+10(FP) instead, and there are now Go func prototypes for every assembly function called from C or Go. This means that 'go vet runtime' checks effectively every assembly function, and go vet's output was used to automate the bulk of the conversion. Some functions, like seek and nsec on Plan 9, needed to be rewritten. Many assembly routines called from C were reading arguments incorrectly, using MOVL instead of MOVQ or vice versa, especially on the less used systems like openbsd. These were found by go vet and have been corrected too. If we're lucky, this may reduce flakiness on those systems. Tested on: darwin/386 darwin/amd64 linux/arm linux/386 linux/amd64 If this breaks another system, the bug is almost certainly in the sys_$GOOS_$GOARCH.s file, since the rest of the CL is tested by the combination of the above systems. LGTM=dvyukov, iant R=golang-codereviews, 0intro, dave, alex.brainman, dvyukov, iant CC=golang-codereviews, josharian, r https://golang.org/cl/135830043
2014-08-27 09:32:17 -06:00
MOVL AX, ret+24(FP)
RET
TEXT bytes·IndexByte(SB),NOSPLIT,$0
MOVL s+0(FP), SI
MOVL s_len+4(FP), CX
MOVB c+12(FP), AL
MOVL SI, DI
CLD; REPN; SCASB
JZ 3(PC)
MOVL $-1, ret+16(FP)
RET
SUBL SI, DI
SUBL $1, DI
MOVL DI, ret+16(FP)
RET
TEXT strings·IndexByte(SB),NOSPLIT,$0
MOVL s+0(FP), SI
MOVL s_len+4(FP), CX
MOVB c+8(FP), AL
MOVL SI, DI
CLD; REPN; SCASB
JZ 3(PC)
MOVL $-1, ret+12(FP)
RET
SUBL SI, DI
SUBL $1, DI
MOVL DI, ret+12(FP)
RET
// input:
// SI = a
// DI = b
// BX = alen
// DX = blen
// output:
// AX = 1/0/-1
TEXT runtime·cmpbody(SB),NOSPLIT,$0-0
CMPL SI, DI
JEQ cmp_allsame
CMPL BX, DX
MOVL DX, BP
CMOVLLT BX, BP // BP = min(alen, blen)
CMPL BP, $4
JB cmp_small
TESTL $0x4000000, runtime·cpuid_edx(SB) // check for sse2
JE cmp_mediumloop
cmp_largeloop:
CMPL BP, $16
JB cmp_mediumloop
MOVOU (SI), X0
MOVOU (DI), X1
PCMPEQB X0, X1
PMOVMSKB X1, AX
XORL $0xffff, AX // convert EQ to NE
JNE cmp_diff16 // branch if at least one byte is not equal
ADDL $16, SI
ADDL $16, DI
SUBL $16, BP
JMP cmp_largeloop
cmp_diff16:
BSFL AX, BX // index of first byte that differs
XORL AX, AX
MOVB (SI)(BX*1), CX
CMPB CX, (DI)(BX*1)
SETHI AX
LEAL -1(AX*2), AX // convert 1/0 to +1/-1
RET
cmp_mediumloop:
CMPL BP, $4
JBE cmp_0through4
MOVL (SI), AX
MOVL (DI), CX
CMPL AX, CX
JNE cmp_diff4
ADDL $4, SI
ADDL $4, DI
SUBL $4, BP
JMP cmp_mediumloop
cmp_0through4:
MOVL -4(SI)(BP*1), AX
MOVL -4(DI)(BP*1), CX
CMPL AX, CX
JEQ cmp_allsame
cmp_diff4:
BSWAPL AX // reverse order of bytes
BSWAPL CX
XORL AX, CX // find bit differences
BSRL CX, CX // index of highest bit difference
SHRL CX, AX // move a's bit to bottom
ANDL $1, AX // mask bit
LEAL -1(AX*2), AX // 1/0 => +1/-1
RET
// 0-3 bytes in common
cmp_small:
LEAL (BP*8), CX
NEGL CX
JEQ cmp_allsame
// load si
CMPB SI, $0xfc
JA cmp_si_high
MOVL (SI), SI
JMP cmp_si_finish
cmp_si_high:
MOVL -4(SI)(BP*1), SI
SHRL CX, SI
cmp_si_finish:
SHLL CX, SI
// same for di
CMPB DI, $0xfc
JA cmp_di_high
MOVL (DI), DI
JMP cmp_di_finish
cmp_di_high:
MOVL -4(DI)(BP*1), DI
SHRL CX, DI
cmp_di_finish:
SHLL CX, DI
BSWAPL SI // reverse order of bytes
BSWAPL DI
XORL SI, DI // find bit differences
JEQ cmp_allsame
BSRL DI, CX // index of highest bit difference
SHRL CX, SI // move a's bit to bottom
ANDL $1, SI // mask bit
LEAL -1(SI*2), AX // 1/0 => +1/-1
RET
// all the bytes in common are the same, so we just need
// to compare the lengths.
cmp_allsame:
XORL AX, AX
XORL CX, CX
CMPL BX, DX
SETGT AX // 1 if alen > blen
SETEQ CX // 1 if alen == blen
LEAL -1(CX)(AX*2), AX // 1,0,-1 result
RET
// A Duff's device for zeroing memory.
// The compiler jumps to computed addresses within
// this routine to zero chunks of memory. Do not
// change this code without also changing the code
// in ../../cmd/8g/ggen.c:clearfat.
// AX: zero
// DI: ptr to memory to be zeroed
// DI is updated as a side effect.
TEXT runtime·duffzero(SB), NOSPLIT, $0-0
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
STOSL
RET
// A Duff's device for copying memory.
// The compiler jumps to computed addresses within
// this routine to copy chunks of memory. Source
// and destination must not overlap. Do not
// change this code without also changing the code
// in ../../cmd/6g/cgen.c:sgen.
// SI: ptr to source memory
// DI: ptr to destination memory
// SI and DI are updated as a side effect.
// NOTE: this is equivalent to a sequence of MOVSL but
// for some reason MOVSL is really slow.
TEXT runtime·duffcopy(SB), NOSPLIT, $0-0
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
MOVL (SI),CX
ADDL $4,SI
MOVL CX,(DI)
ADDL $4,DI
RET
TEXT runtime·fastrand1(SB), NOSPLIT, $0-4
get_tls(CX)
MOVL g(CX), AX
MOVL g_m(AX), AX
MOVL m_fastrand(AX), DX
ADDL DX, DX
MOVL DX, BX
XORL $0x88888eef, DX
CMOVLMI BX, DX
MOVL DX, m_fastrand(AX)
MOVL DX, ret+0(FP)
RET
TEXT runtime·return0(SB), NOSPLIT, $0
MOVL $0, AX
RET
// Called from cgo wrappers, this function returns g->m->curg.stack.hi.
// Must obey the gcc calling convention.
TEXT _cgo_topofstack(SB),NOSPLIT,$0
get_tls(CX)
MOVL g(CX), AX
MOVL g_m(AX), AX
MOVL m_curg(AX), AX
MOVL (g_stack+stack_hi)(AX), AX
RET