pangdudu-ruby-dbus 0.2.2 → 0.2.3

Sign up to get free protection for your applications and to get access to all the features.
data/README CHANGED
@@ -38,6 +38,7 @@ Ruby D-Bus currently supports the following features:
38
38
  * Rubyish D-Bus object and interface syntax support that automatically
39
39
  allows for introspection.
40
40
  * Emitting signals on exported objects.
41
+ * Connection to a local or remote bus over TCP/IP
41
42
 
42
43
  == Usage
43
44
 
data/lib/dbus/auth.rb CHANGED
@@ -33,8 +33,62 @@ module DBus
33
33
  return Process.uid.to_s.split(//).collect { |a| "%x" % a[0] }.join
34
34
  end
35
35
  end
36
+
37
+ # = Authentication class using SHA1 crypto algorithm
38
+ #
39
+ # Class for 'CookieSHA1' type authentication.
40
+ # Implements the AUTH DBUS_COOKIE_SHA1 mechanism.
41
+ class DBusCookieSHA1 < Authenticator
42
+
43
+ #the autenticate method (called in stage one of authentification)
44
+ def authenticate
45
+ require 'etc'
46
+ return "#{hex_encode(Etc.getlogin)}" #server expects it to be binary
47
+ end
36
48
 
37
- # Note: this following stuff is tested with External authenticator only!
49
+ #returns the modules name
50
+ def name
51
+ return 'DBUS_COOKIE_SHA1'
52
+ end
53
+
54
+ #handles the interesting crypto stuff, check the rbus-project for more info: http://rbus.rubyforge.org/
55
+ def data(hexdata)
56
+ require 'digest/sha1'
57
+ data = hex_decode(hexdata)
58
+ # name of cookie file, id of cookie in file, servers random challenge
59
+ context, id, s_challenge = data.split(' ')
60
+ # Random client challenge
61
+ c_challenge = Array.new(s_challenge.length/2).map{|obj|obj=rand(255).to_s}.join
62
+ # Search cookie file for id
63
+ path = File.join(ENV['HOME'], '.dbus-keyrings', context)
64
+ File.foreach(path) do |line|
65
+ if line.index(id) == 0
66
+ # Right line of file, read cookie
67
+ cookie = line.split(' ')[2].chomp
68
+ # Concatenate and encrypt
69
+ to_encrypt = [s_challenge, c_challenge, cookie].join(':')
70
+ sha = Digest::SHA1.hexdigest(to_encrypt)
71
+ #the almighty tcp server wants everything hex encoded
72
+ hex_response = hex_encode("#{c_challenge} #{sha}")
73
+ # Return response
74
+ response = [:AuthOk, hex_response]
75
+ return response
76
+ end
77
+ end
78
+ raise AuthException, 'Unable to locate cookie'
79
+ end
80
+
81
+ # encode plain to hex
82
+ def hex_encode(plain)
83
+ return nil if plain.nil?
84
+ plain.to_s.unpack('H*')[0]
85
+ end
86
+
87
+ # decode hex to plain
88
+ def hex_decode(encoded)
89
+ encoded.scan(/[[:xdigit:]]{2}/).map{|h|h.hex.chr}.join
90
+ end
91
+ end #DBusCookieSHA1 class ends here
38
92
 
39
93
  # = Authentication client class.
40
94
  #
@@ -44,7 +98,7 @@ module DBus
44
98
  def initialize(socket)
45
99
  @socket = socket
46
100
  @state = nil
47
- @auth_list = [External]
101
+ @auth_list = [External,DBusCookieSHA1]
48
102
  end
49
103
 
50
104
  # Start the authentication process.
@@ -81,7 +135,18 @@ module DBus
81
135
  # Read data (a buffer) from the bus until CR LF is encountered.
82
136
  # Return the buffer without the CR LF characters.
83
137
  def next_msg
84
- @socket.readline.chomp.split(" ")
138
+ data,crlf = "","\r\n"
139
+ left = 1024 #1024 byte, no idea if it's ever getting bigger
140
+ while left > 0
141
+ buf = @socket.read( left > 1 ? 1 : left )
142
+ break if buf.nil?
143
+ left -= buf.size
144
+ data += buf
145
+ break if data.include? crlf
146
+ end
147
+ readline = data.chomp.split(" ")
148
+ return readline
149
+ #return @socket.readline.chomp.split(" ")
85
150
  end
86
151
 
87
152
  # Try to reach the next state based on the current state.
@@ -89,10 +154,12 @@ module DBus
89
154
  msg = next_msg
90
155
  if @state == :Starting
91
156
  case msg[0]
157
+ when "OK"
158
+ @state = :WaitingForOk
92
159
  when "CONTINUE"
93
160
  @state = :WaitingForData
94
- when "OK"
95
- @state = :WaitingForOk
161
+ when "REJECTED" #needed by tcp, unix-path/abstract don't get here
162
+ @state = :WaitingForData
96
163
  end
97
164
  end
98
165
  case @state
@@ -152,5 +219,5 @@ module DBus
152
219
  end
153
220
  return true
154
221
  end # def next_state
155
- end # class Client
222
+ end # class Client
156
223
  end # module D-Bus
data/lib/dbus/bus.rb CHANGED
@@ -11,53 +11,11 @@
11
11
  require 'socket'
12
12
  require 'thread'
13
13
  require 'singleton'
14
- require 'connection' #outsourced connection module
15
14
 
16
15
  # = D-Bus main module
17
16
  #
18
17
  # Module containing all the D-Bus modules and classes.
19
18
  module DBus
20
-
21
- # = D-Bus session bus class
22
- #
23
- # The session bus is a session specific bus (mostly for desktop use).
24
- # This is a singleton class.
25
- class SessionBus < Connection
26
- include Singleton
27
-
28
- # Get the the default session bus.
29
- def initialize
30
- super(ENV["DBUS_SESSION_BUS_ADDRESS"])
31
- connect
32
- send_hello
33
- end
34
- end
35
-
36
- # = D-Bus system bus class
37
- #
38
- # The system bus is a system-wide bus mostly used for global or
39
- # system usages. This is a singleton class.
40
- class SystemBus < Connection
41
- include Singleton
42
-
43
- # Get the default system bus.
44
- def initialize
45
- super(SystemSocketName)
46
- connect
47
- send_hello
48
- end
49
- end
50
-
51
- # FIXME: we should get rid of these
52
-
53
- def DBus.system_bus
54
- SystemBus.instance
55
- end
56
-
57
- def DBus.session_bus
58
- SessionBus.instance
59
- end
60
-
61
19
  # This represents a remote service. It should not be instancied directly
62
20
  # Use Bus::service()
63
21
  class Service
@@ -201,6 +159,524 @@ module DBus
201
159
  end
202
160
  end # class Inspect
203
161
 
162
+ # FIXME: rename Connection to Bus?
163
+
164
+ # D-Bus main connection class
165
+ #
166
+ # Main class that maintains a connection to a bus and can handle incoming
167
+ # and outgoing messages.
168
+ class Connection
169
+ # The unique name (by specification) of the message.
170
+ attr_reader :unique_name
171
+ # The socket that is used to connect with the bus.
172
+ attr_reader :socket
173
+
174
+ # Create a new connection to the bus for a given connect _path_. _path_
175
+ # format is described in the D-Bus specification:
176
+ # http://dbus.freedesktop.org/doc/dbus-specification.html#addresses
177
+ # and is something like:
178
+ # "transport1:key1=value1,key2=value2;transport2:key1=value1,key2=value2"
179
+ # e.g. "unix:path=/tmp/dbus-test"
180
+ #
181
+ # Current implementation of ruby-dbus supports only a single server
182
+ # address and only "unix:path=...,guid=..." and
183
+ # "unix:abstract=...,guid=..." forms
184
+ def initialize(path)
185
+ @path = path
186
+ @unique_name = nil
187
+ @buffer = ""
188
+ @method_call_replies = Hash.new
189
+ @method_call_msgs = Hash.new
190
+ @signal_matchrules = Array.new
191
+ @proxy = nil
192
+ @object_root = Node.new("/")
193
+ end
194
+
195
+ # Connect to the bus and initialize the connection.
196
+ def connect
197
+ connect_to_tcp if @path.include? "tcp:" #testing
198
+ connect_to_unix_abstract if @path.include? "unix:" #supposed stable
199
+ end
200
+
201
+ # Connect to a bus over tcp and initialize the connection.
202
+ def connect_to_tcp
203
+ #check if the path is sufficient
204
+ if @path.include? "host=" and @path.include? "port="
205
+ host,port,family = "","",""
206
+ #get the parameters
207
+ @path.split(",").each do |para|
208
+ host = para.sub("tcp:","").sub("host=","") if para.include? "host="
209
+ port = para.sub("port=","").to_i if para.include? "port="
210
+ family = para.sub("family=","") if para.include? "family="
211
+ end
212
+ #puts "host,port,family : #{host},#{port},#{family}"
213
+ #initialize the tcp socket
214
+ @socket = TCPSocket.new(host,port)
215
+ init_connection
216
+ else
217
+ #Danger, Will Robinson: the specified "path" is not usable
218
+ puts "ERROR:dbus/bus.rb/Connection.connect_to_tcp: supplied path: #{@path}, unasable! sry" if $DEBUG
219
+ end
220
+ end
221
+
222
+ # Connect to an abstract unix bus and initialize the connection.
223
+ def connect_to_unix_abstract
224
+ @socket = Socket.new(Socket::Constants::PF_UNIX,Socket::Constants::SOCK_STREAM, 0)
225
+ parse_session_string
226
+ if @transport == "unix" and @type == "abstract"
227
+ if HOST_END == LIL_END
228
+ sockaddr = "\1\0\0#{@unix_abstract}"
229
+ else
230
+ sockaddr = "\0\1\0#{@unix_abstract}"
231
+ end
232
+ elsif @transport == "unix" and @type == "path"
233
+ sockaddr = Socket.pack_sockaddr_un(@unix)
234
+ end
235
+ @socket.connect(sockaddr)
236
+ init_connection
237
+ end
238
+
239
+ # Parse the session string (socket address).
240
+ def parse_session_string
241
+ path_parsed = /^([^:]*):([^;]*)$/.match(@path)
242
+ @transport = path_parsed[1]
243
+ adr = path_parsed[2]
244
+ if @transport == "unix"
245
+ adr.split(",").each do |eqstr|
246
+ idx, val = eqstr.split("=")
247
+ case idx
248
+ when "path"
249
+ @type = idx
250
+ @unix = val
251
+ when "abstract"
252
+ @type = idx
253
+ @unix_abstract = val
254
+ when "guid"
255
+ @guid = val
256
+ end
257
+ end
258
+ end
259
+ end
260
+
261
+ # Send the buffer _buf_ to the bus using Connection#writel.
262
+ def send(buf)
263
+ @socket.write(buf)
264
+ end
265
+
266
+ # Tell a bus to register itself on the glib main loop
267
+ def glibize
268
+ require 'glib2'
269
+ # Circumvent a ruby-glib bug
270
+ @channels ||= Array.new
271
+
272
+ gio = GLib::IOChannel.new(@socket.fileno)
273
+ @channels << gio
274
+ gio.add_watch(GLib::IOChannel::IN) do |c, ch|
275
+ update_buffer
276
+ messages.each do |msg|
277
+ process(msg)
278
+ end
279
+ true
280
+ end
281
+ end
282
+
283
+ # FIXME: describe the following names, flags and constants.
284
+ # See DBus spec for definition
285
+ NAME_FLAG_ALLOW_REPLACEMENT = 0x1
286
+ NAME_FLAG_REPLACE_EXISTING = 0x2
287
+ NAME_FLAG_DO_NOT_QUEUE = 0x4
288
+
289
+ REQUEST_NAME_REPLY_PRIMARY_OWNER = 0x1
290
+ REQUEST_NAME_REPLY_IN_QUEUE = 0x2
291
+ REQUEST_NAME_REPLY_EXISTS = 0x3
292
+ REQUEST_NAME_REPLY_ALREADY_OWNER = 0x4
293
+
294
+ DBUSXMLINTRO = '<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN"
295
+ "http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd">
296
+ <node>
297
+ <interface name="org.freedesktop.DBus.Introspectable">
298
+ <method name="Introspect">
299
+ <arg name="data" direction="out" type="s"/>
300
+ </method>
301
+ </interface>
302
+ <interface name="org.freedesktop.DBus">
303
+ <method name="RequestName">
304
+ <arg direction="in" type="s"/>
305
+ <arg direction="in" type="u"/>
306
+ <arg direction="out" type="u"/>
307
+ </method>
308
+ <method name="ReleaseName">
309
+ <arg direction="in" type="s"/>
310
+ <arg direction="out" type="u"/>
311
+ </method>
312
+ <method name="StartServiceByName">
313
+ <arg direction="in" type="s"/>
314
+ <arg direction="in" type="u"/>
315
+ <arg direction="out" type="u"/>
316
+ </method>
317
+ <method name="Hello">
318
+ <arg direction="out" type="s"/>
319
+ </method>
320
+ <method name="NameHasOwner">
321
+ <arg direction="in" type="s"/>
322
+ <arg direction="out" type="b"/>
323
+ </method>
324
+ <method name="ListNames">
325
+ <arg direction="out" type="as"/>
326
+ </method>
327
+ <method name="ListActivatableNames">
328
+ <arg direction="out" type="as"/>
329
+ </method>
330
+ <method name="AddMatch">
331
+ <arg direction="in" type="s"/>
332
+ </method>
333
+ <method name="RemoveMatch">
334
+ <arg direction="in" type="s"/>
335
+ </method>
336
+ <method name="GetNameOwner">
337
+ <arg direction="in" type="s"/>
338
+ <arg direction="out" type="s"/>
339
+ </method>
340
+ <method name="ListQueuedOwners">
341
+ <arg direction="in" type="s"/>
342
+ <arg direction="out" type="as"/>
343
+ </method>
344
+ <method name="GetConnectionUnixUser">
345
+ <arg direction="in" type="s"/>
346
+ <arg direction="out" type="u"/>
347
+ </method>
348
+ <method name="GetConnectionUnixProcessID">
349
+ <arg direction="in" type="s"/>
350
+ <arg direction="out" type="u"/>
351
+ </method>
352
+ <method name="GetConnectionSELinuxSecurityContext">
353
+ <arg direction="in" type="s"/>
354
+ <arg direction="out" type="ay"/>
355
+ </method>
356
+ <method name="ReloadConfig">
357
+ </method>
358
+ <signal name="NameOwnerChanged">
359
+ <arg type="s"/>
360
+ <arg type="s"/>
361
+ <arg type="s"/>
362
+ </signal>
363
+ <signal name="NameLost">
364
+ <arg type="s"/>
365
+ </signal>
366
+ <signal name="NameAcquired">
367
+ <arg type="s"/>
368
+ </signal>
369
+ </interface>
370
+ </node>
371
+ '
372
+
373
+ def introspect_data(dest, path)
374
+ m = DBus::Message.new(DBus::Message::METHOD_CALL)
375
+ m.path = path
376
+ m.interface = "org.freedesktop.DBus.Introspectable"
377
+ m.destination = dest
378
+ m.member = "Introspect"
379
+ m.sender = unique_name
380
+ if not block_given?
381
+ # introspect in synchronous !
382
+ send_sync(m) do |rmsg|
383
+ if rmsg.is_a?(Error)
384
+ raise rmsg
385
+ else
386
+ return rmsg.params[0]
387
+ end
388
+ end
389
+ else
390
+ send(m.marshall)
391
+ on_return(m) do |rmsg|
392
+ if rmsg.is_a?(Error)
393
+ yield rmsg
394
+ else
395
+ yield rmsg.params[0]
396
+ end
397
+ end
398
+ end
399
+ nil
400
+ end
401
+
402
+ # Issues a call to the org.freedesktop.DBus.Introspectable.Introspect method
403
+ # _dest_ is the service and _path_ the object path you want to introspect
404
+ # If a code block is given, the introspect call in asynchronous. If not
405
+ # data is returned
406
+ #
407
+ # FIXME: link to ProxyObject data definition
408
+ # The returned object is a ProxyObject that has methods you can call to
409
+ # issue somme METHOD_CALL messages, and to setup to receive METHOD_RETURN
410
+ def introspect(dest, path)
411
+ if not block_given?
412
+ # introspect in synchronous !
413
+ data = introspect_data(dest, path)
414
+ pof = DBus::ProxyObjectFactory.new(data, self, dest, path)
415
+ return pof.build
416
+ else
417
+ introspect_data(dest, path) do |data|
418
+ yield(DBus::ProxyObjectFactory.new(data, self, dest, path).build)
419
+ end
420
+ end
421
+ end
422
+
423
+ # Exception raised when a service name is requested that is not available.
424
+ class NameRequestError < Exception
425
+ end
426
+
427
+ # Attempt to request a service _name_.
428
+ def request_service(name)
429
+ r = proxy.RequestName(name, NAME_FLAG_REPLACE_EXISTING)
430
+ raise NameRequestError if r[0] != REQUEST_NAME_REPLY_PRIMARY_OWNER
431
+ @service = Service.new(name, self)
432
+ @service
433
+ end
434
+
435
+ # Set up a ProxyObject for the bus itself, since the bus is introspectable.
436
+ # Returns the object.
437
+ def proxy
438
+ if @proxy == nil
439
+ path = "/org/freedesktop/DBus"
440
+ dest = "org.freedesktop.DBus"
441
+ pof = DBus::ProxyObjectFactory.new(DBUSXMLINTRO, self, dest, path)
442
+ @proxy = pof.build["org.freedesktop.DBus"]
443
+ end
444
+ @proxy
445
+ end
446
+
447
+ # Fill (append) the buffer from data that might be available on the
448
+ # socket.
449
+ def update_buffer
450
+ @buffer += @socket.read_nonblock(MSG_BUF_SIZE)
451
+ end
452
+
453
+ # Get one message from the bus and remove it from the buffer.
454
+ # Return the message.
455
+ def pop_message
456
+ ret = nil
457
+ begin
458
+ ret, size = Message.new.unmarshall_buffer(@buffer)
459
+ @buffer.slice!(0, size)
460
+ rescue IncompleteBufferException => e
461
+ # fall through, let ret be null
462
+ end
463
+ ret
464
+ end
465
+
466
+ # Retrieve all the messages that are currently in the buffer.
467
+ def messages
468
+ ret = Array.new
469
+ while msg = pop_message
470
+ ret << msg
471
+ end
472
+ ret
473
+ end
474
+
475
+ # The buffer size for messages.
476
+ MSG_BUF_SIZE = 4096
477
+
478
+ # Update the buffer and retrieve all messages using Connection#messages.
479
+ # Return the messages.
480
+ def poll_messages
481
+ ret = nil
482
+ r, d, d = IO.select([@socket], nil, nil, 0)
483
+ if r and r.size > 0
484
+ update_buffer
485
+ end
486
+ messages
487
+ end
488
+
489
+ # Wait for a message to arrive. Return it once it is available.
490
+ def wait_for_message
491
+ ret = pop_message
492
+ while ret == nil
493
+ r, d, d = IO.select([@socket])
494
+ if r and r[0] == @socket
495
+ update_buffer
496
+ ret = pop_message
497
+ end
498
+ end
499
+ ret
500
+ end
501
+
502
+ # Send a message _m_ on to the bus. This is done synchronously, thus
503
+ # the call will block until a reply message arrives.
504
+ def send_sync(m, &retc) # :yields: reply/return message
505
+ send(m.marshall)
506
+ @method_call_msgs[m.serial] = m
507
+ @method_call_replies[m.serial] = retc
508
+
509
+ retm = wait_for_message
510
+ process(retm)
511
+ until [DBus::Message::ERROR,
512
+ DBus::Message::METHOD_RETURN].include?(retm.message_type) and
513
+ retm.reply_serial == m.serial
514
+ retm = wait_for_message
515
+ process(retm)
516
+ end
517
+ end
518
+
519
+ # Specify a code block that has to be executed when a reply for
520
+ # message _m_ is received.
521
+ def on_return(m, &retc)
522
+ # Have a better exception here
523
+ if m.message_type != Message::METHOD_CALL
524
+ raise "on_return should only get method_calls"
525
+ end
526
+ @method_call_msgs[m.serial] = m
527
+ @method_call_replies[m.serial] = retc
528
+ end
529
+
530
+ # Asks bus to send us messages matching mr, and execute slot when
531
+ # received
532
+ def add_match(mr, &slot)
533
+ # check this is a signal.
534
+ @signal_matchrules << [mr, slot]
535
+ self.proxy.AddMatch(mr.to_s)
536
+ end
537
+
538
+ # Process a message _m_ based on its type.
539
+ # method call:: FIXME...
540
+ # method call return value:: FIXME...
541
+ # signal:: FIXME...
542
+ # error:: FIXME...
543
+ def process(m)
544
+ case m.message_type
545
+ when Message::ERROR, Message::METHOD_RETURN
546
+ raise InvalidPacketException if m.reply_serial == nil
547
+ mcs = @method_call_replies[m.reply_serial]
548
+ if not mcs
549
+ puts "no return code for #{mcs.inspect} (#{m.inspect})" if $DEBUG
550
+ else
551
+ if m.message_type == Message::ERROR
552
+ mcs.call(Error.new(m))
553
+ else
554
+ mcs.call(m)
555
+ end
556
+ @method_call_replies.delete(m.reply_serial)
557
+ @method_call_msgs.delete(m.reply_serial)
558
+ end
559
+ when DBus::Message::METHOD_CALL
560
+ if m.path == "/org/freedesktop/DBus"
561
+ puts "Got method call on /org/freedesktop/DBus" if $DEBUG
562
+ end
563
+ # handle introspectable as an exception:
564
+ if m.interface == "org.freedesktop.DBus.Introspectable" and
565
+ m.member == "Introspect"
566
+ reply = Message.new(Message::METHOD_RETURN).reply_to(m)
567
+ reply.sender = @unique_name
568
+ node = @service.get_node(m.path)
569
+ raise NotImplementedError if not node
570
+ reply.sender = @unique_name
571
+ reply.add_param(Type::STRING, @service.get_node(m.path).to_xml)
572
+ send(reply.marshall)
573
+ else
574
+ node = @service.get_node(m.path)
575
+ return if node.nil?
576
+ obj = node.object
577
+ return if obj.nil?
578
+ obj.dispatch(m) if obj
579
+ end
580
+ when DBus::Message::SIGNAL
581
+ @signal_matchrules.each do |elem|
582
+ mr, slot = elem
583
+ if mr.match(m)
584
+ slot.call(m)
585
+ return
586
+ end
587
+ end
588
+ else
589
+ puts "Unknown message type: #{m.message_type}" if $DEBUG
590
+ end
591
+ end
592
+
593
+ # Retrieves the service with the given _name_.
594
+ def service(name)
595
+ # The service might not exist at this time so we cannot really check
596
+ # anything
597
+ Service.new(name, self)
598
+ end
599
+ alias :[] :service
600
+
601
+ # Emit a signal event for the given _service_, object _obj_, interface
602
+ # _intf_ and signal _sig_ with arguments _args_.
603
+ def emit(service, obj, intf, sig, *args)
604
+ m = Message.new(DBus::Message::SIGNAL)
605
+ m.path = obj.path
606
+ m.interface = intf.name
607
+ m.member = sig.name
608
+ m.sender = service.name
609
+ i = 0
610
+ sig.params.each do |par|
611
+ m.add_param(par[1], args[i])
612
+ i += 1
613
+ end
614
+ send(m.marshall)
615
+ end
616
+
617
+ ###########################################################################
618
+ private
619
+
620
+ # Send a hello messages to the bus to let it know we are here.
621
+ def send_hello
622
+ m = Message.new(DBus::Message::METHOD_CALL)
623
+ m.path = "/org/freedesktop/DBus"
624
+ m.destination = "org.freedesktop.DBus"
625
+ m.interface = "org.freedesktop.DBus"
626
+ m.member = "Hello"
627
+ send_sync(m) do |rmsg|
628
+ @unique_name = rmsg.destination
629
+ puts "Got hello reply. Our unique_name is #{@unique_name}" if $DEBUG
630
+ end
631
+ end
632
+
633
+ # Initialize the connection to the bus.
634
+ def init_connection
635
+ @client = Client.new(@socket)
636
+ @client.authenticate
637
+ end
638
+ end # class Connection
639
+
640
+ # = D-Bus session bus class
641
+ #
642
+ # The session bus is a session specific bus (mostly for desktop use).
643
+ # This is a singleton class.
644
+ class SessionBus < Connection
645
+ include Singleton
646
+
647
+ # Get the the default session bus.
648
+ def initialize socket_name=SessionSocketName
649
+ super(socket_name)
650
+ connect
651
+ send_hello
652
+ end
653
+ end
654
+
655
+ # = D-Bus system bus class
656
+ #
657
+ # The system bus is a system-wide bus mostly used for global or
658
+ # system usages. This is a singleton class.
659
+ class SystemBus < Connection
660
+ include Singleton
661
+
662
+ # Get the default system bus.
663
+ def initialize socket_name=SystemSocketName
664
+ super(socket_name)
665
+ connect
666
+ send_hello
667
+ end
668
+ end
669
+
670
+ # FIXME: we should get rid of these singeltons
671
+
672
+ def DBus.system_bus
673
+ SystemBus.instance
674
+ end
675
+
676
+ def DBus.session_bus
677
+ SessionBus.instance
678
+ end
679
+
204
680
  # = Main event loop class.
205
681
  #
206
682
  # Class that takes care of handling message and signal events
@@ -1,3 +1,10 @@
1
+ require 'dbus/bus'
2
+ require 'dbus/auth'
3
+
4
+ # = D-Bus main module
5
+ #
6
+ # Module containing all the D-Bus modules and classes.
7
+ module DBus
1
8
  # D-Bus main connection class
2
9
  #
3
10
  # Main class that maintains a connection to a bus and can handle incoming
@@ -26,14 +33,18 @@
26
33
  @method_call_msgs = Hash.new
27
34
  @signal_matchrules = Array.new
28
35
  @proxy = nil
29
- # FIXME: can be TCP or any stream
30
- @socket = Socket.new(Socket::Constants::PF_UNIX,
31
- Socket::Constants::SOCK_STREAM, 0)
36
+ # FIXME: can be TCP or any stream, let's do it.
37
+ @socket = Socket.new(Socket::Constants::PF_UNIX,Socket::Constants::SOCK_STREAM, 0)
32
38
  @object_root = Node.new("/")
33
39
  end
34
40
 
35
41
  # Connect to the bus and initialize the connection.
36
42
  def connect
43
+ connect_to_unix_abstract
44
+ end
45
+
46
+ # Connect to the bus and initialize the connection.
47
+ def connect_to_unix_abstract
37
48
  parse_session_string
38
49
  if @transport == "unix" and @type == "abstract"
39
50
  if HOST_END == LIL_END
@@ -454,4 +465,4 @@
454
465
  #writel("BEGIN")
455
466
  end
456
467
  end # class Connection
457
-
468
+ end # module DBus
data/lib/dbus.rb CHANGED
@@ -16,7 +16,6 @@ require 'dbus/marshall'
16
16
  require 'dbus/message'
17
17
  require 'dbus/matchrule'
18
18
  require 'dbus/auth'
19
-
20
19
  require 'socket'
21
20
  require 'thread'
22
21
 
@@ -27,6 +26,9 @@ module DBus
27
26
  # Default socket name for the system bus.
28
27
  SystemSocketName = "unix:path=/var/run/dbus/system_bus_socket"
29
28
 
29
+ # Socket name for the session bus.
30
+ SessionSocketName = ENV["DBUS_SESSION_BUS_ADDRESS"]
31
+
30
32
  # Byte signifying big endianness.
31
33
  BIG_END = ?B
32
34
  # Byte signifying little endianness.
@@ -80,3 +82,5 @@ module DBus
80
82
  class InvalidIntrospectionData < Exception
81
83
  end
82
84
  end # module DBus
85
+ #just for my info
86
+ puts "pangdudus ruby-dbus fork."
metadata CHANGED
@@ -1,10 +1,10 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pangdudu-ruby-dbus
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.2
4
+ version: 0.2.3
5
5
  platform: ruby
6
6
  authors:
7
- - Ruby DBUS Team
7
+ - Ruby DBUS Team, pangdudu
8
8
  autorequire: dbus
9
9
  bindir: bin
10
10
  cert_chain: []