* builtins.def (BUILT_IN_SETJMP): Revert latest change.
[official-gcc.git] / libgo / go / runtime / signal_gccgo.go
blob056be36a729716c739a1a3415b37e8938852a405
1 // Copyright 2016 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 "unsafe"
13 // Functions for gccgo to support signal handling. In the gc runtime
14 // these are written in OS-specific files and in assembler.
16 //extern sigaction
17 func sigaction(signum uint32, act *_sigaction, oact *_sigaction) int32
19 //extern sigprocmask
20 func sigprocmask(how int32, set *sigset, oldset *sigset) int32
22 //extern sigfillset
23 func sigfillset(set *sigset) int32
25 //extern sigemptyset
26 func sigemptyset(set *sigset) int32
28 //extern sigaddset
29 func c_sigaddset(set *sigset, signum uint32) int32
31 //extern sigdelset
32 func c_sigdelset(set *sigset, signum uint32) int32
34 //extern sigaltstack
35 func sigaltstack(ss *_stack_t, oss *_stack_t) int32
37 //extern raise
38 func raise(sig uint32) int32
40 //extern getpid
41 func getpid() _pid_t
43 //extern kill
44 func kill(pid _pid_t, sig uint32) int32
46 //extern setitimer
47 func setitimer(which int32, new *_itimerval, old *_itimerval) int32
49 type sigTabT struct {
50 flags int32
51 name string
54 type sigctxt struct {
55 info *_siginfo_t
56 ctxt unsafe.Pointer
59 func (c *sigctxt) sigcode() uint64 {
60 if c.info == nil {
61 // This can happen on Solaris 10. We don't know the
62 // code, just avoid a misleading value.
63 return _SI_USER + 1
65 return uint64(c.info.si_code)
68 //go:nosplit
69 //go:nowritebarrierrec
70 func setsig(i uint32, fn uintptr) {
71 var sa _sigaction
72 sa.sa_flags = _SA_SIGINFO | _SA_RESTART
74 // For gccgo we do not set SA_ONSTACK for a signal that can
75 // cause a panic. Instead, we trust that the split stack has
76 // enough room to start the signal handler. This is because
77 // otherwise we have no good way to switch back to the
78 // original stack before panicing.
79 if sigtable[i].flags&_SigPanic == 0 {
80 sa.sa_flags |= _SA_ONSTACK
83 sigfillset((*sigset)(unsafe.Pointer(&sa.sa_mask)))
84 setSigactionHandler(&sa, fn)
85 sigaction(i, &sa, nil)
88 //go:nosplit
89 //go:nowritebarrierrec
90 func setsigstack(i uint32) {
91 var sa _sigaction
92 sigaction(i, nil, &sa)
93 handler := getSigactionHandler(&sa)
94 if handler == 0 || handler == _SIG_DFL || handler == _SIG_IGN || sa.sa_flags&_SA_ONSTACK != 0 {
95 return
97 if sigtable[i].flags&_SigPanic != 0 {
98 return
100 sa.sa_flags |= _SA_ONSTACK
101 sigaction(i, &sa, nil)
104 //go:nosplit
105 //go:nowritebarrierrec
106 func getsig(i uint32) uintptr {
107 var sa _sigaction
108 if sigaction(i, nil, &sa) < 0 {
109 // On GNU/Linux glibc rejects attempts to call
110 // sigaction with signal 32 (SIGCANCEL) or 33 (SIGSETXID).
111 if GOOS == "linux" && (i == 32 || i == 33) {
112 return _SIG_DFL
114 throw("sigaction read failure")
116 return getSigactionHandler(&sa)
119 func signalstack(p unsafe.Pointer, n uintptr)
121 //go:nosplit
122 //go:nowritebarrierrec
123 func raiseproc(sig uint32) {
124 kill(getpid(), sig)
127 //go:nosplit
128 //go:nowritebarrierrec
129 func sigfwd(fn uintptr, sig uint32, info *_siginfo_t, ctx unsafe.Pointer) {
130 f1 := [1]uintptr{fn}
131 f2 := &f1
132 f3 := *(*func(uint32, *_siginfo_t, unsafe.Pointer))(unsafe.Pointer(&f2))
133 f3(sig, info, ctx)
136 //go:nosplit
137 //go:nowritebarrierrec
138 func sigaddset(mask *sigset, i int) {
139 c_sigaddset(mask, uint32(i))
142 func sigdelset(mask *sigset, i int) {
143 c_sigdelset(mask, uint32(i))