em-ruby-dbus 0.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (76) hide show
  1. checksums.yaml +7 -0
  2. data/COPYING +504 -0
  3. data/NEWS +253 -0
  4. data/README.md +93 -0
  5. data/Rakefile +58 -0
  6. data/VERSION +1 -0
  7. data/doc/Reference.md +207 -0
  8. data/doc/Tutorial.md +480 -0
  9. data/doc/ex-calling-methods.body.rb +8 -0
  10. data/doc/ex-calling-methods.rb +3 -0
  11. data/doc/ex-properties.body.rb +9 -0
  12. data/doc/ex-properties.rb +3 -0
  13. data/doc/ex-setup.rb +7 -0
  14. data/doc/ex-signal.body.rb +20 -0
  15. data/doc/ex-signal.rb +3 -0
  16. data/doc/example-helper.rb +6 -0
  17. data/em-ruby-dbus.gemspec +20 -0
  18. data/examples/gdbus/gdbus +255 -0
  19. data/examples/gdbus/gdbus.glade +184 -0
  20. data/examples/gdbus/launch.sh +4 -0
  21. data/examples/no-introspect/nm-test.rb +21 -0
  22. data/examples/no-introspect/tracker-test.rb +16 -0
  23. data/examples/rhythmbox/playpause.rb +25 -0
  24. data/examples/service/call_service.rb +25 -0
  25. data/examples/service/service_newapi.rb +51 -0
  26. data/examples/simple/call_introspect.rb +34 -0
  27. data/examples/simple/properties.rb +19 -0
  28. data/examples/utils/listnames.rb +11 -0
  29. data/examples/utils/notify.rb +19 -0
  30. data/lib/dbus.rb +82 -0
  31. data/lib/dbus/auth.rb +269 -0
  32. data/lib/dbus/bus.rb +739 -0
  33. data/lib/dbus/core_ext/array/extract_options.rb +31 -0
  34. data/lib/dbus/core_ext/class/attribute.rb +129 -0
  35. data/lib/dbus/core_ext/kernel/singleton_class.rb +8 -0
  36. data/lib/dbus/core_ext/module/remove_method.rb +14 -0
  37. data/lib/dbus/error.rb +46 -0
  38. data/lib/dbus/export.rb +128 -0
  39. data/lib/dbus/introspect.rb +219 -0
  40. data/lib/dbus/logger.rb +31 -0
  41. data/lib/dbus/loop-em.rb +19 -0
  42. data/lib/dbus/marshall.rb +434 -0
  43. data/lib/dbus/matchrule.rb +101 -0
  44. data/lib/dbus/message.rb +276 -0
  45. data/lib/dbus/message_queue.rb +166 -0
  46. data/lib/dbus/proxy_object.rb +149 -0
  47. data/lib/dbus/proxy_object_factory.rb +41 -0
  48. data/lib/dbus/proxy_object_interface.rb +128 -0
  49. data/lib/dbus/type.rb +193 -0
  50. data/lib/dbus/xml.rb +161 -0
  51. data/test/async_spec.rb +47 -0
  52. data/test/binding_spec.rb +74 -0
  53. data/test/bus_and_xml_backend_spec.rb +39 -0
  54. data/test/bus_driver_spec.rb +20 -0
  55. data/test/bus_spec.rb +20 -0
  56. data/test/byte_array_spec.rb +38 -0
  57. data/test/err_msg_spec.rb +42 -0
  58. data/test/introspect_xml_parser_spec.rb +26 -0
  59. data/test/introspection_spec.rb +32 -0
  60. data/test/main_loop_spec.rb +82 -0
  61. data/test/property_spec.rb +53 -0
  62. data/test/server_robustness_spec.rb +66 -0
  63. data/test/server_spec.rb +53 -0
  64. data/test/service_newapi.rb +217 -0
  65. data/test/session_bus_spec_manual.rb +15 -0
  66. data/test/signal_spec.rb +90 -0
  67. data/test/spec_helper.rb +33 -0
  68. data/test/thread_safety_spec.rb +31 -0
  69. data/test/tools/dbus-launch-simple +35 -0
  70. data/test/tools/dbus-limited-session.conf +28 -0
  71. data/test/tools/test_env +13 -0
  72. data/test/tools/test_server +39 -0
  73. data/test/type_spec.rb +19 -0
  74. data/test/value_spec.rb +81 -0
  75. data/test/variant_spec.rb +66 -0
  76. metadata +145 -0
