github.com/SagerNet/gvisor@v0.0.0-20210707092255-7731c139d75c/pkg/sync/atomicptr/generic_atomicptr_unsafe.go (about) 1 // Copyright 2019 The gVisor Authors. 2 // 3 // Use of this source code is governed by a BSD-style 4 // license that can be found in the LICENSE file. 5 6 // Package seqatomic doesn't exist. This file must be instantiated using the 7 // go_template_instance rule in tools/go_generics/defs.bzl. 8 package seqatomic 9 10 import ( 11 "sync/atomic" 12 "unsafe" 13 ) 14 15 // Value is a required type parameter. 16 type Value struct{} 17 18 // An AtomicPtr is a pointer to a value of type Value that can be atomically 19 // loaded and stored. The zero value of an AtomicPtr represents nil. 20 // 21 // Note that copying AtomicPtr by value performs a non-atomic read of the 22 // stored pointer, which is unsafe if Store() can be called concurrently; in 23 // this case, do `dst.Store(src.Load())` instead. 24 // 25 // +stateify savable 26 type AtomicPtr struct { 27 ptr unsafe.Pointer `state:".(*Value)"` 28 } 29 30 func (p *AtomicPtr) savePtr() *Value { 31 return p.Load() 32 } 33 34 func (p *AtomicPtr) loadPtr(v *Value) { 35 p.Store(v) 36 } 37 38 // Load returns the value set by the most recent Store. It returns nil if there 39 // has been no previous call to Store. 40 func (p *AtomicPtr) Load() *Value { 41 return (*Value)(atomic.LoadPointer(&p.ptr)) 42 } 43 44 // Store sets the value returned by Load to x. 45 func (p *AtomicPtr) Store(x *Value) { 46 atomic.StorePointer(&p.ptr, (unsafe.Pointer)(x)) 47 }