MOVL AX, ret+8(FP)
RET
-TEXT runtime·xchgp1(SB), NOSPLIT, $0-12
- MOVL ptr+0(FP), BX
- MOVL new+4(FP), AX
- XCHGL AX, 0(BX)
- MOVL AX, ret+8(FP)
- RET
-
TEXT runtime·xchguintptr(SB), NOSPLIT, $0-12
JMP runtime·xchg(SB)
MOVQ AX, ret+16(FP)
RET
-TEXT runtime·xchgp1(SB), NOSPLIT, $0-24
- MOVQ ptr+0(FP), BX
- MOVQ new+8(FP), AX
- XCHGQ AX, 0(BX)
- MOVQ AX, ret+16(FP)
- RET
-
TEXT runtime·xchguintptr(SB), NOSPLIT, $0-24
JMP runtime·xchg64(SB)
MOVQ AX, ret+16(FP)
RET
-TEXT runtime·xchgp1(SB), NOSPLIT, $0-12
- MOVL ptr+0(FP), BX
- MOVL new+4(FP), AX
- XCHGL AX, 0(BX)
- MOVL AX, ret+8(FP)
- RET
-
TEXT runtime·xchguintptr(SB), NOSPLIT, $0-12
JMP runtime·xchg(SB)
MOVD R3, ret+16(FP)
RET
-TEXT runtime·xchgp1(SB), NOSPLIT, $0-24
- BR runtime·xchg64(SB)
-
TEXT runtime·xchguintptr(SB), NOSPLIT, $0-24
BR runtime·xchg64(SB)
//go:noescape
func xchg(ptr *uint32, new uint32) uint32
-// NO go:noescape annotation; see atomic_pointer.go.
-func xchgp1(ptr unsafe.Pointer, new unsafe.Pointer) unsafe.Pointer
-
//go:noescape
func xchguintptr(ptr *uintptr, new uintptr) uintptr
//go:noescape
func xchg64(ptr *uint64, new uint64) uint64
-// NO go:noescape annotation; see atomic_pointer.go.
-func xchgp1(ptr unsafe.Pointer, new unsafe.Pointer) unsafe.Pointer
-
//go:noescape
func xchguintptr(ptr *uintptr, new uintptr) uintptr
}
}
-//go:nosplit
-func xchgp1(addr unsafe.Pointer, v unsafe.Pointer) unsafe.Pointer {
- for {
- old := *(*unsafe.Pointer)(addr)
- if casp1((*unsafe.Pointer)(addr), old, v) {
- return old
- }
- }
-}
-
//go:nosplit
func xchguintptr(addr *uintptr, v uintptr) uintptr {
return uintptr(xchg((*uint32)(unsafe.Pointer(addr)), uint32(v)))
//go:noescape
func xchg64(ptr *uint64, new uint64) uint64
-// NO go:noescape annotation; see atomic_pointer.go.
-func xchgp1(ptr unsafe.Pointer, new unsafe.Pointer) unsafe.Pointer
-
//go:noescape
func xchguintptr(ptr *uintptr, new uintptr) uintptr
// because while ptr does not escape, new does.
// If new is marked as not escaping, the compiler will make incorrect
// escape analysis decisions about the pointer value being stored.
-// Instead, these are wrappers around the actual atomics (xchgp1 and so on)
+// Instead, these are wrappers around the actual atomics (casp1 and so on)
// that use noescape to convey which arguments do not escape.
//
// Additionally, these functions must update the shadow heap for
writebarrierptr_nostore((*uintptr)(ptr), uintptr(new))
}
-//go:nosplit
-func xchgp(ptr unsafe.Pointer, new unsafe.Pointer) unsafe.Pointer {
- old := xchgp1(noescape(ptr), new)
- writebarrierptr_nostore((*uintptr)(ptr), uintptr(new))
- return old
-}
-
//go:nosplit
func casp(ptr *unsafe.Pointer, old, new unsafe.Pointer) bool {
if !casp1((*unsafe.Pointer)(noescape(unsafe.Pointer(ptr))), noescape(old), new) {
//go:noescape
func xchg64(ptr *uint64, new uint64) uint64
-// NO go:noescape annotation; see atomic_pointer.go.
-func xchgp1(ptr unsafe.Pointer, new unsafe.Pointer) unsafe.Pointer
-
//go:noescape
func xchguintptr(ptr *uintptr, new uintptr) uintptr