rsc.io/go@v0.0.0-20150416155037-e040fd465409/src/runtime/sigqueue_plan9.go (about) 1 // Copyright 2009 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 // This file implements runtime support for signal handling. 6 7 package runtime 8 9 const qsize = 64 10 11 var sig struct { 12 q noteQueue 13 inuse bool 14 15 lock mutex 16 note note 17 sleeping bool 18 } 19 20 type noteQueue struct { 21 lock mutex 22 data [qsize]*byte 23 ri int 24 wi int 25 full bool 26 } 27 28 func (q *noteQueue) push(item *byte) bool { 29 lock(&q.lock) 30 if q.full { 31 unlock(&q.lock) 32 return false 33 } 34 q.data[q.wi] = item 35 q.wi++ 36 if q.wi == qsize { 37 q.wi = 0 38 } 39 if q.wi == q.ri { 40 q.full = true 41 } 42 unlock(&q.lock) 43 return true 44 } 45 46 func (q *noteQueue) pop() *byte { 47 lock(&q.lock) 48 q.full = false 49 if q.ri == q.wi { 50 unlock(&q.lock) 51 return nil 52 } 53 item := q.data[q.ri] 54 q.ri++ 55 if q.ri == qsize { 56 q.ri = 0 57 } 58 unlock(&q.lock) 59 return item 60 } 61 62 // Called from sighandler to send a signal back out of the signal handling thread. 63 // Reports whether the signal was sent. If not, the caller typically crashes the program. 64 func sendNote(s *byte) bool { 65 if !sig.inuse { 66 return false 67 } 68 69 // Add signal to outgoing queue. 70 if !sig.q.push(s) { 71 return false 72 } 73 74 lock(&sig.lock) 75 if sig.sleeping { 76 sig.sleeping = false 77 notewakeup(&sig.note) 78 } 79 unlock(&sig.lock) 80 81 return true 82 } 83 84 // Called to receive the next queued signal. 85 // Must only be called from a single goroutine at a time. 86 func signal_recv() string { 87 for { 88 note := sig.q.pop() 89 if note != nil { 90 return gostring(note) 91 } 92 93 lock(&sig.lock) 94 sig.sleeping = true 95 noteclear(&sig.note) 96 unlock(&sig.lock) 97 notetsleepg(&sig.note, -1) 98 } 99 } 100 101 // Must only be called from a single goroutine at a time. 102 func signal_enable(s uint32) { 103 if !sig.inuse { 104 // The first call to signal_enable is for us 105 // to use for initialization. It does not pass 106 // signal information in m. 107 sig.inuse = true // enable reception of signals; cannot disable 108 noteclear(&sig.note) 109 return 110 } 111 } 112 113 // Must only be called from a single goroutine at a time. 114 func signal_disable(s uint32) { 115 } 116 117 // Must only be called from a single goroutine at a time. 118 func signal_ignore(s uint32) { 119 }