github.com/ttpreport/gvisor-ligolo@v0.0.0-20240123134145-a858404967ba/pkg/sentry/kernel/atomicptr_descriptor_unsafe.go (about)

     1  package kernel
     2  
     3  import (
     4  	"sync/atomic"
     5  	"unsafe"
     6  )
     7  
     8  // An AtomicPtr is a pointer to a value of type Value that can be atomically
     9  // loaded and stored. The zero value of an AtomicPtr represents nil.
    10  //
    11  // Note that copying AtomicPtr by value performs a non-atomic read of the
    12  // stored pointer, which is unsafe if Store() can be called concurrently; in
    13  // this case, do `dst.Store(src.Load())` instead.
    14  //
    15  // +stateify savable
    16  type descriptorAtomicPtr struct {
    17  	ptr unsafe.Pointer `state:".(*descriptor)"`
    18  }
    19  
    20  func (p *descriptorAtomicPtr) savePtr() *descriptor {
    21  	return p.Load()
    22  }
    23  
    24  func (p *descriptorAtomicPtr) loadPtr(v *descriptor) {
    25  	p.Store(v)
    26  }
    27  
    28  // Load returns the value set by the most recent Store. It returns nil if there
    29  // has been no previous call to Store.
    30  //
    31  //go:nosplit
    32  func (p *descriptorAtomicPtr) Load() *descriptor {
    33  	return (*descriptor)(atomic.LoadPointer(&p.ptr))
    34  }
    35  
    36  // Store sets the value returned by Load to x.
    37  func (p *descriptorAtomicPtr) Store(x *descriptor) {
    38  	atomic.StorePointer(&p.ptr, (unsafe.Pointer)(x))
    39  }
    40  
    41  // Swap atomically stores `x` into *p and returns the previous *p value.
    42  func (p *descriptorAtomicPtr) Swap(x *descriptor) *descriptor {
    43  	return (*descriptor)(atomic.SwapPointer(&p.ptr, (unsafe.Pointer)(x)))
    44  }