diff options
Diffstat (limited to 'src/runtime')
| -rw-r--r-- | src/runtime/cgocall.go | 22 | ||||
| -rw-r--r-- | src/runtime/iface.go | 10 | ||||
| -rw-r--r-- | src/runtime/os_windows.go | 8 | ||||
| -rw-r--r-- | src/runtime/sys_darwin.go | 8 | ||||
| -rw-r--r-- | src/runtime/testdata/testprogcgo/numgoroutine.go | 7 |
5 files changed, 26 insertions, 29 deletions
diff --git a/src/runtime/cgocall.go b/src/runtime/cgocall.go index a881ae1489..5f8ff8139a 100644 --- a/src/runtime/cgocall.go +++ b/src/runtime/cgocall.go @@ -406,24 +406,24 @@ var racecgosync uint64 // represents possible synchronization in C code // cgoCheckPointer checks if the argument contains a Go pointer that // points to a Go pointer, and panics if it does. -func cgoCheckPointer(ptr interface{}, args ...interface{}) { +func cgoCheckPointer(ptr interface{}, arg interface{}) { if debug.cgocheck == 0 { return } - ep := (*eface)(unsafe.Pointer(&ptr)) + ep := efaceOf(&ptr) t := ep._type top := true - if len(args) > 0 && (t.kind&kindMask == kindPtr || t.kind&kindMask == kindUnsafePointer) { + if arg != nil && (t.kind&kindMask == kindPtr || t.kind&kindMask == kindUnsafePointer) { p := ep.data if t.kind&kindDirectIface == 0 { p = *(*unsafe.Pointer)(p) } - if !cgoIsGoPointer(p) { + if p == nil || !cgoIsGoPointer(p) { return } - aep := (*eface)(unsafe.Pointer(&args[0])) + aep := efaceOf(&arg) switch aep._type.kind & kindMask { case kindBool: if t.kind&kindMask == kindUnsafePointer { @@ -460,7 +460,7 @@ const cgoResultFail = "cgo result has Go pointer" // depending on indir. The top parameter is whether we are at the top // level, where Go pointers are allowed. func cgoCheckArg(t *_type, p unsafe.Pointer, indir, top bool, msg string) { - if t.ptrdata == 0 { + if t.ptrdata == 0 || p == nil { // If the type has no pointers there is nothing to do. return } @@ -517,7 +517,7 @@ func cgoCheckArg(t *_type, p unsafe.Pointer, indir, top bool, msg string) { st := (*slicetype)(unsafe.Pointer(t)) s := (*slice)(p) p = s.array - if !cgoIsGoPointer(p) { + if p == nil || !cgoIsGoPointer(p) { return } if !top { @@ -548,11 +548,17 @@ func cgoCheckArg(t *_type, p unsafe.Pointer, indir, top bool, msg string) { return } for _, f := range st.fields { + if f.typ.ptrdata == 0 { + continue + } cgoCheckArg(f.typ, add(p, f.offset()), true, top, msg) } case kindPtr, kindUnsafePointer: if indir { p = *(*unsafe.Pointer)(p) + if p == nil { + return + } } if !cgoIsGoPointer(p) { @@ -644,7 +650,7 @@ func cgoCheckResult(val interface{}) { return } - ep := (*eface)(unsafe.Pointer(&val)) + ep := efaceOf(&val) t := ep._type cgoCheckArg(t, ep.data, t.kind&kindDirectIface == 0, false, cgoResultFail) } diff --git a/src/runtime/iface.go b/src/runtime/iface.go index bb4eccc9bd..243e51fc48 100644 --- a/src/runtime/iface.go +++ b/src/runtime/iface.go @@ -295,11 +295,11 @@ var ( stringEface interface{} = stringInterfacePtr("") sliceEface interface{} = sliceInterfacePtr(nil) - uint16Type *_type = (*eface)(unsafe.Pointer(&uint16Eface))._type - uint32Type *_type = (*eface)(unsafe.Pointer(&uint32Eface))._type - uint64Type *_type = (*eface)(unsafe.Pointer(&uint64Eface))._type - stringType *_type = (*eface)(unsafe.Pointer(&stringEface))._type - sliceType *_type = (*eface)(unsafe.Pointer(&sliceEface))._type + uint16Type *_type = efaceOf(&uint16Eface)._type + uint32Type *_type = efaceOf(&uint32Eface)._type + uint64Type *_type = efaceOf(&uint64Eface)._type + stringType *_type = efaceOf(&stringEface)._type + sliceType *_type = efaceOf(&sliceEface)._type ) // The conv and assert functions below do very similar things. diff --git a/src/runtime/os_windows.go b/src/runtime/os_windows.go index 567c567000..34d0627fcb 100644 --- a/src/runtime/os_windows.go +++ b/src/runtime/os_windows.go @@ -277,13 +277,11 @@ func monitorSuspendResume() { return // Running on Windows 7, where we don't need it anyway. } var fn interface{} = func(context uintptr, changeType uint32, setting uintptr) uintptr { - lock(&allglock) - for _, gp := range allgs { - if gp.m != nil && gp.m.resumesema != 0 { - stdcall1(_SetEvent, gp.m.resumesema) + for mp := (*m)(atomic.Loadp(unsafe.Pointer(&allm))); mp != nil; mp = mp.alllink { + if mp.resumesema != 0 { + stdcall1(_SetEvent, mp.resumesema) } } - unlock(&allglock) return 0 } params := _DEVICE_NOTIFY_SUBSCRIBE_PARAMETERS{ diff --git a/src/runtime/sys_darwin.go b/src/runtime/sys_darwin.go index 932a2a7757..46825d5937 100644 --- a/src/runtime/sys_darwin.go +++ b/src/runtime/sys_darwin.go @@ -60,7 +60,7 @@ func libcCall(fn, arg unsafe.Pointer) int32 { //go:nosplit //go:cgo_unsafe_args func syscall_syscall(fn, a1, a2, a3 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscall)), unsafe.Pointer(&fn)) exitsyscall() return @@ -71,7 +71,7 @@ func syscall() //go:nosplit //go:cgo_unsafe_args func syscall_syscall6(fn, a1, a2, a3, a4, a5, a6 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscall6)), unsafe.Pointer(&fn)) exitsyscall() return @@ -82,7 +82,7 @@ func syscall6() //go:nosplit //go:cgo_unsafe_args func syscall_syscall6X(fn, a1, a2, a3, a4, a5, a6 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscall6X)), unsafe.Pointer(&fn)) exitsyscall() return @@ -93,7 +93,7 @@ func syscall6X() //go:nosplit //go:cgo_unsafe_args func syscall_syscallPtr(fn, a1, a2, a3 uintptr) (r1, r2, err uintptr) { - entersyscallblock() + entersyscall() libcCall(unsafe.Pointer(funcPC(syscallPtr)), unsafe.Pointer(&fn)) exitsyscall() return diff --git a/src/runtime/testdata/testprogcgo/numgoroutine.go b/src/runtime/testdata/testprogcgo/numgoroutine.go index 12fda49a13..5bdfe52ed4 100644 --- a/src/runtime/testdata/testprogcgo/numgoroutine.go +++ b/src/runtime/testdata/testprogcgo/numgoroutine.go @@ -41,13 +41,6 @@ func NumGoroutine() { // Test that there are just the expected number of goroutines // running. Specifically, test that the spare M's goroutine // doesn't show up. - // - // On non-Windows platforms there's a signal handling thread - // started by os/signal.init in addition to the main - // goroutine. - if runtime.GOOS != "windows" { - baseGoroutines = 1 - } if _, ok := checkNumGoroutine("first", 1+baseGoroutines); !ok { return } |
