github.com/4ad/go@v0.0.0-20161219182952-69a12818b605/src/runtime/os3_solaris.go (about)

     1  // Copyright 2011 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  package runtime
     6  
     7  import "unsafe"
     8  
     9  //go:cgo_export_dynamic runtime.end _end
    10  //go:cgo_export_dynamic runtime.etext _etext
    11  //go:cgo_export_dynamic runtime.edata _edata
    12  
    13  //go:cgo_import_dynamic libc____errno ___errno "libc.so"
    14  //go:cgo_import_dynamic libc_clock_gettime clock_gettime "libc.so"
    15  //go:cgo_import_dynamic libc_close close "libc.so"
    16  //go:cgo_import_dynamic libc_exit exit "libc.so"
    17  //go:cgo_import_dynamic libc_fstat fstat "libc.so"
    18  //go:cgo_import_dynamic libc_getcontext getcontext "libc.so"
    19  //go:cgo_import_dynamic libc_getrlimit getrlimit "libc.so"
    20  //go:cgo_import_dynamic libc_kill kill "libc.so"
    21  //go:cgo_import_dynamic libc_madvise madvise "libc.so"
    22  //go:cgo_import_dynamic libc_malloc malloc "libc.so"
    23  //go:cgo_import_dynamic libc_mmap mmap "libc.so"
    24  //go:cgo_import_dynamic libc_munmap munmap "libc.so"
    25  //go:cgo_import_dynamic libc_open open "libc.so"
    26  //go:cgo_import_dynamic libc_pthread_attr_destroy pthread_attr_destroy "libc.so"
    27  //go:cgo_import_dynamic libc_pthread_attr_getstack pthread_attr_getstack "libc.so"
    28  //go:cgo_import_dynamic libc_pthread_attr_init pthread_attr_init "libc.so"
    29  //go:cgo_import_dynamic libc_pthread_attr_setdetachstate pthread_attr_setdetachstate "libc.so"
    30  //go:cgo_import_dynamic libc_pthread_attr_setstack pthread_attr_setstack "libc.so"
    31  //go:cgo_import_dynamic libc_pthread_create pthread_create "libc.so"
    32  //go:cgo_import_dynamic libc_raise raise "libc.so"
    33  //go:cgo_import_dynamic libc_read read "libc.so"
    34  //go:cgo_import_dynamic libc_select select "libc.so"
    35  //go:cgo_import_dynamic libc_sched_yield sched_yield "libc.so"
    36  //go:cgo_import_dynamic libc_sem_init sem_init "libc.so"
    37  //go:cgo_import_dynamic libc_sem_post sem_post "libc.so"
    38  //go:cgo_import_dynamic libc_sem_reltimedwait_np sem_reltimedwait_np "libc.so"
    39  //go:cgo_import_dynamic libc_sem_wait sem_wait "libc.so"
    40  //go:cgo_import_dynamic libc_setitimer setitimer "libc.so"
    41  //go:cgo_import_dynamic libc_sigaction sigaction "libc.so"
    42  //go:cgo_import_dynamic libc_sigaltstack sigaltstack "libc.so"
    43  //go:cgo_import_dynamic libc_sigprocmask sigprocmask "libc.so"
    44  //go:cgo_import_dynamic libc_sysconf sysconf "libc.so"
    45  //go:cgo_import_dynamic libc_usleep usleep "libc.so"
    46  //go:cgo_import_dynamic libc_write write "libc.so"
    47  
    48  //go:linkname libc____errno libc____errno
    49  //go:linkname libc_clock_gettime libc_clock_gettime
    50  //go:linkname libc_close libc_close
    51  //go:linkname libc_exit libc_exit
    52  //go:linkname libc_fstat libc_fstat
    53  //go:linkname libc_getcontext libc_getcontext
    54  //go:linkname libc_getrlimit libc_getrlimit
    55  //go:linkname libc_kill libc_kill
    56  //go:linkname libc_madvise libc_madvise
    57  //go:linkname libc_malloc libc_malloc
    58  //go:linkname libc_mmap libc_mmap
    59  //go:linkname libc_munmap libc_munmap
    60  //go:linkname libc_open libc_open
    61  //go:linkname libc_pthread_attr_destroy libc_pthread_attr_destroy
    62  //go:linkname libc_pthread_attr_getstack libc_pthread_attr_getstack
    63  //go:linkname libc_pthread_attr_init libc_pthread_attr_init
    64  //go:linkname libc_pthread_attr_setdetachstate libc_pthread_attr_setdetachstate
    65  //go:linkname libc_pthread_attr_setstack libc_pthread_attr_setstack
    66  //go:linkname libc_pthread_create libc_pthread_create
    67  //go:linkname libc_raise libc_raise
    68  //go:linkname libc_read libc_read
    69  //go:linkname libc_select libc_select
    70  //go:linkname libc_sched_yield libc_sched_yield
    71  //go:linkname libc_sem_init libc_sem_init
    72  //go:linkname libc_sem_post libc_sem_post
    73  //go:linkname libc_sem_reltimedwait_np libc_sem_reltimedwait_np
    74  //go:linkname libc_sem_wait libc_sem_wait
    75  //go:linkname libc_setitimer libc_setitimer
    76  //go:linkname libc_sigaction libc_sigaction
    77  //go:linkname libc_sigaltstack libc_sigaltstack
    78  //go:linkname libc_sigprocmask libc_sigprocmask
    79  //go:linkname libc_sysconf libc_sysconf
    80  //go:linkname libc_usleep libc_usleep
    81  //go:linkname libc_write libc_write
    82  
    83  var (
    84  	libc____errno,
    85  	libc_clock_gettime,
    86  	libc_close,
    87  	libc_exit,
    88  	libc_fstat,
    89  	libc_getcontext,
    90  	libc_getrlimit,
    91  	libc_kill,
    92  	libc_madvise,
    93  	libc_malloc,
    94  	libc_mmap,
    95  	libc_munmap,
    96  	libc_open,
    97  	libc_pthread_attr_destroy,
    98  	libc_pthread_attr_getstack,
    99  	libc_pthread_attr_init,
   100  	libc_pthread_attr_setdetachstate,
   101  	libc_pthread_attr_setstack,
   102  	libc_pthread_create,
   103  	libc_raise,
   104  	libc_read,
   105  	libc_sched_yield,
   106  	libc_select,
   107  	libc_sem_init,
   108  	libc_sem_post,
   109  	libc_sem_reltimedwait_np,
   110  	libc_sem_wait,
   111  	libc_setitimer,
   112  	libc_sigaction,
   113  	libc_sigaltstack,
   114  	libc_sigprocmask,
   115  	libc_sysconf,
   116  	libc_usleep,
   117  	libc_write libcFunc
   118  )
   119  
   120  var sigset_all = sigset{[4]uint32{^uint32(0), ^uint32(0), ^uint32(0), ^uint32(0)}}
   121  
   122  func getncpu() int32 {
   123  	n := int32(sysconf(__SC_NPROCESSORS_ONLN))
   124  	if n < 1 {
   125  		return 1
   126  	}
   127  	return n
   128  }
   129  
   130  func getPageSize() uintptr {
   131  	n := int32(sysconf(__SC_PAGESIZE))
   132  	if n <= 0 {
   133  		return 0
   134  	}
   135  	return uintptr(n)
   136  }
   137  
   138  func osinit() {
   139  	ncpu = getncpu()
   140  	physPageSize = getPageSize()
   141  }
   142  
   143  func tstart_sysvicall()
   144  
   145  // May run with m.p==nil, so write barriers are not allowed.
   146  //go:nowritebarrier
   147  func newosproc(mp *m, _ unsafe.Pointer) {
   148  	var (
   149  		attr pthreadattr
   150  		oset sigset
   151  		tid  pthread
   152  		ret  int32
   153  		size uint64
   154  	)
   155  
   156  	if pthread_attr_init(&attr) != 0 {
   157  		throw("pthread_attr_init")
   158  	}
   159  	if pthread_attr_setstack(&attr, 0, 0x200000) != 0 {
   160  		throw("pthread_attr_setstack")
   161  	}
   162  	if pthread_attr_getstack(&attr, unsafe.Pointer(&mp.g0.stack.hi), &size) != 0 {
   163  		throw("pthread_attr_getstack")
   164  	}
   165  	mp.g0.stack.lo = mp.g0.stack.hi - uintptr(size)
   166  	if pthread_attr_setdetachstate(&attr, _PTHREAD_CREATE_DETACHED) != 0 {
   167  		throw("pthread_attr_setdetachstate")
   168  	}
   169  
   170  	// Disable signals during create, so that the new thread starts
   171  	// with signals disabled. It will enable them in minit.
   172  	sigprocmask(_SIG_SETMASK, &sigset_all, &oset)
   173  	ret = pthread_create(&tid, &attr, funcPC(tstart_sysvicall), unsafe.Pointer(mp))
   174  	sigprocmask(_SIG_SETMASK, &oset, nil)
   175  	if ret != 0 {
   176  		print("runtime: failed to create new OS thread (have ", mcount(), " already; errno=", ret, ")\n")
   177  		if ret == -_EAGAIN {
   178  			println("runtime: may need to increase max user processes (ulimit -u)")
   179  		}
   180  		throw("newosproc")
   181  	}
   182  }
   183  
   184  var urandom_dev = []byte("/dev/urandom\x00")
   185  
   186  //go:nosplit
   187  func getRandomData(r []byte) {
   188  	fd := open(&urandom_dev[0], 0 /* O_RDONLY */, 0)
   189  	n := read(fd, unsafe.Pointer(&r[0]), int32(len(r)))
   190  	closefd(fd)
   191  	extendRandom(r, int(n))
   192  }
   193  
   194  func goenvs() {
   195  	goenvs_unix()
   196  }
   197  
   198  // Called to initialize a new m (including the bootstrap m).
   199  // Called on the parent thread (main thread in case of bootstrap), can allocate memory.
   200  func mpreinit(mp *m) {
   201  	mp.gsignal = malg(32 * 1024)
   202  	mp.gsignal.m = mp
   203  }
   204  
   205  func miniterrno()
   206  
   207  //go:nosplit
   208  func msigsave(mp *m) {
   209  	sigprocmask(_SIG_SETMASK, nil, &mp.sigmask)
   210  }
   211  
   212  //go:nosplit
   213  func msigrestore(sigmask sigset) {
   214  	sigprocmask(_SIG_SETMASK, &sigmask, nil)
   215  }
   216  
   217  //go:nosplit
   218  func sigblock() {
   219  	sigprocmask(_SIG_SETMASK, &sigset_all, nil)
   220  }
   221  
   222  // Called to initialize a new m (including the bootstrap m).
   223  // Called on the new thread, cannot allocate memory.
   224  func minit() {
   225  	_g_ := getg()
   226  	asmcgocall(unsafe.Pointer(funcPC(miniterrno)), unsafe.Pointer(&libc____errno))
   227  	// Initialize signal handling
   228  	var st sigaltstackt
   229  	sigaltstack(nil, &st)
   230  	if st.ss_flags&_SS_DISABLE != 0 {
   231  		signalstack(&_g_.m.gsignal.stack)
   232  		_g_.m.newSigstack = true
   233  	} else {
   234  		// Use existing signal stack.
   235  		stsp := uintptr(unsafe.Pointer(st.ss_sp))
   236  		_g_.m.gsignal.stack.lo = stsp
   237  		_g_.m.gsignal.stack.hi = stsp + uintptr(st.ss_size)
   238  		_g_.m.gsignal.stackguard0 = stsp + _StackGuard
   239  		_g_.m.gsignal.stackguard1 = stsp + _StackGuard
   240  		_g_.m.gsignal.stackAlloc = uintptr(st.ss_size)
   241  		_g_.m.newSigstack = false
   242  	}
   243  
   244  	// restore signal mask from m.sigmask and unblock essential signals
   245  	nmask := _g_.m.sigmask
   246  	for i := range sigtable {
   247  		if sigtable[i].flags&_SigUnblock != 0 {
   248  			nmask.__sigbits[(i-1)/32] &^= 1 << ((uint32(i) - 1) & 31)
   249  		}
   250  	}
   251  	sigprocmask(_SIG_SETMASK, &nmask, nil)
   252  }
   253  
   254  // Called from dropm to undo the effect of an minit.
   255  func unminit() {
   256  	if getg().m.newSigstack {
   257  		signalstack(nil)
   258  	}
   259  }
   260  
   261  func memlimit() uintptr {
   262  	/*
   263  		TODO: Convert to Go when something actually uses the result.
   264  		Rlimit rl;
   265  		extern byte runtime·text[], runtime·end[];
   266  		uintptr used;
   267  
   268  		if(runtime·getrlimit(RLIMIT_AS, &rl) != 0)
   269  			return 0;
   270  		if(rl.rlim_cur >= 0x7fffffff)
   271  			return 0;
   272  
   273  		// Estimate our VM footprint excluding the heap.
   274  		// Not an exact science: use size of binary plus
   275  		// some room for thread stacks.
   276  		used = runtime·end - runtime·text + (64<<20);
   277  		if(used >= rl.rlim_cur)
   278  			return 0;
   279  
   280  		// If there's not at least 16 MB left, we're probably
   281  		// not going to be able to do much. Treat as no limit.
   282  		rl.rlim_cur -= used;
   283  		if(rl.rlim_cur < (16<<20))
   284  			return 0;
   285  
   286  		return rl.rlim_cur - used;
   287  	*/
   288  
   289  	return 0
   290  }
   291  
   292  func sigtramp()
   293  
   294  //go:nosplit
   295  //go:nowritebarrierrec
   296  func setsig(i int32, fn uintptr, restart bool) {
   297  	var sa sigactiont
   298  
   299  	sa.sa_flags = _SA_SIGINFO | _SA_ONSTACK
   300  	if restart {
   301  		sa.sa_flags |= _SA_RESTART
   302  	}
   303  	sa.sa_mask = sigset_all
   304  	if fn == funcPC(sighandler) {
   305  		fn = funcPC(sigtramp)
   306  	}
   307  	*((*uintptr)(unsafe.Pointer(&sa._funcptr))) = fn
   308  	sigaction(i, &sa, nil)
   309  }
   310  
   311  //go:nosplit
   312  //go:nowritebarrierrec
   313  func setsigstack(i int32) {
   314  	var sa sigactiont
   315  	sigaction(i, nil, &sa)
   316  	handler := *((*uintptr)(unsafe.Pointer(&sa._funcptr)))
   317  	if handler == 0 || handler == _SIG_DFL || handler == _SIG_IGN || sa.sa_flags&_SA_ONSTACK != 0 {
   318  		return
   319  	}
   320  	sa.sa_flags |= _SA_ONSTACK
   321  	sigaction(i, &sa, nil)
   322  }
   323  
   324  //go:nosplit
   325  //go:nowritebarrierrec
   326  func getsig(i int32) uintptr {
   327  	var sa sigactiont
   328  	sigaction(i, nil, &sa)
   329  	if *((*uintptr)(unsafe.Pointer(&sa._funcptr))) == funcPC(sigtramp) {
   330  		return funcPC(sighandler)
   331  	}
   332  	return *((*uintptr)(unsafe.Pointer(&sa._funcptr)))
   333  }
   334  
   335  //go:nosplit
   336  func signalstack(s *stack) {
   337  	var st sigaltstackt
   338  	if s == nil {
   339  		st.ss_flags = _SS_DISABLE
   340  	} else {
   341  		st.ss_sp = (*byte)(unsafe.Pointer(s.lo))
   342  		st.ss_size = uint64(s.hi - s.lo)
   343  		st.ss_flags = 0
   344  	}
   345  	sigaltstack(&st, nil)
   346  }
   347  
   348  //go:nosplit
   349  //go:nowritebarrierrec
   350  func updatesigmask(m sigmask) {
   351  	var mask sigset
   352  	copy(mask.__sigbits[:], m[:])
   353  	sigprocmask(_SIG_SETMASK, &mask, nil)
   354  }
   355  
   356  func unblocksig(sig int32) {
   357  	var mask sigset
   358  	mask.__sigbits[(sig-1)/32] |= 1 << ((uint32(sig) - 1) & 31)
   359  	sigprocmask(_SIG_UNBLOCK, &mask, nil)
   360  }
   361  
   362  //go:nosplit
   363  func semacreate(mp *m) {
   364  	if mp.waitsema != 0 {
   365  		return
   366  	}
   367  
   368  	var sem *semt
   369  	_g_ := getg()
   370  
   371  	// Call libc's malloc rather than malloc. This will
   372  	// allocate space on the C heap. We can't call malloc
   373  	// here because it could cause a deadlock.
   374  	_g_.m.libcall.fn = uintptr(unsafe.Pointer(&libc_malloc))
   375  	_g_.m.libcall.n = 1
   376  	memclr(unsafe.Pointer(&_g_.m.scratch), uintptr(len(_g_.m.scratch.v)))
   377  	_g_.m.scratch.v[0] = unsafe.Sizeof(*sem)
   378  	_g_.m.libcall.args = uintptr(unsafe.Pointer(&_g_.m.scratch))
   379  	asmcgocall(unsafe.Pointer(&asmsysvicall6), unsafe.Pointer(&_g_.m.libcall))
   380  	sem = (*semt)(unsafe.Pointer(_g_.m.libcall.r1))
   381  	if sem_init(sem, 0, 0) != 0 {
   382  		throw("sem_init")
   383  	}
   384  	mp.waitsema = uintptr(unsafe.Pointer(sem))
   385  }
   386  
   387  //go:nosplit
   388  func semasleep(ns int64) int32 {
   389  	_m_ := getg().m
   390  	if ns >= 0 {
   391  		_m_.ts.tv_sec = ns / 1000000000
   392  		_m_.ts.tv_nsec = ns % 1000000000
   393  
   394  		_m_.libcall.fn = uintptr(unsafe.Pointer(&libc_sem_reltimedwait_np))
   395  		_m_.libcall.n = 2
   396  		memclr(unsafe.Pointer(&_m_.scratch), uintptr(len(_m_.scratch.v)))
   397  		_m_.scratch.v[0] = _m_.waitsema
   398  		_m_.scratch.v[1] = uintptr(unsafe.Pointer(&_m_.ts))
   399  		_m_.libcall.args = uintptr(unsafe.Pointer(&_m_.scratch))
   400  		asmcgocall(unsafe.Pointer(&asmsysvicall6), unsafe.Pointer(&_m_.libcall))
   401  		if *_m_.perrno != 0 {
   402  			if *_m_.perrno == _ETIMEDOUT || *_m_.perrno == _EAGAIN || *_m_.perrno == _EINTR {
   403  				return -1
   404  			}
   405  			throw("sem_reltimedwait_np")
   406  		}
   407  		return 0
   408  	}
   409  	for {
   410  		_m_.libcall.fn = uintptr(unsafe.Pointer(&libc_sem_wait))
   411  		_m_.libcall.n = 1
   412  		memclr(unsafe.Pointer(&_m_.scratch), uintptr(len(_m_.scratch.v)))
   413  		_m_.scratch.v[0] = _m_.waitsema
   414  		_m_.libcall.args = uintptr(unsafe.Pointer(&_m_.scratch))
   415  		asmcgocall(unsafe.Pointer(&asmsysvicall6), unsafe.Pointer(&_m_.libcall))
   416  		if _m_.libcall.r1 == 0 {
   417  			break
   418  		}
   419  		if *_m_.perrno == _EINTR {
   420  			continue
   421  		}
   422  		throw("sem_wait")
   423  	}
   424  	return 0
   425  }
   426  
   427  //go:nosplit
   428  func semawakeup(mp *m) {
   429  	if sem_post((*semt)(unsafe.Pointer(mp.waitsema))) != 0 {
   430  		throw("sem_post")
   431  	}
   432  }
   433  
   434  //go:nosplit
   435  func closefd(fd int32) int32 {
   436  	return int32(sysvicall1(&libc_close, uintptr(fd)))
   437  }
   438  
   439  //go:nosplit
   440  func exit(r int32) {
   441  	sysvicall1(&libc_exit, uintptr(r))
   442  }
   443  
   444  //go:nosplit
   445  func getcontext(context *ucontext) /* int32 */ {
   446  	sysvicall1(&libc_getcontext, uintptr(unsafe.Pointer(context)))
   447  }
   448  
   449  //go:nosplit
   450  func madvise(addr unsafe.Pointer, n uintptr, flags int32) {
   451  	sysvicall3(&libc_madvise, uintptr(addr), uintptr(n), uintptr(flags))
   452  }
   453  
   454  //go:nosplit
   455  func mmap(addr unsafe.Pointer, n uintptr, prot, flags, fd int32, off uint32) unsafe.Pointer {
   456  	p, err := doMmap(uintptr(addr), n, uintptr(prot), uintptr(flags), uintptr(fd), uintptr(off))
   457  	if p == ^uintptr(0) {
   458  		return unsafe.Pointer(err)
   459  	}
   460  	return unsafe.Pointer(p)
   461  }
   462  
   463  //go:nosplit
   464  func doMmap(addr, n, prot, flags, fd, off uintptr) (uintptr, uintptr) {
   465  	var libcall libcall
   466  	libcall.fn = uintptr(unsafe.Pointer(&libc_mmap))
   467  	libcall.n = 6
   468  	libcall.args = uintptr(noescape(unsafe.Pointer(&addr)))
   469  	asmcgocall(unsafe.Pointer(&asmsysvicall6), unsafe.Pointer(&libcall))
   470  	return libcall.r1, libcall.err
   471  }
   472  
   473  //go:nosplit
   474  func munmap(addr unsafe.Pointer, n uintptr) {
   475  	sysvicall2(&libc_munmap, uintptr(addr), uintptr(n))
   476  }
   477  
   478  func nanotime1()
   479  
   480  //go:nosplit
   481  func nanotime() int64 {
   482  	return int64(sysvicall0((*libcFunc)(unsafe.Pointer(funcPC(nanotime1)))))
   483  }
   484  
   485  //go:nosplit
   486  func open(path *byte, mode, perm int32) int32 {
   487  	return int32(sysvicall3(&libc_open, uintptr(unsafe.Pointer(path)), uintptr(mode), uintptr(perm)))
   488  }
   489  
   490  func pthread_attr_destroy(attr *pthreadattr) int32 {
   491  	return int32(sysvicall1(&libc_pthread_attr_destroy, uintptr(unsafe.Pointer(attr))))
   492  }
   493  
   494  func pthread_attr_getstack(attr *pthreadattr, addr unsafe.Pointer, size *uint64) int32 {
   495  	return int32(sysvicall3(&libc_pthread_attr_getstack, uintptr(unsafe.Pointer(attr)), uintptr(addr), uintptr(unsafe.Pointer(size))))
   496  }
   497  
   498  func pthread_attr_init(attr *pthreadattr) int32 {
   499  	return int32(sysvicall1(&libc_pthread_attr_init, uintptr(unsafe.Pointer(attr))))
   500  }
   501  
   502  func pthread_attr_setdetachstate(attr *pthreadattr, state int32) int32 {
   503  	return int32(sysvicall2(&libc_pthread_attr_setdetachstate, uintptr(unsafe.Pointer(attr)), uintptr(state)))
   504  }
   505  
   506  func pthread_attr_setstack(attr *pthreadattr, addr uintptr, size uint64) int32 {
   507  	return int32(sysvicall3(&libc_pthread_attr_setstack, uintptr(unsafe.Pointer(attr)), uintptr(addr), uintptr(size)))
   508  }
   509  
   510  func pthread_create(thread *pthread, attr *pthreadattr, fn uintptr, arg unsafe.Pointer) int32 {
   511  	return int32(sysvicall4(&libc_pthread_create, uintptr(unsafe.Pointer(thread)), uintptr(unsafe.Pointer(attr)), uintptr(fn), uintptr(arg)))
   512  }
   513  
   514  //go:nosplit
   515  //go:nowritebarrierrec
   516  func raise(sig int32) /* int32 */ {
   517  	sysvicall1(&libc_raise, uintptr(sig))
   518  }
   519  
   520  func raiseproc(sig int32) /* int32 */ {
   521  	pid := sysvicall0(&libc_getpid)
   522  	sysvicall2(&libc_kill, pid, uintptr(sig))
   523  }
   524  
   525  //go:nosplit
   526  func read(fd int32, buf unsafe.Pointer, nbyte int32) int32 {
   527  	return int32(sysvicall3(&libc_read, uintptr(fd), uintptr(buf), uintptr(nbyte)))
   528  }
   529  
   530  //go:nosplit
   531  func sem_init(sem *semt, pshared int32, value uint32) int32 {
   532  	return int32(sysvicall3(&libc_sem_init, uintptr(unsafe.Pointer(sem)), uintptr(pshared), uintptr(value)))
   533  }
   534  
   535  //go:nosplit
   536  func sem_post(sem *semt) int32 {
   537  	return int32(sysvicall1(&libc_sem_post, uintptr(unsafe.Pointer(sem))))
   538  }
   539  
   540  //go:nosplit
   541  func sem_reltimedwait_np(sem *semt, timeout *timespec) int32 {
   542  	return int32(sysvicall2(&libc_sem_reltimedwait_np, uintptr(unsafe.Pointer(sem)), uintptr(unsafe.Pointer(timeout))))
   543  }
   544  
   545  //go:nosplit
   546  func sem_wait(sem *semt) int32 {
   547  	return int32(sysvicall1(&libc_sem_wait, uintptr(unsafe.Pointer(sem))))
   548  }
   549  
   550  func setitimer(which int32, value *itimerval, ovalue *itimerval) /* int32 */ {
   551  	sysvicall3(&libc_setitimer, uintptr(which), uintptr(unsafe.Pointer(value)), uintptr(unsafe.Pointer(ovalue)))
   552  }
   553  
   554  //go:nosplit
   555  //go:nowritebarrierrec
   556  func sigaction(sig int32, act *sigactiont, oact *sigactiont) /* int32 */ {
   557  	sysvicall3(&libc_sigaction, uintptr(sig), uintptr(unsafe.Pointer(act)), uintptr(unsafe.Pointer(oact)))
   558  }
   559  
   560  //go:nosplit
   561  //go:nowritebarrierrec
   562  func sigaltstack(ss *sigaltstackt, oss *sigaltstackt) /* int32 */ {
   563  	sysvicall2(&libc_sigaltstack, uintptr(unsafe.Pointer(ss)), uintptr(unsafe.Pointer(oss)))
   564  }
   565  
   566  //go:nosplit
   567  //go:nowritebarrierrec
   568  func sigprocmask(how int32, set *sigset, oset *sigset) /* int32 */ {
   569  	sysvicall3(&libc_sigprocmask, uintptr(how), uintptr(unsafe.Pointer(set)), uintptr(unsafe.Pointer(oset)))
   570  }
   571  
   572  func sysconf(name int32) int64 {
   573  	return int64(sysvicall1(&libc_sysconf, uintptr(name)))
   574  }
   575  
   576  func usleep1(uint32)
   577  
   578  //go:nosplit
   579  func usleep(µs uint32) {
   580  	usleep1(µs)
   581  }
   582  
   583  //go:nosplit
   584  func write(fd uintptr, buf unsafe.Pointer, nbyte int32) int32 {
   585  	return int32(sysvicall3(&libc_write, uintptr(fd), uintptr(buf), uintptr(nbyte)))
   586  }
   587  
   588  func osyield1()
   589  
   590  //go:nosplit
   591  func osyield() {
   592  	_g_ := getg()
   593  
   594  	// Check the validity of m because we might be called in cgo callback
   595  	// path early enough where there isn't a m available yet.
   596  	if _g_ != nil && _g_.m != nil {
   597  		sysvicall0(&libc_sched_yield)
   598  		return
   599  	}
   600  	osyield1()
   601  }
   602  
   603  //go:nosplit
   604  func threaddump() {
   605  	g := getg()
   606  	print("threaddump: g=", g, ", g.m=", g.m, ", g.m.g0=", g.m.g0, ", g.m.gsignal=", g.m.gsignal, "\n")
   607  	print("	g.stack.hi=", hex(g.stack.hi), ", g.stack.lo", hex(g.stack.lo), ", g.stackguard0=", hex(g.stackguard0), ", g.stackguard1=", hex(g.stackguard1), "\n")
   608  	print("	callersp=", hex(getcallersp(unsafe.Pointer(&g))), "\n")
   609  }