DeepConnect 0.4.06

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.
@@ -0,0 +1,151 @@
1
+ # encoding: UTF-8
2
+ #
3
+ # port.rb -
4
+ # Copyright (C) 1996-2010 Keiju ISHITSUKA
5
+ # (Penta Advanced Labrabries, Co.,Ltd)
6
+ #
7
+ # --
8
+ #
9
+ #
10
+ #
11
+
12
+ require "deep-connect/event"
13
+
14
+ module DeepConnect
15
+ class Port
16
+
17
+ PACK_n_SIZE = [1].pack("n").size
18
+ PACK_N_SIZE = [1].pack("N").size
19
+
20
+ def initialize(sock)
21
+ @io = sock
22
+ @peeraddr = @io.peeraddr
23
+ @session = nil
24
+ end
25
+
26
+ def close
27
+ @io.close
28
+ end
29
+
30
+ def shutdown_reading
31
+ @io.shutdown(Socket::SHUT_RD)
32
+ end
33
+
34
+ def addr
35
+ @io.addr
36
+ end
37
+
38
+ def peeraddr
39
+ @peeraddr
40
+ end
41
+
42
+ def attach(session)
43
+ @session = session
44
+ end
45
+
46
+ def import2
47
+ # puts "IMPORT: start0"
48
+ # sz = read(PACK_N_SIZE).unpack("N").first
49
+ # bin = read(sz)
50
+ a = Marshal.load(@io)
51
+ begin
52
+ # ijijć, ōŃňů|ůČ??8Ĺī??-ĢĪ.
53
+ ev = Event.materialize(@session, a.first, *a)
54
+ rescue
55
+ p $!, $@
56
+ raise
57
+ end
58
+ puts "IMPORT: #{ev.inspect}" if Conf.MESSAGE_DISPLAY
59
+ ev
60
+ end
61
+
62
+ def import
63
+ # puts "IMPORT: start0"
64
+ sz = read(PACK_N_SIZE).unpack("N").first
65
+ bin = read(sz)
66
+ begin
67
+ a = Marshal.load(bin)
68
+ rescue
69
+ p bin
70
+ p $!, $@
71
+ raise
72
+ end
73
+ begin
74
+ # ここで, ネットワーク通信発生する可能性あり.
75
+ ev = Event.materialize(@session, a.first, *a)
76
+ rescue
77
+ p $!, $@
78
+ raise
79
+ end
80
+ puts "IMPORT: #{ev.inspect}" if Conf.MESSAGE_DISPLAY
81
+ ev
82
+ end
83
+
84
+ def export2(ev)
85
+ puts "EXPORT: #{ev.inspect}" if Conf.MESSAGE_DISPLAY
86
+ bin = Marshal.dump(ev.serialize, @io)
87
+ # size = bin.size
88
+
89
+ # packet = [size].pack("N")+bin
90
+ # write(packet)
91
+ puts "EXPORT: finsh" if Conf.MESSAGE_DISPLAY
92
+ end
93
+
94
+ def export(ev)
95
+ puts "EXPORT: #{ev.inspect}" if Conf.MESSAGE_DISPLAY
96
+ begin
97
+ bin = Marshal.dump(ev.serialize)
98
+ rescue
99
+ puts "Exception Rised: #{$!}"
100
+ puts $@
101
+ p ev.serialize
102
+ raise
103
+ end
104
+ size = bin.size
105
+
106
+ packet = [size].pack("N")+bin
107
+ write(packet)
108
+ puts "EXPORT: finsh" if Conf.MESSAGE_DISPLAY
109
+ end
110
+
111
+ # def import
112
+ # sz = read(PACK_N_SIZE).unpack("N").first
113
+ # bin = read(sz).unpack("a#{sz}")
114
+ # a = Marshal.load(bin.first)
115
+ # ev = Event.materialize(@session, a.first, *a)
116
+ # puts "IMPORT: #{ev.inspect}" if Conf.MESSAGE_DISPLAY
117
+ # ev
118
+ # end
119
+
120
+ # def export(ev)
121
+ # puts "EXPORT: #{ev.inspect}" if Conf.MESSAGE_DISPLAY
122
+ # s = Marshal.dump(ev.serialize)
123
+ # size = s.size
124
+ # packet = [size, s].pack("Na#{size}")
125
+ # write(packet)
126
+ # end
127
+
128
+ def read(n)
129
+ begin
130
+ packet = @io.read(n)
131
+ fail EOFError, "socket closed" unless packet
132
+ # DC::Raise ProtocolError unless packet.size == n
133
+ packet
134
+ rescue Errno::ECONNRESET, EOFError
135
+ puts "WARN: read中に[#{peeraddr.join(', ')}]の接続が切れました"
136
+ DC::Raise DisconnectClient, peeraddr
137
+ end
138
+ end
139
+
140
+ def write(packet)
141
+ begin
142
+ @io.write(packet)
143
+ # @io.flush
144
+ rescue Errno::ECONNRESET
145
+ puts "WARN: write中に[#{peeraddr.join(', ')}]の接続が切れました"
146
+ DC::Raise DisconnectClient, peeraddr
147
+ end
148
+ end
149
+ end
150
+ end
151
+
@@ -0,0 +1,422 @@
1
+ # encoding: UTF-8
2
+ #
3
+ # reference.rb -
4
+ # Copyright (C) 1996-2010 Keiju ISHITSUKA
5
+ # (Penta Advanced Labrabries, Co.,Ltd)
6
+ #
7
+ # --
8
+ #
9
+ #
10
+ #
11
+
12
+ require "deep-connect/class-spec-space"
13
+
14
+ module DeepConnect
15
+ class Reference
16
+
17
+ preserved = [
18
+ :__id__, :object_id, :__send__, :public_send, :respond_to?, :send,
19
+ :instance_eval, :instance_exec, :extend, "!".intern
20
+ ]
21
+ instance_methods.each do |m|
22
+ next if preserved.include?(m.intern)
23
+ alias_method "__deep_connect_org_#{m}", m
24
+ undef_method m
25
+ end
26
+
27
+ # session ローカルなプロキシを生成
28
+ # [クラス名, 値]
29
+ # [クラス名, ローカルSESSION, 値]
30
+ def Reference.serialize(deep_space, value, spec = nil)
31
+ if spec
32
+ return Reference.serialize_with_spec(deep_space, value, spec)
33
+ end
34
+
35
+ if value.__deep_connect_reference?
36
+ if deep_space == value.deep_space
37
+ [value.__deep_connect_real_class, value.csid, value.peer_id, :PEER_OBJECT]
38
+ else
39
+ uuid = value.deep_space.peer_uuid.dup
40
+ if uuid[0] == "127.0.0.1" || uuid[0] == "::ffff:127.0.0.1"
41
+ uuid[0] = :SAME_UUIDADDR
42
+ end
43
+
44
+ [value.__deep_connect_real_class, value.csid, value.peer_id, uuid]
45
+ end
46
+ else
47
+ case value
48
+ when *Organizer::immutable_classes
49
+ [value.__deep_connect_real_class, value.__deep_connect_real_class.name, value]
50
+ else
51
+ object_id = deep_space.set_root(value)
52
+ csid = deep_space.my_csid_of(value)
53
+ [Reference, csid, object_id]
54
+ end
55
+ end
56
+ end
57
+
58
+ def Reference.serialize_with_spec(deep_space, value, spec)
59
+ if value.__deep_connect_reference?
60
+ if deep_space == value.deep_space
61
+ [value.__deep_connect_real_class, value.csid, value.peer_id, :PEER_OBJECT]
62
+ else
63
+ uuid = value.deep_space.peer_uuid.dup
64
+ if uuid[0] == "127.0.0.1" || uuid[0] == "::ffff:127.0.0.1"
65
+ uuid[0] = :SAME_UUIDADDR
66
+ end
67
+
68
+ [value.__deep_connect_real_class, value.csid, value.peer_id, uuid]
69
+ end
70
+ elsif Organizer::absolute_immutable_classes.include?(value.class)
71
+ [value.__deep_connect_real_class, value.__deep_connect_real_class.name, value]
72
+ else
73
+ case spec
74
+ when MethodSpec::DefaultParamSpec
75
+ Reference.serialize(deep_space, value)
76
+ when MethodSpec::RefParamSpec
77
+ object_id = deep_space.set_root(value)
78
+ csid = deep_space.my_csid_of(value)
79
+ [Reference, csid, object_id]
80
+ when MethodSpec::ValParamSpec
81
+ serialize_val(deep_space, value, spec)
82
+ when MethodSpec::DValParamSpec
83
+ # 第2引数意味なし
84
+ [value.__deep_connect_real_class, value.__deep_connect_real_class.name, value]
85
+ else
86
+ raise ArgumentError,
87
+ "argument is only specified(#{MethodSpec::ARG_SPEC.join(', ')})(#{spec})"
88
+ end
89
+ end
90
+ end
91
+
92
+ def Reference.serialize_val(deep_space, value, spec)
93
+ case value
94
+ when *Organizer::immutable_classes
95
+ [value.__deep_connect_real_class, value.__deep_connect_real_class.name, value]
96
+ else
97
+ [:VAL, value.__deep_connect_real_class.name,
98
+ [value.__deep_connect_real_class, value.deep_connect_serialize_val(deep_space)]]
99
+ end
100
+ end
101
+
102
+ def Reference.materialize(deep_space, type, csid, object_id, uuid=nil)
103
+ if type == Reference
104
+ if uuid
105
+ if uuid == :PEER_OBJECT
106
+ deep_space.root(object_id)
107
+ else
108
+ if uuid[0] == :SAME_UUIDADDR
109
+ uuid[0] = deep_space.peer_uuid[0].dup
110
+ end
111
+ peer_deep_space = deep_space.organizer.deep_space(uuid)
112
+ peer_deep_space.register_root_to_peer(object_id)
113
+ type.new(peer_deep_space, csid, object_id)
114
+ end
115
+ else
116
+ type.new(deep_space, csid, object_id)
117
+ end
118
+ else
119
+ if type == :VAL
120
+ materialize_val(deep_space, type,
121
+ csid, object_id[0], object_id[1])
122
+ else
123
+ # 即値
124
+ object_id
125
+ end
126
+ end
127
+ end
128
+
129
+ def Reference.materialize_val(deep_space, type, csid, klass, value)
130
+ klass.deep_connect_materialize_val(deep_space, value)
131
+ end
132
+
133
+ # def Reference.register(deep_space, o)
134
+ # deep_space.peer.set_root(o)
135
+ # Reference.new(session, o.id)
136
+ # end
137
+
138
+ def Reference.new(deep_space, csid, peer_id)
139
+ if r = deep_space.import_reference(peer_id)
140
+ return r
141
+ end
142
+ r = super
143
+ deep_space.register_import_reference(r)
144
+ r
145
+ end
146
+
147
+ def initialize(deep_space, csid, peer_id)
148
+ @deep_space = deep_space
149
+ @csid = csid
150
+ @peer_id = peer_id
151
+ end
152
+
153
+ attr_reader :deep_space
154
+ alias deepspace deep_space
155
+ attr_reader :csid
156
+ attr_reader :peer_id
157
+
158
+ def peer
159
+ @deep_space.root(@peer_id)
160
+ end
161
+
162
+ def release
163
+ @deep_space.deregister_import_reference_id(self)
164
+ end
165
+
166
+ # TO_METHODS = [:to_ary, :to_str, :to_int, :to_regexp]
167
+ # TO_METHODS = [:to_ary, :to_str, :to_int, :to_regexp, :to_splat]
168
+
169
+ def method_missing(method, *args, &block)
170
+ puts "SEND MESSAGE: #{self.inspect} #{method.id2name}" if Conf.DISPLAY_MESSAGE_TRACE
171
+
172
+ # if TO_METHODS.include?(method)
173
+ # return self.dc_dup.send(method)
174
+ # end
175
+ begin
176
+ if iterator?
177
+ @deep_space.session.send_to(self, method, args, &block)
178
+ else
179
+ @deep_space.session.send_to(self, method, args)
180
+ end
181
+ # rescue NoMethodError
182
+ # p $@
183
+ # p $!
184
+ # super
185
+ end
186
+ end
187
+
188
+ def asynchronus_send_with_callback(method, *args, &callback)
189
+ @deep_space.session.asyncronus_send_to(self, method, args, callback)
190
+ end
191
+ alias asynchronus_send asynchronus_send_with_callback
192
+
193
+ # def peer_to_s
194
+ # @deep_space.session.send_to(self, :to_s)
195
+ # end
196
+
197
+ # def peer_inspect
198
+ # @deep_space.session.send_to(self, :inspect)
199
+ # end
200
+
201
+ # def peer_class
202
+ # @deep_space.session.send_to(self, :class)
203
+ # end
204
+
205
+ # def to_s
206
+ # @deep_space.session.send_to(self, :to_s)
207
+ # end
208
+
209
+ # def to_a
210
+ # a = []
211
+ # @deep_space.session.send_to(self, :to_a).each{|e| a.push e}
212
+ # a
213
+ # end
214
+
215
+ # def =~(other)
216
+ # @deep_space.session.send_to(self, :=~, other)
217
+ # end
218
+
219
+ # def ===(other)
220
+ # @deep_space.session.send_to(self, :===, other)
221
+ # end
222
+
223
+ # def id
224
+ # @deep_space.session.send_to(self, :id)
225
+ # end
226
+
227
+ # def coerce(other)
228
+ # return other, peer
229
+ # end
230
+
231
+ def __deep_connect_reference?
232
+ true
233
+ end
234
+ alias dc_reference? __deep_connect_reference?
235
+
236
+ def __deep_connect_real_class
237
+ Reference
238
+ end
239
+
240
+ class UndefinedClass;end
241
+
242
+ def peer_class
243
+ return @peer_class if @peer_class
244
+ begin
245
+ @peer_class = self.class.dc_deep_copy
246
+ rescue
247
+ @peer_class = UndefinedClass
248
+ end
249
+ @peer_class
250
+ end
251
+
252
+ def respond_to?(m, include_private = false)
253
+ # m = m.intern
254
+ # if m != :to_ary && super
255
+ # return true
256
+ # end
257
+ return true if super
258
+ return @deep_space.session.send_to(self, :respond_to?, [m, include_private])
259
+ end
260
+
261
+ # ここは, オブジェクトの同値性を用いていない
262
+ # def ==(obj)
263
+ # return true if obj.equal?(self)
264
+ #
265
+ ## self.deep_connect_copy == obj
266
+ # false
267
+ # end
268
+ def ==(obj)
269
+ obj.__deep_connect_reference? &&
270
+ @deep_space == obj.deep_space &&
271
+ @peer_id == obj.peer_id
272
+ end
273
+
274
+ alias eql? ==
275
+
276
+ def equal?(obj)
277
+ self.object_id == obj.object_id
278
+ end
279
+
280
+ def hash
281
+ @deep_space.object_id ^ @peer_id
282
+ end
283
+
284
+ def kind_of?(klass)
285
+ if klass.__deep_connect_reference?
286
+ @deep_space.session.send_to(self, :kind_of?, klass)
287
+ else
288
+ self.peer_class <= klass
289
+ end
290
+ end
291
+
292
+ def nil?
293
+ false
294
+ end
295
+
296
+ # def ===(other)
297
+ # if other.__deep_connect_reference?
298
+ # @deep_space.session.send_to(self, :===, other)
299
+ # else
300
+ # case other
301
+ # when Class
302
+ # self.peer_class <= klass
303
+ # end
304
+ # end
305
+ # end
306
+
307
+ # def marshal_dump
308
+ # Reference.serialize(@deep_space, self)
309
+ # end
310
+
311
+ # def marshal_load(obj)
312
+ # Reference.materialize(
313
+ # end
314
+
315
+ # def marshal_load(obj)
316
+ # Reference.materialize(
317
+ # end
318
+
319
+ # def to_ary
320
+ # if respond_to?(:to_ary)
321
+ # p "AAAAAAA"
322
+ # self.dc_dup.to_ary
323
+ # p "BBBBBBBB"
324
+ # else
325
+ # # raise NoMethodError.new("undefined method `to_ary' for #{self}@@@", :to_ary)
326
+ # raise NoMethodError, "to_ary"
327
+ # end
328
+ # end
329
+
330
+ # def to_str
331
+ # if respond_to?(:to_str)
332
+ # self.dc_dup.to_str
333
+ # end
334
+ # end
335
+
336
+ # def to_a
337
+ # self.dc_dup.to_a
338
+ # end
339
+
340
+ def to_s(force = false)
341
+ if !force && /deep-connect/ =~ caller(1).first
342
+ unless /deep-connect\/test/ =~ caller(1).first
343
+ return __deep_connect_org_to_s
344
+ end
345
+ end
346
+
347
+ if @deep_space.status == :SERVICING
348
+ @deep_space.session.send_to(self, :to_s)
349
+ else
350
+ "(no service)"
351
+ end
352
+ end
353
+
354
+ def inspect(force = false)
355
+ if !force && /deep-connect/ =~ caller(1).first
356
+ unless /deep-connect\/test/ =~ caller(1).first
357
+ return sprintf("<DC::Ref: deep_space=%s csid=%s id=%x>",
358
+ @deep_space.to_s,
359
+ @csid,
360
+ @peer_id)
361
+ end
362
+ end
363
+
364
+ if Conf.DEBUG_REFERENCE
365
+ sprintf("<DC::Ref[deep_space=%s csid=%s id=%x]: %s>",
366
+ @deep_space.to_s,
367
+ @csid,
368
+ @peer_id,
369
+ to_s)
370
+ else
371
+ sprintf("<DC::Ref: %s>", to_s(true))
372
+ end
373
+ end
374
+
375
+ def peer_inspect
376
+ begin
377
+ @deep_space.session.send_to(self, :inspect)
378
+ rescue SessionServiceStopped
379
+ sprintf("<DC::Ref[deep_space=%s csid=%s id=%x]: %s>",
380
+ @deep_space.to_s,
381
+ @csid,
382
+ @peer_id,
383
+ "(service stoped)")
384
+ end
385
+ end
386
+
387
+ def my_inspect
388
+ __deep_connect_org_inspect
389
+ end
390
+
391
+ def deep_connect_dup
392
+ @deep_space.session.send_to(self, :deep_connect_dup)
393
+ end
394
+ alias dc_dup deep_connect_dup
395
+
396
+ def deep_connect_deep_copy
397
+ @deep_space.session.send_to(self, :deep_connect_deep_copy)
398
+ end
399
+ alias dc_deep_copy deep_connect_deep_copy
400
+ end
401
+ end
402
+
403
+ class Object
404
+ def __deep_connect_reference?
405
+ false
406
+ end
407
+ alias dc_reference? __deep_connect_reference?
408
+
409
+ def __deep_connect_real_class
410
+ self.class
411
+ end
412
+ end
413
+
414
+ class Module
415
+ def ===(other)
416
+ other.kind_of?(self)
417
+ end
418
+ end
419
+
420
+
421
+
422
+