* typeck2.c (cxx_incomplete_type_diagnostic): Revert change and
[official-gcc.git] / libgo / go / runtime / signal_unix.go
blobc8713b6770ac0f5632075ebfe50f1e55051f523d
1 // Copyright 2012 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.
5 // +build aix darwin dragonfly freebsd linux netbsd openbsd solaris
7 package runtime
9 import (
10 "runtime/internal/sys"
11 "unsafe"
14 // For gccgo's C code to call:
15 //go:linkname initsig runtime.initsig
16 //go:linkname crash runtime.crash
17 //go:linkname resetcpuprofiler runtime.resetcpuprofiler
18 //go:linkname sigtrampgo runtime.sigtrampgo
20 //go:linkname os_sigpipe os.sigpipe
21 func os_sigpipe() {
22 systemstack(sigpipe)
25 func signame(sig uint32) string {
26 if sig >= uint32(len(sigtable)) {
27 return ""
29 return sigtable[sig].name
32 const (
33 _SIG_DFL uintptr = 0
34 _SIG_IGN uintptr = 1
37 // Stores the signal handlers registered before Go installed its own.
38 // These signal handlers will be invoked in cases where Go doesn't want to
39 // handle a particular signal (e.g., signal occurred on a non-Go thread).
40 // See sigfwdgo() for more information on when the signals are forwarded.
42 // Signal forwarding is currently available only on Darwin and Linux.
43 var fwdSig [_NSIG]uintptr
45 // channels for synchronizing signal mask updates with the signal mask
46 // thread
47 var (
48 disableSigChan chan uint32
49 enableSigChan chan uint32
50 maskUpdatedChan chan struct{}
53 func init() {
54 // _NSIG is the number of signals on this operating system.
55 // sigtable should describe what to do for all the possible signals.
56 if len(sigtable) != _NSIG {
57 print("runtime: len(sigtable)=", len(sigtable), " _NSIG=", _NSIG, "\n")
58 throw("bad sigtable len")
62 var signalsOK bool
64 // Initialize signals.
65 // Called by libpreinit so runtime may not be initialized.
66 //go:nosplit
67 //go:nowritebarrierrec
68 func initsig(preinit bool) {
69 if preinit {
70 // preinit is only passed as true if isarchive should be true.
71 isarchive = true
74 if !preinit {
75 // It's now OK for signal handlers to run.
76 signalsOK = true
79 // For c-archive/c-shared this is called by libpreinit with
80 // preinit == true.
81 if (isarchive || islibrary) && !preinit {
82 return
85 for i := uint32(0); i < _NSIG; i++ {
86 t := &sigtable[i]
87 if t.flags == 0 || t.flags&_SigDefault != 0 {
88 continue
90 fwdSig[i] = getsig(i)
92 if !sigInstallGoHandler(i) {
93 // Even if we are not installing a signal handler,
94 // set SA_ONSTACK if necessary.
95 if fwdSig[i] != _SIG_DFL && fwdSig[i] != _SIG_IGN {
96 setsigstack(i)
98 continue
101 t.flags |= _SigHandling
102 setsig(i, getSigtramp())
106 //go:nosplit
107 //go:nowritebarrierrec
108 func sigInstallGoHandler(sig uint32) bool {
109 // For some signals, we respect an inherited SIG_IGN handler
110 // rather than insist on installing our own default handler.
111 // Even these signals can be fetched using the os/signal package.
112 switch sig {
113 case _SIGHUP, _SIGINT:
114 if fwdSig[sig] == _SIG_IGN {
115 return false
119 t := &sigtable[sig]
120 if t.flags&_SigSetStack != 0 {
121 return false
124 // When built using c-archive or c-shared, only install signal
125 // handlers for synchronous signals.
126 if (isarchive || islibrary) && t.flags&_SigPanic == 0 {
127 return false
130 return true
133 func sigenable(sig uint32) {
134 if sig >= uint32(len(sigtable)) {
135 return
138 t := &sigtable[sig]
139 if t.flags&_SigNotify != 0 {
140 ensureSigM()
141 enableSigChan <- sig
142 <-maskUpdatedChan
143 if t.flags&_SigHandling == 0 {
144 t.flags |= _SigHandling
145 fwdSig[sig] = getsig(sig)
146 setsig(sig, getSigtramp())
151 func sigdisable(sig uint32) {
152 if sig >= uint32(len(sigtable)) {
153 return
156 t := &sigtable[sig]
157 if t.flags&_SigNotify != 0 {
158 ensureSigM()
159 disableSigChan <- sig
160 <-maskUpdatedChan
162 // If initsig does not install a signal handler for a
163 // signal, then to go back to the state before Notify
164 // we should remove the one we installed.
165 if !sigInstallGoHandler(sig) {
166 t.flags &^= _SigHandling
167 setsig(sig, fwdSig[sig])
172 func sigignore(sig uint32) {
173 if sig >= uint32(len(sigtable)) {
174 return
177 t := &sigtable[sig]
178 if t.flags&_SigNotify != 0 {
179 t.flags &^= _SigHandling
180 setsig(sig, _SIG_IGN)
184 func resetcpuprofiler(hz int32) {
185 var it _itimerval
186 if hz == 0 {
187 setitimer(_ITIMER_PROF, &it, nil)
188 } else {
189 it.it_interval.tv_sec = 0
190 it.it_interval.set_usec(1000000 / hz)
191 it.it_value = it.it_interval
192 setitimer(_ITIMER_PROF, &it, nil)
194 _g_ := getg()
195 _g_.m.profilehz = hz
198 func sigpipe() {
199 if sigsend(_SIGPIPE) {
200 return
202 dieFromSignal(_SIGPIPE)
205 // sigtrampgo is called from the signal handler function, sigtramp,
206 // written in assembly code.
207 // This is called by the signal handler, and the world may be stopped.
208 //go:nosplit
209 //go:nowritebarrierrec
210 func sigtrampgo(sig uint32, info *_siginfo_t, ctx unsafe.Pointer) {
211 if sigfwdgo(sig, info, ctx) {
212 return
214 g := getg()
215 if g == nil {
216 c := sigctxt{info, ctx}
217 if sig == _SIGPROF {
218 _, pc := getSiginfo(info, ctx)
219 sigprofNonGo(pc)
220 return
222 badsignal(uintptr(sig), &c)
223 return
226 setg(g.m.gsignal)
227 sighandler(sig, info, ctx, g)
228 setg(g)
231 // sigpanic turns a synchronous signal into a run-time panic.
232 // If the signal handler sees a synchronous panic, it arranges the
233 // stack to look like the function where the signal occurred called
234 // sigpanic, sets the signal's PC value to sigpanic, and returns from
235 // the signal handler. The effect is that the program will act as
236 // though the function that got the signal simply called sigpanic
237 // instead.
238 func sigpanic() {
239 g := getg()
240 if !canpanic(g) {
241 throw("unexpected signal during runtime execution")
244 switch g.sig {
245 case _SIGBUS:
246 if g.sigcode0 == _BUS_ADRERR && g.sigcode1 < 0x1000 {
247 panicmem()
249 // Support runtime/debug.SetPanicOnFault.
250 if g.paniconfault {
251 panicmem()
253 print("unexpected fault address ", hex(g.sigcode1), "\n")
254 throw("fault")
255 case _SIGSEGV:
256 if (g.sigcode0 == 0 || g.sigcode0 == _SEGV_MAPERR || g.sigcode0 == _SEGV_ACCERR) && g.sigcode1 < 0x1000 {
257 panicmem()
259 // Support runtime/debug.SetPanicOnFault.
260 if g.paniconfault {
261 panicmem()
263 print("unexpected fault address ", hex(g.sigcode1), "\n")
264 throw("fault")
265 case _SIGFPE:
266 switch g.sigcode0 {
267 case _FPE_INTDIV:
268 panicdivide()
269 case _FPE_INTOVF:
270 panicoverflow()
272 panicfloat()
275 if g.sig >= uint32(len(sigtable)) {
276 // can't happen: we looked up g.sig in sigtable to decide to call sigpanic
277 throw("unexpected signal value")
279 panic(errorString(sigtable[g.sig].name))
282 // dieFromSignal kills the program with a signal.
283 // This provides the expected exit status for the shell.
284 // This is only called with fatal signals expected to kill the process.
285 //go:nosplit
286 //go:nowritebarrierrec
287 func dieFromSignal(sig uint32) {
288 setsig(sig, _SIG_DFL)
289 unblocksig(sig)
290 raise(sig)
292 // That should have killed us. On some systems, though, raise
293 // sends the signal to the whole process rather than to just
294 // the current thread, which means that the signal may not yet
295 // have been delivered. Give other threads a chance to run and
296 // pick up the signal.
297 osyield()
298 osyield()
299 osyield()
301 // If we are still somehow running, just exit with the wrong status.
302 exit(2)
305 // raisebadsignal is called when a signal is received on a non-Go
306 // thread, and the Go program does not want to handle it (that is, the
307 // program has not called os/signal.Notify for the signal).
308 func raisebadsignal(sig uint32, c *sigctxt) {
309 if sig == _SIGPROF {
310 // Ignore profiling signals that arrive on non-Go threads.
311 return
314 var handler uintptr
315 if sig >= _NSIG {
316 handler = _SIG_DFL
317 } else {
318 handler = fwdSig[sig]
321 // Reset the signal handler and raise the signal.
322 // We are currently running inside a signal handler, so the
323 // signal is blocked. We need to unblock it before raising the
324 // signal, or the signal we raise will be ignored until we return
325 // from the signal handler. We know that the signal was unblocked
326 // before entering the handler, or else we would not have received
327 // it. That means that we don't have to worry about blocking it
328 // again.
329 unblocksig(sig)
330 setsig(sig, handler)
332 // If we're linked into a non-Go program we want to try to
333 // avoid modifying the original context in which the signal
334 // was raised. If the handler is the default, we know it
335 // is non-recoverable, so we don't have to worry about
336 // re-installing sighandler. At this point we can just
337 // return and the signal will be re-raised and caught by
338 // the default handler with the correct context.
339 if (isarchive || islibrary) && handler == _SIG_DFL && c.sigcode() != _SI_USER {
340 return
343 raise(sig)
345 // Give the signal a chance to be delivered.
346 // In almost all real cases the program is about to crash,
347 // so sleeping here is not a waste of time.
348 usleep(1000)
350 // If the signal didn't cause the program to exit, restore the
351 // Go signal handler and carry on.
353 // We may receive another instance of the signal before we
354 // restore the Go handler, but that is not so bad: we know
355 // that the Go program has been ignoring the signal.
356 setsig(sig, getSigtramp())
359 func crash() {
360 if GOOS == "darwin" {
361 // OS X core dumps are linear dumps of the mapped memory,
362 // from the first virtual byte to the last, with zeros in the gaps.
363 // Because of the way we arrange the address space on 64-bit systems,
364 // this means the OS X core file will be >128 GB and even on a zippy
365 // workstation can take OS X well over an hour to write (uninterruptible).
366 // Save users from making that mistake.
367 if sys.PtrSize == 8 {
368 return
372 dieFromSignal(_SIGABRT)
375 // ensureSigM starts one global, sleeping thread to make sure at least one thread
376 // is available to catch signals enabled for os/signal.
377 func ensureSigM() {
378 if maskUpdatedChan != nil {
379 return
381 maskUpdatedChan = make(chan struct{})
382 disableSigChan = make(chan uint32)
383 enableSigChan = make(chan uint32)
384 go func() {
385 // Signal masks are per-thread, so make sure this goroutine stays on one
386 // thread.
387 LockOSThread()
388 defer UnlockOSThread()
389 // The sigBlocked mask contains the signals not active for os/signal,
390 // initially all signals except the essential. When signal.Notify()/Stop is called,
391 // sigenable/sigdisable in turn notify this thread to update its signal
392 // mask accordingly.
393 var sigBlocked sigset
394 sigfillset(&sigBlocked)
395 for i := range sigtable {
396 if sigtable[i].flags&_SigUnblock != 0 {
397 sigdelset(&sigBlocked, i)
400 sigprocmask(_SIG_SETMASK, &sigBlocked, nil)
401 for {
402 select {
403 case sig := <-enableSigChan:
404 if sig > 0 {
405 sigdelset(&sigBlocked, int(sig))
407 case sig := <-disableSigChan:
408 if sig > 0 {
409 sigaddset(&sigBlocked, int(sig))
412 sigprocmask(_SIG_SETMASK, &sigBlocked, nil)
413 maskUpdatedChan <- struct{}{}
418 // This is called when we receive a signal when there is no signal stack.
419 // This can only happen if non-Go code calls sigaltstack to disable the
420 // signal stack.
421 func noSignalStack(sig uint32) {
422 println("signal", sig, "received on thread with no signal stack")
423 throw("non-Go code disabled sigaltstack")
426 // This is called if we receive a signal when there is a signal stack
427 // but we are not on it. This can only happen if non-Go code called
428 // sigaction without setting the SS_ONSTACK flag.
429 func sigNotOnStack(sig uint32) {
430 println("signal", sig, "received but handler not on signal stack")
431 throw("non-Go code set up signal handler without SA_ONSTACK flag")
434 // This runs on a foreign stack, without an m or a g. No stack split.
435 //go:nosplit
436 //go:norace
437 //go:nowritebarrierrec
438 func badsignal(sig uintptr, c *sigctxt) {
439 needm(0)
440 if !sigsend(uint32(sig)) {
441 // A foreign thread received the signal sig, and the
442 // Go code does not want to handle it.
443 raisebadsignal(uint32(sig), c)
445 dropm()
448 // Determines if the signal should be handled by Go and if not, forwards the
449 // signal to the handler that was installed before Go's. Returns whether the
450 // signal was forwarded.
451 // This is called by the signal handler, and the world may be stopped.
452 //go:nosplit
453 //go:nowritebarrierrec
454 func sigfwdgo(sig uint32, info *_siginfo_t, ctx unsafe.Pointer) bool {
455 if sig >= uint32(len(sigtable)) {
456 return false
458 fwdFn := fwdSig[sig]
460 if !signalsOK {
461 // The only way we can get here is if we are in a
462 // library or archive, we installed a signal handler
463 // at program startup, but the Go runtime has not yet
464 // been initialized.
465 if fwdFn == _SIG_DFL {
466 dieFromSignal(sig)
467 } else {
468 sigfwd(fwdFn, sig, info, ctx)
470 return true
473 flags := sigtable[sig].flags
475 // If there is no handler to forward to, no need to forward.
476 if fwdFn == _SIG_DFL {
477 return false
480 // If we aren't handling the signal, forward it.
481 if flags&_SigHandling == 0 {
482 sigfwd(fwdFn, sig, info, ctx)
483 return true
486 // Only forward synchronous signals.
487 c := sigctxt{info, ctx}
488 if c.sigcode() == _SI_USER || flags&_SigPanic == 0 {
489 return false
491 // Determine if the signal occurred inside Go code. We test that:
492 // (1) we were in a goroutine (i.e., m.curg != nil), and
493 // (2) we weren't in CGO (i.e., m.curg.syscallsp == 0).
494 g := getg()
495 if g != nil && g.m != nil && g.m.curg != nil && g.m.curg.syscallsp == 0 {
496 return false
498 // Signal not handled by Go, forward it.
499 if fwdFn != _SIG_IGN {
500 sigfwd(fwdFn, sig, info, ctx)
502 return true
505 // msigsave saves the current thread's signal mask into mp.sigmask.
506 // This is used to preserve the non-Go signal mask when a non-Go
507 // thread calls a Go function.
508 // This is nosplit and nowritebarrierrec because it is called by needm
509 // which may be called on a non-Go thread with no g available.
510 //go:nosplit
511 //go:nowritebarrierrec
512 func msigsave(mp *m) {
513 sigprocmask(_SIG_SETMASK, nil, &mp.sigmask)
516 // msigrestore sets the current thread's signal mask to sigmask.
517 // This is used to restore the non-Go signal mask when a non-Go thread
518 // calls a Go function.
519 // This is nosplit and nowritebarrierrec because it is called by dropm
520 // after g has been cleared.
521 //go:nosplit
522 //go:nowritebarrierrec
523 func msigrestore(sigmask sigset) {
524 sigprocmask(_SIG_SETMASK, &sigmask, nil)
527 // sigblock blocks all signals in the current thread's signal mask.
528 // This is used to block signals while setting up and tearing down g
529 // when a non-Go thread calls a Go function.
530 // The OS-specific code is expected to define sigset_all.
531 // This is nosplit and nowritebarrierrec because it is called by needm
532 // which may be called on a non-Go thread with no g available.
533 //go:nosplit
534 //go:nowritebarrierrec
535 func sigblock() {
536 var set sigset
537 sigfillset(&set)
538 sigprocmask(_SIG_SETMASK, &set, nil)
541 // unblocksig removes sig from the current thread's signal mask.
542 // This is nosplit and nowritebarrierrec because it is called from
543 // dieFromSignal, which can be called by sigfwdgo while running in the
544 // signal handler, on the signal stack, with no g available.
545 //go:nosplit
546 //go:nowritebarrierrec
547 func unblocksig(sig uint32) {
548 var set sigset
549 sigemptyset(&set)
550 sigaddset(&set, int(sig))
551 sigprocmask(_SIG_UNBLOCK, &set, nil)
554 // minitSignals is called when initializing a new m to set the
555 // thread's alternate signal stack and signal mask.
556 func minitSignals() {
557 minitSignalStack()
558 minitSignalMask()
561 // minitSignalStack is called when initializing a new m to set the
562 // alternate signal stack. If the alternate signal stack is not set
563 // for the thread (the normal case) then set the alternate signal
564 // stack to the gsignal stack. If the alternate signal stack is set
565 // for the thread (the case when a non-Go thread sets the alternate
566 // signal stack and then calls a Go function) then set the gsignal
567 // stack to the alternate signal stack. Record which choice was made
568 // in newSigstack, so that it can be undone in unminit.
569 func minitSignalStack() {
570 _g_ := getg()
571 var st _stack_t
572 sigaltstack(nil, &st)
573 if st.ss_flags&_SS_DISABLE != 0 {
574 signalstack(_g_.m.gsignalstack, _g_.m.gsignalstacksize)
575 _g_.m.newSigstack = true
576 } else {
577 _g_.m.newSigstack = false
581 // minitSignalMask is called when initializing a new m to set the
582 // thread's signal mask. When this is called all signals have been
583 // blocked for the thread. This starts with m.sigmask, which was set
584 // either from initSigmask for a newly created thread or by calling
585 // msigsave if this is a non-Go thread calling a Go function. It
586 // removes all essential signals from the mask, thus causing those
587 // signals to not be blocked. Then it sets the thread's signal mask.
588 // After this is called the thread can receive signals.
589 func minitSignalMask() {
590 nmask := getg().m.sigmask
591 for i := range sigtable {
592 if sigtable[i].flags&_SigUnblock != 0 {
593 sigdelset(&nmask, i)
596 sigprocmask(_SIG_SETMASK, &nmask, nil)
599 // unminitSignals is called from dropm, via unminit, to undo the
600 // effect of calling minit on a non-Go thread.
601 //go:nosplit
602 func unminitSignals() {
603 if getg().m.newSigstack {
604 signalstack(nil, 0)