type Pinner … // Pin pins a Go object, preventing it from being moved or freed by the garbage // collector until the [Pinner.Unpin] method has been called. // // A pointer to a pinned object can be directly stored in C memory or can be // contained in Go memory passed to C functions. If the pinned object itself // contains pointers to Go objects, these objects must be pinned separately if they // are going to be accessed from C code. // // The argument must be a pointer of any type or an [unsafe.Pointer]. // It's safe to call Pin on non-Go pointers, in which case Pin will do nothing. func (p *Pinner) Pin(pointer any) { … } // Unpin unpins all pinned objects of the [Pinner]. func (p *Pinner) Unpin() { … } const pinnerSize … const pinnerRefStoreSize … type pinner … func (p *pinner) unpin() { … } func pinnerGetPtr(i *any) unsafe.Pointer { … } // isPinned checks if a Go pointer is pinned. // nosplit, because it's called from nosplit code in cgocheck. // //go:nosplit func isPinned(ptr unsafe.Pointer) bool { … } // setPinned marks or unmarks a Go pointer as pinned, when the ptr is a Go pointer. // It will be ignored while try to pin a non-Go pointer, // and it will be panic while try to unpin a non-Go pointer, // which should not happen in normal usage. func setPinned(ptr unsafe.Pointer, pin bool) bool { … } type pinState … // nosplit, because it's called by isPinned, which is nosplit // //go:nosplit func (v *pinState) isPinned() bool { … } func (v *pinState) isMultiPinned() bool { … } func (v *pinState) setPinned(val bool) { … } func (v *pinState) setMultiPinned(val bool) { … } // set sets the pin bit of the pinState to val. If multipin is true, it // sets/unsets the multipin bit instead. func (v *pinState) set(val bool, multipin bool) { … } type pinnerBits … // ofObject returns the pinState of the n'th object. // nosplit, because it's called by isPinned, which is nosplit // //go:nosplit func (p *pinnerBits) ofObject(n uintptr) pinState { … } func (s *mspan) pinnerBitSize() uintptr { … } // newPinnerBits returns a pointer to 8 byte aligned bytes to be used for this // span's pinner bits. newPinnerBits is used to mark objects that are pinned. // They are copied when the span is swept. func (s *mspan) newPinnerBits() *pinnerBits { … } // nosplit, because it's called by isPinned, which is nosplit // //go:nosplit func (s *mspan) getPinnerBits() *pinnerBits { … } func (s *mspan) setPinnerBits(p *pinnerBits) { … } // refreshPinnerBits replaces pinnerBits with a fresh copy in the arenas for the // next GC cycle. If it does not contain any pinned objects, pinnerBits of the // span is set to nil. func (s *mspan) refreshPinnerBits() { … } // incPinCounter is only called for multiple pins of the same object and records // the _additional_ pins. func (span *mspan) incPinCounter(offset uintptr) { … } // decPinCounter decreases the counter. If the counter reaches 0, the counter // special is deleted and false is returned. Otherwise true is returned. func (span *mspan) decPinCounter(offset uintptr) bool { … } // only for tests func pinnerGetPinCounter(addr unsafe.Pointer) *uintptr { … } var pinnerLeakPanic …