@@ -0,0 +1,4 @@
1
+ #!/bin/sh
2
+ set -e
3
+ # for the lazy typer
4
+ ruby -w -I ../../lib gdbus
@@ -0,0 +1,21 @@
1
+ #!/usr/bin/env ruby
2
+ #
3
+ # Trivial network interface lister using NetworkManager.
4
+ # NetworkManager does not support introspection, so the api is not that sexy.
5
+
6
+ require 'dbus'
7
+
8
+ bus = DBus::SystemBus.instance
9
+
10
+ nm_service = bus.service("org.freedesktop.NetworkManager")
11
+ nm_manager = nm_service.object("/org/freedesktop/NetworkManager")
12
+ poi = DBus::ProxyObjectInterface.new(nm_manager, "org.freedesktop.NetworkManager")
13
+ begin
14
+ poi.define_method("getDevices", "") # NM 0.6
15
+ p poi.getDevices
16
+ rescue Exception
17
+ poi.define_method("GetDevices", "") # NM 0.7
18
+ p poi.GetDevices
19
+ end
20
+
21
+
@@ -0,0 +1,16 @@
1
+ #!/usr/bin/env ruby
2
+ #
3
+ # Trivial network interface lister using NetworkManager.
4
+ # NetworkManager does not support introspection, so the api is not that sexy.
5
+
6
+ require 'dbus'
7
+
8
+ bus = DBus::SessionBus.instance
9
+
10
+ tracker_service = bus.service("org.freedesktop.Tracker")
11
+ tracker_manager = tracker_service.object("/org/freedesktop/tracker")
12
+ poi = DBus::ProxyObjectInterface.new(tracker_manager, "org.freedesktop.Tracker.Files")
13
+ poi.define_method("GetMetadataForFilesInFolder", "in live_query_id:i, in uri:s, in fields:as, out values:aas")
14
+ p poi.GetMetadataForFilesInFolder(-1, ENV['HOME'] + "/Desktop", ["File:Name", "File:Size"])
15
+
16
+
@@ -0,0 +1,25 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'dbus'
4
+ bus = DBus::SessionBus.instance
5
+ # get a rb object
6
+ proxy = bus.introspect("org.gnome.Rhythmbox", "/org/gnome/Rhythmbox/Player")
7
+ proxyi = proxy["org.gnome.Rhythmbox.Player"]
8
+
9
+ # register for signals
10
+
11
+ mr = DBus::MatchRule.new
12
+ mr.type = "signal"
13
+ mr.interface = "org.gnome.Rhythmbox.Player"
14
+ mr.path = "/org/gnome/Rhythmbox/Player"
15
+ bus.add_match(mr) do |msg, first_param|
16
+ print msg.member + " "
17
+ puts first_param
18
+ end
19
+
20
+ proxyi.playPause(true)
21
+
22
+ main = DBus::Main.new
23
+ main << bus
24
+ main.run
25
+
@@ -0,0 +1,25 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "dbus"
4
+
5
+ session_bus = DBus::SessionBus.instance
6
+
7
+ ruby_srv = session_bus.service("org.ruby.service")
8
+
9
+ # Get the object from this service
10
+ player = ruby_srv.object("/org/ruby/MyInstance")
11
+
12
+ # Introspect it
13
+ puts player.introspect
14
+ player.default_iface = "org.ruby.SampleInterface"
15
+ player.test_variant(["s", "coucou"])
16
+ player.on_signal("SomethingJustHappened") do |u, v|
17
+ puts "SomethingJustHappened: #{u} #{v}"
18
+ end
19
+ player.hello("8=======D", "(_._)")
20
+ p player["org.ruby.AnotherInterface"].Reverse("Hello world!")
21
+
22
+ main = DBus::Main.new
23
+ main << session_bus
24
+ main.run
25
+
@@ -0,0 +1,51 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'dbus'
4
+ require 'thread'
5
+ Thread.abort_on_exception = true
6
+
7
+ class Test < DBus::Object
8
+ # Create an interface aggregating all upcoming dbus_method defines.
9
+ dbus_interface "org.ruby.SampleInterface" do
10
+ dbus_method :hello, "in name:s, in name2:s" do |name, name2|
11
+ puts "hello(#{name}, #{name2})"
12
+ end
13
+
14
+ dbus_method :test_variant, "in stuff:v" do |variant|
15
+ p variant
16
+ end
17
+
18
+ dbus_signal :SomethingJustHappened, "toto:s, tutu:u"
19
+ end
20
+
21
+ dbus_interface "org.ruby.AnotherInterface" do
22
+ dbus_method :ThatsALongMethodNameIThink do
23
+ puts "ThatsALongMethodNameIThink"
24
+ end
25
+ dbus_method :Reverse, "in instr:s, out outstr:s" do |instr|
26
+ outstr = instr.split(//).reverse.join
27
+ puts "got: #{instr}, replying: #{outstr}"
28
+ [outstr]
29
+ end
30
+ end
31
+ end
32
+
33
+ bus = DBus::SessionBus.instance
34
+ service = bus.request_service("org.ruby.service")
35
+ myobj = Test.new("/org/ruby/MyInstance")
36
+ service.export(myobj)
37
+
38
+ Thread.new do
39
+ i = 0
40
+ loop do
41
+ # Signal emission
42
+ myobj.SomethingJustHappened("hey", i += 1)
43
+ sleep(0.5)
44
+ end
45
+ end
46
+
47
+ puts "listening"
48
+ main = DBus::Main.new
49
+ main << bus
50
+ main.run
51
+
@@ -0,0 +1,34 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "dbus"
4
+
5
+ session_bus = DBus::SessionBus.instance
6
+
7
+ # Get the Rhythmbox service
8
+ rhythmbox = session_bus.service("org.gnome.Rhythmbox")
9
+
10
+ # Get the object from this service
11
+ player = rhythmbox.object("/org/gnome/Rhythmbox/Player")
12
+
13
+ # Introspect it
14
+ player.introspect
15
+ if player.has_iface? "org.gnome.Rhythmbox.Player"
16
+ puts "We have Rhythmbox Player interface"
17
+ end
18
+
19
+ player_with_iface = player["org.gnome.Rhythmbox.Player"]
20
+ p player_with_iface.getPlayingUri
21
+
22
+ # Maybe support default_iface=(iface_str) on an ProxyObject, so
23
+ # that this is possible?
24
+ player.default_iface = "org.gnome.Rhythmbox.Player"
25
+ puts "default_iface test:"
26
+ p player.getPlayingUri
27
+ player.on_signal("elapsedChanged") do |u|
28
+ puts "elapsedChanged: #{u}"
29
+ end
30
+
31
+ main = DBus::Main.new
32
+ main << session_bus
33
+ main.run
34
+
@@ -0,0 +1,19 @@
1
+ #! /usr/bin/env ruby
2
+ require 'dbus'
3
+
4
+ bus = DBus::SystemBus.instance
5
+ nm_service = bus["org.freedesktop.NetworkManager"]
6
+ network_manager_object = nm_service.object("/org/freedesktop/NetworkManager")
7
+ network_manager_object.introspect
8
+ nm_iface = network_manager_object["org.freedesktop.NetworkManager"]
9
+
10
+ # read a property
11
+ enabled = nm_iface["WirelessEnabled"]
12
+ if enabled
13
+ puts "Wireless is enabled"
14
+ else
15
+ puts "Wireless is disabled"
16
+ end
17
+ puts "Toggling wireless"
18
+ # write a property
19
+ nm_iface["WirelessEnabled"] = ! enabled
@@ -0,0 +1,11 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'dbus'
4
+
5
+ d = if ARGV.member?("--system")
6
+ DBus::SystemBus.instance
7
+ else
8
+ DBus::SessionBus.instance
9
+ end
10
+ d.proxy.ListNames[0].each{ |n| puts "\t#{n}" }
11
+
@@ -0,0 +1,19 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'dbus'
4
+
5
+ if ARGV.size < 2
6
+ puts "Usage:"
7
+ puts "notify.rb \"title\" \"body\""
8
+ exit
9
+ end
10
+
11
+ d = DBus::SessionBus.instance
12
+ o = d.service("org.freedesktop.Notifications").object("/org/freedesktop/Notifications")
13
+ o.introspect
14
+
15
+ i = o["org.freedesktop.Notifications"]
16
+
17
+ i.Notify('notify.rb', 0, 'info', ARGV[0], ARGV[1], [], {}, 2000) do |ret, param|
18
+ end
19
+
data/lib/dbus.rb ADDED
@@ -0,0 +1,82 @@
1
+ # dbus.rb - Module containing the low-level D-Bus implementation
2
+ #
3
+ # This file is part of the ruby-dbus project
4
+ # Copyright (C) 2007 Arnaud Cornet and Paul van Tilburg
5
+ #
6
+ # This library is free software; you can redistribute it and/or
7
+ # modify it under the terms of the GNU Lesser General Public
8
+ # License, version 2.1 as published by the Free Software Foundation.
9
+ # See the file "COPYING" for the exact licensing terms.
10
+
11
+ require_relative "dbus/auth"
12
+ require_relative "dbus/bus"
13
+ require_relative "dbus/core_ext/class/attribute"
14
+ require_relative "dbus/error"
15
+ require_relative "dbus/export"
16
+ require_relative "dbus/introspect"
17
+ require_relative "dbus/logger"
18
+ require_relative "dbus/marshall"
19
+ require_relative "dbus/matchrule"
20
+ require_relative "dbus/message"
21
+ require_relative "dbus/message_queue"
22
+ require_relative "dbus/proxy_object"
23
+ require_relative "dbus/proxy_object_factory"
24
+ require_relative "dbus/proxy_object_interface"
25
+ require_relative "dbus/type"
26
+ require_relative "dbus/xml"
27
+
28
+ require "socket"
29
+ require "thread"
30
+
31
+ # = D-Bus main module
32
+ #
33
+ # Module containing all the D-Bus modules and classes.
34
+ module DBus
35
+ # Default socket name for the system bus.
36
+ SystemSocketName = "unix:path=/var/run/dbus/system_bus_socket"
37
+
38
+ # Byte signifying big endianness.
39
+ BIG_END = ?B
40
+ # Byte signifying little endianness.
41
+ LIL_END = ?l
42
+
43
+ # Byte signifying the host's endianness.
44
+ HOST_END = if [0x01020304].pack("L").unpack("V")[0] == 0x01020304
45
+ LIL_END
46
+ else
47
+ BIG_END
48
+ end
49
+
50
+ # General exceptions.
51
+
52
+ # Exception raised when an invalid packet is encountered.
53
+ class InvalidPacketException < Exception
54
+ end
55
+
56
+ # Exception raised when there is a problem with a type (may be unknown or
57
+ # mismatch).
58
+ class TypeException < Exception
59
+ end
60
+
61
+ # Exception raised when an unmarshalled buffer is truncated and
62
+ # incomplete.
63
+ class IncompleteBufferException < Exception
64
+ end
65
+
66
+ # Exception raised when a method has not been implemented (yet).
67
+ class MethodNotImplemented < Exception
68
+ end
69
+
70
+ # Exception raised when a method is invoked with invalid
71
+ # parameters (wrong number or type).
72
+ class InvalidParameters < Exception
73
+ end
74
+
75
+ # Exception raised when an invalid method name is used.
76
+ class InvalidMethodName < Exception
77
+ end
78
+
79
+ # Exception raised when invalid introspection data is parsed/used.
80
+ class InvalidIntrospectionData < Exception
81
+ end
82
+ end # module DBus
data/lib/dbus/auth.rb ADDED
@@ -0,0 +1,269 @@
1
+ # This file is part of the ruby-dbus project
2
+ # Copyright (C) 2007 Arnaud Cornet and Paul van Tilburg
3
+ #
4
+ # This library is free software; you can redistribute it and/or
5
+ # modify it under the terms of the GNU Lesser General Public
6
+ # License, version 2.1 as published by the Free Software Foundation.
7
+ # See the file "COPYING" for the exact licensing terms.
8
+
9
+ require 'rbconfig'
10
+
11
+ module DBus
12
+ # Exception raised when authentication fails somehow.
13
+ class AuthenticationFailed < Exception
14
+ end
15
+
16
+ # = General class for authentication.
17
+ class Authenticator
18
+ # Returns the name of the authenticator.
19
+ def name
20
+ self.class.to_s.upcase.sub(/.*::/, "")
21
+ end
22
+ end
23
+
24
+ # = Anonymous authentication class
25
+ class Anonymous < Authenticator
26
+ def authenticate
27
+ '527562792044427573' # Hex encoded version of "Ruby DBus"
28
+ end
29
+ end
30
+
31
+ # = External authentication class
32
+ #
33
+ # Class for 'external' type authentication.
34
+ class External < Authenticator
35
+ # Performs the authentication.
36
+ def authenticate
37
+ # Take the user id (eg integer 1000) make a string out of it "1000", take
38
+ # each character and determin hex value "1" => 0x31, "0" => 0x30. You
39
+ # obtain for "1000" => 31303030 This is what the server is expecting.
40
+ # Why? I dunno. How did I come to that conclusion? by looking at rbus
41
+ # code. I have no idea how he found that out.
42
+ return Process.uid.to_s.split(//).collect { |a| "%x" % a[0].ord }.join
43
+ end
44
+ end
45
+
46
+ # = Authentication class using SHA1 crypto algorithm
47
+ #
48
+ # Class for 'CookieSHA1' type authentication.
49
+ # Implements the AUTH DBUS_COOKIE_SHA1 mechanism.
50
+ class DBusCookieSHA1 < Authenticator
51
+
52
+ #the autenticate method (called in stage one of authentification)
53
+ def authenticate
54
+ require 'etc'
55
+ #number of retries we have for auth
56
+ @retries = 1
57
+ return "#{hex_encode(Etc.getlogin)}" #server expects it to be binary
58
+ end
59
+
60
+ #returns the modules name
61
+ def name
62
+ return 'DBUS_COOKIE_SHA1'
63
+ end
64
+
65
+ #handles the interesting crypto stuff, check the rbus-project for more info: http://rbus.rubyforge.org/
66
+ def data(hexdata)
67
+ require 'digest/sha1'
68
+ data = hex_decode(hexdata)
69
+ # name of cookie file, id of cookie in file, servers random challenge
70
+ context, id, s_challenge = data.split(' ')
71
+ # Random client challenge
72
+ c_challenge = Array.new(s_challenge.bytesize/2).map{|obj|obj=rand(255).to_s}.join
73
+ # Search cookie file for id
74
+ path = File.join(ENV['HOME'], '.dbus-keyrings', context)
75
+ DBus.logger.debug "path: #{path.inspect}"
76
+ File.foreach(path) do |line|
77
+ if line.index(id) == 0
78
+ # Right line of file, read cookie
79
+ cookie = line.split(' ')[2].chomp
80
+ DBus.logger.debug "cookie: #{cookie.inspect}"
81
+ # Concatenate and encrypt
82
+ to_encrypt = [s_challenge, c_challenge, cookie].join(':')
83
+ sha = Digest::SHA1.hexdigest(to_encrypt)
84
+ #the almighty tcp server wants everything hex encoded
85
+ hex_response = hex_encode("#{c_challenge} #{sha}")
86
+ # Return response
87
+ response = [:AuthOk, hex_response]
88
+ return response
89
+ end
90
+ end
91
+ #a little rescue magic
92
+ unless @retries <= 0
93
+ puts "ERROR: Could not auth, will now exit."
94
+ puts "ERROR: Unable to locate cookie, retry in 1 second."
95
+ @retries -= 1
96
+ sleep 1
97
+ data(hexdata)
98
+ end
99
+ end
100
+
101
+ # encode plain to hex
102
+ def hex_encode(plain)
103
+ return nil if plain.nil?
104
+ plain.to_s.unpack('H*')[0]
105
+ end
106
+
107
+ # decode hex to plain
108
+ def hex_decode(encoded)
109
+ encoded.scan(/[[:xdigit:]]{2}/).map{|h|h.hex.chr}.join
110
+ end
111
+ end #DBusCookieSHA1 class ends here
112
+
113
+ # Note: this following stuff is tested with External authenticator only!
114
+
115
+ # = Authentication client class.
116
+ #
117
+ # Class tha performs the actional authentication.
118
+ class Client
119
+ # Create a new authentication client.
120
+ def initialize(socket)
121
+ @socket = socket
122
+ @state = nil
123
+ @auth_list = [External,DBusCookieSHA1,Anonymous]
124
+ end
125
+
126
+ # Start the authentication process.
127
+ def authenticate
128
+ if (RbConfig::CONFIG["target_os"] =~ /freebsd/)
129
+ @socket.sendmsg(0.chr, 0, nil, [:SOCKET, :SCM_CREDS, ""])
130
+ else
131
+ @socket.write(0.chr)
132
+ end
133
+ next_authenticator
134
+ @state = :Starting
135
+ while @state != :Authenticated
136
+ r = next_state
137
+ return r if not r
138
+ end
139
+ true
140
+ end
141
+
142
+ ##########
143
+ private
144
+ ##########
145
+
146
+ # Send an authentication method _meth_ with arguments _args_ to the
147
+ # server.
148
+ def send(meth, *args)
149
+ o = ([meth] + args).join(" ")
150
+ @socket.write(o + "\r\n")
151
+ end
152
+
153
+ # Try authentication using the next authenticator.
154
+ def next_authenticator
155
+ begin
156
+ raise AuthenticationFailed if @auth_list.size == 0
157
+ @authenticator = @auth_list.shift.new
158
+ auth_msg = ["AUTH", @authenticator.name, @authenticator.authenticate]
159
+ DBus.logger.debug "auth_msg: #{auth_msg.inspect}"
160
+ send(auth_msg)
161
+ rescue AuthenticationFailed
162
+ @socket.close
163
+ raise
164
+ end
165
+ end
166
+
167
+ # Read data (a buffer) from the bus until CR LF is encountered.
168
+ # Return the buffer without the CR LF characters.
169
+ def next_msg
170
+ data,crlf = "","\r\n"
171
+ left = 1024 #1024 byte, no idea if it's ever getting bigger
172
+ while left > 0
173
+ buf = @socket.read( left > 1 ? 1 : left )
174
+ break if buf.nil?
175
+ left -= buf.bytesize
176
+ data += buf
177
+ break if data.include? crlf #crlf means line finished, the TCP socket keeps on listening, so we break
178
+ end
179
+ readline = data.chomp.split(" ")
180
+ DBus.logger.debug "readline: #{readline.inspect}"
181
+ return readline
182
+ end
183
+
184
+ =begin
185
+ # Read data (a buffer) from the bus until CR LF is encountered.
186
+ # Return the buffer without the CR LF characters.
187
+ def next_msg
188
+ @socket.readline.chomp.split(" ")
189
+ end
190
+ =end
191
+
192
+ # Try to reach the next state based on the current state.
193
+ def next_state
194
+ msg = next_msg
195
+ if @state == :Starting
196
+ DBus.logger.debug ":Starting msg: #{msg[0].inspect}"
197
+ case msg[0]
198
+ when "OK"
199
+ @state = :WaitingForOk
200
+ when "CONTINUE"
201
+ @state = :WaitingForData
202
+ when "REJECTED" #needed by tcp, unix-path/abstract doesn't get here
203
+ @state = :WaitingForData
204
+ end
205
+ end
206
+ DBus.logger.debug "state: #{@state}"
207
+ case @state
208
+ when :WaitingForData
209
+ DBus.logger.debug ":WaitingForData msg: #{msg[0].inspect}"
210
+ case msg[0]
211
+ when "DATA"
212
+ chall = msg[1]
213
+ resp, chall = @authenticator.data(chall)
214
+ DBus.logger.debug ":WaitingForData/DATA resp: #{resp.inspect}"
215
+ case resp
216
+ when :AuthContinue
217
+ send("DATA", chall)
218
+ @state = :WaitingForData
219
+ when :AuthOk
220
+ send("DATA", chall)
221
+ @state = :WaitingForOk
222
+ when :AuthError
223
+ send("ERROR")
224
+ @state = :WaitingForData
225
+ end
226
+ when "REJECTED"
227
+ next_authenticator
228
+ @state = :WaitingForData
229
+ when "ERROR"
230
+ send("CANCEL")
231
+ @state = :WaitingForReject
232
+ when "OK"
233
+ send("BEGIN")
234
+ @state = :Authenticated
235
+ else
236
+ send("ERROR")
237
+ @state = :WaitingForData
238
+ end
239
+ when :WaitingForOk
240
+ DBus.logger.debug ":WaitingForOk msg: #{msg[0].inspect}"
241
+ case msg[0]
242
+ when "OK"
243
+ send("BEGIN")
244
+ @state = :Authenticated
245
+ when "REJECT"
246
+ next_authenticator
247
+ @state = :WaitingForData
248
+ when "DATA", "ERROR"
249
+ send("CANCEL")
250
+ @state = :WaitingForReject
251
+ else
252
+ send("ERROR")
253
+ @state = :WaitingForOk
254
+ end
255
+ when :WaitingForReject
256
+ DBus.logger.debug ":WaitingForReject msg: #{msg[0].inspect}"
257
+ case msg[0]
258
+ when "REJECT"
259
+ next_authenticator
260
+ @state = :WaitingForOk
261
+ else
262
+ @socket.close
263
+ return false
264
+ end
265
+ end
266
+ return true
267
+ end # def next_state
268
+ end # class Client
269
+ end # module D-Bus