default_handler.go 6.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322
  1. package dbus
  2. import (
  3. "bytes"
  4. "reflect"
  5. "strings"
  6. "sync"
  7. )
  8. func newIntrospectIntf(h *defaultHandler) *exportedIntf {
  9. methods := make(map[string]Method)
  10. methods["Introspect"] = exportedMethod{
  11. reflect.ValueOf(func(msg Message) (string, *Error) {
  12. path := msg.Headers[FieldPath].value.(ObjectPath)
  13. return h.introspectPath(path), nil
  14. }),
  15. }
  16. return newExportedIntf(methods, true)
  17. }
  18. //NewDefaultHandler returns an instance of the default
  19. //call handler. This is useful if you want to implement only
  20. //one of the two handlers but not both.
  21. //
  22. // Deprecated: this is the default value, don't use it, it will be unexported.
  23. func NewDefaultHandler() *defaultHandler {
  24. h := &defaultHandler{
  25. objects: make(map[ObjectPath]*exportedObj),
  26. defaultIntf: make(map[string]*exportedIntf),
  27. }
  28. h.defaultIntf["org.freedesktop.DBus.Introspectable"] = newIntrospectIntf(h)
  29. return h
  30. }
  31. type defaultHandler struct {
  32. sync.RWMutex
  33. objects map[ObjectPath]*exportedObj
  34. defaultIntf map[string]*exportedIntf
  35. }
  36. func (h *defaultHandler) PathExists(path ObjectPath) bool {
  37. _, ok := h.objects[path]
  38. return ok
  39. }
  40. func (h *defaultHandler) introspectPath(path ObjectPath) string {
  41. subpath := make(map[string]struct{})
  42. var xml bytes.Buffer
  43. xml.WriteString("<node>")
  44. for obj, _ := range h.objects {
  45. p := string(path)
  46. if p != "/" {
  47. p += "/"
  48. }
  49. if strings.HasPrefix(string(obj), p) {
  50. node_name := strings.Split(string(obj[len(p):]), "/")[0]
  51. subpath[node_name] = struct{}{}
  52. }
  53. }
  54. for s, _ := range subpath {
  55. xml.WriteString("\n\t<node name=\"" + s + "\"/>")
  56. }
  57. xml.WriteString("\n</node>")
  58. return xml.String()
  59. }
  60. func (h *defaultHandler) LookupObject(path ObjectPath) (ServerObject, bool) {
  61. h.RLock()
  62. defer h.RUnlock()
  63. object, ok := h.objects[path]
  64. if ok {
  65. return object, ok
  66. }
  67. // If an object wasn't found for this exact path,
  68. // look for a matching subtree registration
  69. subtreeObject := newExportedObject()
  70. path = path[:strings.LastIndex(string(path), "/")]
  71. for len(path) > 0 {
  72. object, ok = h.objects[path]
  73. if ok {
  74. for name, iface := range object.interfaces {
  75. // Only include this handler if it registered for the subtree
  76. if iface.isFallbackInterface() {
  77. subtreeObject.interfaces[name] = iface
  78. }
  79. }
  80. break
  81. }
  82. path = path[:strings.LastIndex(string(path), "/")]
  83. }
  84. for name, intf := range h.defaultIntf {
  85. if _, exists := subtreeObject.interfaces[name]; exists {
  86. continue
  87. }
  88. subtreeObject.interfaces[name] = intf
  89. }
  90. return subtreeObject, true
  91. }
  92. func (h *defaultHandler) AddObject(path ObjectPath, object *exportedObj) {
  93. h.Lock()
  94. h.objects[path] = object
  95. h.Unlock()
  96. }
  97. func (h *defaultHandler) DeleteObject(path ObjectPath) {
  98. h.Lock()
  99. delete(h.objects, path)
  100. h.Unlock()
  101. }
  102. type exportedMethod struct {
  103. reflect.Value
  104. }
  105. func (m exportedMethod) Call(args ...interface{}) ([]interface{}, error) {
  106. t := m.Type()
  107. params := make([]reflect.Value, len(args))
  108. for i := 0; i < len(args); i++ {
  109. params[i] = reflect.ValueOf(args[i]).Elem()
  110. }
  111. ret := m.Value.Call(params)
  112. err := ret[t.NumOut()-1].Interface().(*Error)
  113. ret = ret[:t.NumOut()-1]
  114. out := make([]interface{}, len(ret))
  115. for i, val := range ret {
  116. out[i] = val.Interface()
  117. }
  118. if err == nil {
  119. //concrete type to interface nil is a special case
  120. return out, nil
  121. }
  122. return out, err
  123. }
  124. func (m exportedMethod) NumArguments() int {
  125. return m.Value.Type().NumIn()
  126. }
  127. func (m exportedMethod) ArgumentValue(i int) interface{} {
  128. return reflect.Zero(m.Type().In(i)).Interface()
  129. }
  130. func (m exportedMethod) NumReturns() int {
  131. return m.Value.Type().NumOut()
  132. }
  133. func (m exportedMethod) ReturnValue(i int) interface{} {
  134. return reflect.Zero(m.Type().Out(i)).Interface()
  135. }
  136. func newExportedObject() *exportedObj {
  137. return &exportedObj{
  138. interfaces: make(map[string]*exportedIntf),
  139. }
  140. }
  141. type exportedObj struct {
  142. mu sync.RWMutex
  143. interfaces map[string]*exportedIntf
  144. }
  145. func (obj *exportedObj) LookupInterface(name string) (Interface, bool) {
  146. if name == "" {
  147. return obj, true
  148. }
  149. obj.mu.RLock()
  150. defer obj.mu.RUnlock()
  151. intf, exists := obj.interfaces[name]
  152. return intf, exists
  153. }
  154. func (obj *exportedObj) AddInterface(name string, iface *exportedIntf) {
  155. obj.mu.Lock()
  156. defer obj.mu.Unlock()
  157. obj.interfaces[name] = iface
  158. }
  159. func (obj *exportedObj) DeleteInterface(name string) {
  160. obj.mu.Lock()
  161. defer obj.mu.Unlock()
  162. delete(obj.interfaces, name)
  163. }
  164. func (obj *exportedObj) LookupMethod(name string) (Method, bool) {
  165. obj.mu.RLock()
  166. defer obj.mu.RUnlock()
  167. for _, intf := range obj.interfaces {
  168. method, exists := intf.LookupMethod(name)
  169. if exists {
  170. return method, exists
  171. }
  172. }
  173. return nil, false
  174. }
  175. func (obj *exportedObj) isFallbackInterface() bool {
  176. return false
  177. }
  178. func newExportedIntf(methods map[string]Method, includeSubtree bool) *exportedIntf {
  179. return &exportedIntf{
  180. methods: methods,
  181. includeSubtree: includeSubtree,
  182. }
  183. }
  184. type exportedIntf struct {
  185. methods map[string]Method
  186. // Whether or not this export is for the entire subtree
  187. includeSubtree bool
  188. }
  189. func (obj *exportedIntf) LookupMethod(name string) (Method, bool) {
  190. out, exists := obj.methods[name]
  191. return out, exists
  192. }
  193. func (obj *exportedIntf) isFallbackInterface() bool {
  194. return obj.includeSubtree
  195. }
  196. //NewDefaultSignalHandler returns an instance of the default
  197. //signal handler. This is useful if you want to implement only
  198. //one of the two handlers but not both.
  199. //
  200. // Deprecated: this is the default value, don't use it, it will be unexported.
  201. func NewDefaultSignalHandler() *defaultSignalHandler {
  202. return &defaultSignalHandler{
  203. closeChan: make(chan struct{}),
  204. }
  205. }
  206. func isDefaultSignalHandler(handler SignalHandler) bool {
  207. _, ok := handler.(*defaultSignalHandler)
  208. return ok
  209. }
  210. type defaultSignalHandler struct {
  211. sync.RWMutex
  212. closed bool
  213. signals []chan<- *Signal
  214. closeChan chan struct{}
  215. }
  216. func (sh *defaultSignalHandler) DeliverSignal(intf, name string, signal *Signal) {
  217. sh.RLock()
  218. defer sh.RUnlock()
  219. if sh.closed {
  220. return
  221. }
  222. for _, ch := range sh.signals {
  223. select {
  224. case ch <- signal:
  225. case <-sh.closeChan:
  226. return
  227. default:
  228. go func() {
  229. select {
  230. case ch <- signal:
  231. case <-sh.closeChan:
  232. return
  233. }
  234. }()
  235. }
  236. }
  237. }
  238. func (sh *defaultSignalHandler) Init() error {
  239. sh.Lock()
  240. sh.signals = make([]chan<- *Signal, 0)
  241. sh.closeChan = make(chan struct{})
  242. sh.Unlock()
  243. return nil
  244. }
  245. func (sh *defaultSignalHandler) Terminate() {
  246. sh.Lock()
  247. if !sh.closed {
  248. close(sh.closeChan)
  249. }
  250. sh.closed = true
  251. for _, ch := range sh.signals {
  252. close(ch)
  253. }
  254. sh.signals = nil
  255. sh.Unlock()
  256. }
  257. func (sh *defaultSignalHandler) addSignal(ch chan<- *Signal) {
  258. sh.Lock()
  259. defer sh.Unlock()
  260. if sh.closed {
  261. return
  262. }
  263. sh.signals = append(sh.signals, ch)
  264. }
  265. func (sh *defaultSignalHandler) removeSignal(ch chan<- *Signal) {
  266. sh.Lock()
  267. defer sh.Unlock()
  268. if sh.closed {
  269. return
  270. }
  271. for i := len(sh.signals) - 1; i >= 0; i-- {
  272. if ch == sh.signals[i] {
  273. copy(sh.signals[i:], sh.signals[i+1:])
  274. sh.signals[len(sh.signals)-1] = nil
  275. sh.signals = sh.signals[:len(sh.signals)-1]
  276. }
  277. }
  278. }