sysvshm_unix.go raw

   1  // Copyright 2021 The Go Authors. All rights reserved.
   2  // Use of this source code is governed by a BSD-style
   3  // license that can be found in the LICENSE file.
   4  
   5  //go:build (darwin && !ios) || linux || zos
   6  
   7  package unix
   8  
   9  import "unsafe"
  10  
  11  // SysvShmAttach attaches the Sysv shared memory segment associated with the
  12  // shared memory identifier id.
  13  func SysvShmAttach(id int, addr uintptr, flag int) ([]byte, error) {
  14  	addr, errno := shmat(id, addr, flag)
  15  	if errno != nil {
  16  		return nil, errno
  17  	}
  18  
  19  	// Retrieve the size of the shared memory to enable slice creation
  20  	var info SysvShmDesc
  21  
  22  	_, err := SysvShmCtl(id, IPC_STAT, &info)
  23  	if err != nil {
  24  		// release the shared memory if we can't find the size
  25  
  26  		// ignoring error from shmdt as there's nothing sensible to return here
  27  		shmdt(addr)
  28  		return nil, err
  29  	}
  30  
  31  	// Use unsafe to convert addr into a []byte.
  32  	b := unsafe.Slice((*byte)(unsafe.Pointer(addr)), int(info.Segsz))
  33  	return b, nil
  34  }
  35  
  36  // SysvShmDetach unmaps the shared memory slice returned from SysvShmAttach.
  37  //
  38  // It is not safe to use the slice after calling this function.
  39  func SysvShmDetach(data []byte) error {
  40  	if len(data) == 0 {
  41  		return EINVAL
  42  	}
  43  
  44  	return shmdt(uintptr(unsafe.Pointer(&data[0])))
  45  }
  46  
  47  // SysvShmGet returns the Sysv shared memory identifier associated with key.
  48  // If the IPC_CREAT flag is specified a new segment is created.
  49  func SysvShmGet(key, size, flag int) (id int, err error) {
  50  	return shmget(key, size, flag)
  51  }
  52