line |
stmt |
bran |
cond |
sub |
pod |
time |
code |
1
|
|
|
|
|
|
|
package Protocol::DBus::Peer; |
2
|
|
|
|
|
|
|
|
3
|
6
|
|
|
6
|
|
2288
|
use strict; |
|
6
|
|
|
|
|
13
|
|
|
6
|
|
|
|
|
133
|
|
4
|
6
|
|
|
6
|
|
24
|
use warnings; |
|
6
|
|
|
|
|
7
|
|
|
6
|
|
|
|
|
147
|
|
5
|
|
|
|
|
|
|
|
6
|
|
|
|
|
|
|
=encoding utf-8 |
7
|
|
|
|
|
|
|
|
8
|
|
|
|
|
|
|
=head1 NAME |
9
|
|
|
|
|
|
|
|
10
|
|
|
|
|
|
|
Protocol::DBus::Peer - base class for a D-Bus peer |
11
|
|
|
|
|
|
|
|
12
|
|
|
|
|
|
|
=head1 SYNOPSIS |
13
|
|
|
|
|
|
|
|
14
|
|
|
|
|
|
|
$dbus->send_call( |
15
|
|
|
|
|
|
|
interface => 'org.freedesktop.DBus.Properties', |
16
|
|
|
|
|
|
|
member => 'GetAll', |
17
|
|
|
|
|
|
|
signature => 's', |
18
|
|
|
|
|
|
|
path => '/org/freedesktop/DBus', |
19
|
|
|
|
|
|
|
destination => 'org.freedesktop.DBus', |
20
|
|
|
|
|
|
|
body => [ 'org.freedesktop.DBus' ], |
21
|
|
|
|
|
|
|
)->then( sub { .. } ); |
22
|
|
|
|
|
|
|
|
23
|
|
|
|
|
|
|
my $msg = $dbus->get_message(); |
24
|
|
|
|
|
|
|
|
25
|
|
|
|
|
|
|
# Same pattern as the IO::Handle method. |
26
|
|
|
|
|
|
|
$dbus->blocking(0); |
27
|
|
|
|
|
|
|
|
28
|
|
|
|
|
|
|
my $fileno = $dbus->fileno(); |
29
|
|
|
|
|
|
|
|
30
|
|
|
|
|
|
|
$dbus->flush_write_queue() if $dbus->pending_send(); |
31
|
|
|
|
|
|
|
|
32
|
|
|
|
|
|
|
# I’m not sure why you’d want to do this, but … |
33
|
|
|
|
|
|
|
$dbus->big_endian(); |
34
|
|
|
|
|
|
|
|
35
|
|
|
|
|
|
|
=head1 DESCRIPTION |
36
|
|
|
|
|
|
|
|
37
|
|
|
|
|
|
|
This class contains D-Bus logic that is useful in both client and |
38
|
|
|
|
|
|
|
server contexts. (Currently this distribution does not include a server |
39
|
|
|
|
|
|
|
implementation.) |
40
|
|
|
|
|
|
|
|
41
|
|
|
|
|
|
|
=cut |
42
|
|
|
|
|
|
|
|
43
|
6
|
|
|
6
|
|
2150
|
use Call::Context; |
|
6
|
|
|
|
|
1746
|
|
|
6
|
|
|
|
|
145
|
|
44
|
|
|
|
|
|
|
|
45
|
6
|
|
|
6
|
|
2113
|
use Protocol::DBus::Message; |
|
6
|
|
|
|
|
18
|
|
|
6
|
|
|
|
|
152
|
|
46
|
6
|
|
|
6
|
|
2060
|
use Protocol::DBus::Parser; |
|
6
|
|
|
|
|
13
|
|
|
6
|
|
|
|
|
145
|
|
47
|
6
|
|
|
6
|
|
2094
|
use Protocol::DBus::WriteMsg; |
|
6
|
|
|
|
|
13
|
|
|
6
|
|
|
|
|
164
|
|
48
|
|
|
|
|
|
|
|
49
|
6
|
|
|
6
|
|
31
|
use constant _PROMISE_CLASS => 'Promise::ES6'; |
|
6
|
|
|
|
|
12
|
|
|
6
|
|
|
|
|
1049
|
|
50
|
|
|
|
|
|
|
|
51
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
52
|
|
|
|
|
|
|
|
53
|
|
|
|
|
|
|
=head1 METHODS |
54
|
|
|
|
|
|
|
|
55
|
|
|
|
|
|
|
=head2 $msg = I->get_message() |
56
|
|
|
|
|
|
|
|
57
|
|
|
|
|
|
|
This returns a single instace of L, or undef if |
58
|
|
|
|
|
|
|
no message is available. It will also fire the appropriate “on_return” |
59
|
|
|
|
|
|
|
method on METHOD_RETURN or ERROR messages. |
60
|
|
|
|
|
|
|
|
61
|
|
|
|
|
|
|
The backend I/O logic reads data in chunks; thus, if there is a message |
62
|
|
|
|
|
|
|
already available in the read buffer, no I/O is done. If you’re doing |
63
|
|
|
|
|
|
|
non-blocking I/O then it is thus B that, every time the DBus socket |
64
|
|
|
|
|
|
|
is readable, you call this function until undef is returned. |
65
|
|
|
|
|
|
|
|
66
|
|
|
|
|
|
|
=cut |
67
|
|
|
|
|
|
|
|
68
|
|
|
|
|
|
|
sub get_message { |
69
|
6
|
|
|
6
|
1
|
66
|
my $msg = $_[0]->{'_parser'}->get_message(); |
70
|
|
|
|
|
|
|
|
71
|
6
|
50
|
|
|
|
28
|
if ($msg) { |
72
|
6
|
100
|
|
|
|
36
|
if (my $serial = $msg->get_header('REPLY_SERIAL')) { |
73
|
2
|
|
|
|
|
5
|
delete $_[0]->{'_on_armageddon'}{$serial}; |
74
|
|
|
|
|
|
|
|
75
|
2
|
50
|
|
|
|
8
|
if (my $cb = delete $_[0]->{'_on_return'}{$serial}) { |
76
|
2
|
|
|
|
|
6
|
$cb->($msg); |
77
|
|
|
|
|
|
|
} |
78
|
|
|
|
|
|
|
} |
79
|
|
|
|
|
|
|
} |
80
|
|
|
|
|
|
|
|
81
|
6
|
|
|
|
|
124
|
return $msg; |
82
|
|
|
|
|
|
|
} |
83
|
|
|
|
|
|
|
|
84
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
85
|
|
|
|
|
|
|
|
86
|
|
|
|
|
|
|
=head2 I->flush_write_queue() |
87
|
|
|
|
|
|
|
|
88
|
|
|
|
|
|
|
Same as L’s method of the same name. |
89
|
|
|
|
|
|
|
|
90
|
|
|
|
|
|
|
=cut |
91
|
|
|
|
|
|
|
|
92
|
|
|
|
|
|
|
sub flush_write_queue { |
93
|
0
|
0
|
|
0
|
1
|
0
|
if ($_[0]->{'_io'}->get_write_queue_count()) { |
94
|
0
|
|
|
|
|
0
|
return $_[0]->{'_io'}->flush_write_queue(); |
95
|
|
|
|
|
|
|
} |
96
|
|
|
|
|
|
|
|
97
|
0
|
|
|
|
|
0
|
return 1; |
98
|
|
|
|
|
|
|
} |
99
|
|
|
|
|
|
|
|
100
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
101
|
|
|
|
|
|
|
|
102
|
|
|
|
|
|
|
=head2 $promise = I->send_call( %OPTS ) |
103
|
|
|
|
|
|
|
|
104
|
|
|
|
|
|
|
Send a METHOD_CALL message. |
105
|
|
|
|
|
|
|
|
106
|
|
|
|
|
|
|
%OPTS are C, C, C, C, C, |
107
|
|
|
|
|
|
|
and C. These do as you’d expect, but note that C, if given, |
108
|
|
|
|
|
|
|
must be an array reference. |
109
|
|
|
|
|
|
|
|
110
|
|
|
|
|
|
|
C may be given as an array reference of strings, e.g., |
111
|
|
|
|
|
|
|
C. See the D-Bus Specification for all possible values. |
112
|
|
|
|
|
|
|
|
113
|
|
|
|
|
|
|
The return value is an instance of L. Normally this promise |
114
|
|
|
|
|
|
|
resolves when a METHOD_RETURN arrives in response. The resolution value is a |
115
|
|
|
|
|
|
|
a L instance that represents the response. If, |
116
|
|
|
|
|
|
|
however, C is given and contains C, the promise |
117
|
|
|
|
|
|
|
resolves as soon as the message is sent. |
118
|
|
|
|
|
|
|
|
119
|
|
|
|
|
|
|
If an ERROR arrives in response instead, the promise will instead reject |
120
|
|
|
|
|
|
|
with a L instance that represents that ERROR. |
121
|
|
|
|
|
|
|
The promise will also reject if some other error happens (e.g., an I/O |
122
|
|
|
|
|
|
|
error while sending the initial METHOD_CALL). |
123
|
|
|
|
|
|
|
|
124
|
|
|
|
|
|
|
=cut |
125
|
|
|
|
|
|
|
|
126
|
6
|
|
|
6
|
|
32
|
use constant _METHOD_RETURN_NUM => Protocol::DBus::Message::Header::MESSAGE_TYPE()->{'METHOD_RETURN'}; |
|
6
|
|
|
|
|
12
|
|
|
6
|
|
|
|
|
7571
|
|
127
|
|
|
|
|
|
|
|
128
|
|
|
|
|
|
|
sub _get_promise_class { |
129
|
6
|
|
|
6
|
|
17
|
my ($self) = @_; |
130
|
|
|
|
|
|
|
|
131
|
6
|
|
66
|
|
|
66
|
$self->{'_loaded_promise'} ||= do { |
132
|
4
|
|
|
|
|
16
|
local ($!, $@); |
133
|
4
|
|
|
|
|
78
|
my $path = $self->_PROMISE_CLASS() . '.pm'; |
134
|
4
|
|
|
|
|
63
|
$path =~ s[::][/]g; |
135
|
|
|
|
|
|
|
|
136
|
4
|
|
|
|
|
1745
|
require $path; |
137
|
|
|
|
|
|
|
}; |
138
|
|
|
|
|
|
|
|
139
|
6
|
|
|
|
|
15348
|
return $self->_PROMISE_CLASS(); |
140
|
|
|
|
|
|
|
} |
141
|
|
|
|
|
|
|
|
142
|
|
|
|
|
|
|
sub send_call { |
143
|
2
|
|
|
2
|
1
|
41
|
my ($self, %opts) = @_; |
144
|
|
|
|
|
|
|
|
145
|
2
|
|
|
|
|
8
|
my ($res, $rej, $response_expected); |
146
|
|
|
|
|
|
|
|
147
|
2
|
|
|
|
|
0
|
my $ok; |
148
|
|
|
|
|
|
|
|
149
|
2
|
|
|
|
|
22
|
my $promise_class = $self->_get_promise_class(); |
150
|
|
|
|
|
|
|
|
151
|
2
|
|
|
|
|
4
|
my $serial; |
152
|
|
|
|
|
|
|
|
153
|
2
|
|
50
|
|
|
30
|
my $on_armageddon_hr = $self->{'_on_armageddon'} ||= {}; |
154
|
|
|
|
|
|
|
|
155
|
|
|
|
|
|
|
my $promise = $promise_class->new( sub { |
156
|
2
|
|
|
2
|
|
70
|
($res, $rej) = @_; |
157
|
|
|
|
|
|
|
|
158
|
2
|
50
|
33
|
|
|
11
|
if ($opts{'flags'} && grep { $_ eq 'NO_REPLY_EXPECTED' } @{ $opts{'flags'} }) { |
|
0
|
|
|
|
|
0
|
|
|
0
|
|
|
|
|
0
|
|
159
|
0
|
|
|
|
|
0
|
$response_expected = 0; |
160
|
|
|
|
|
|
|
} |
161
|
|
|
|
|
|
|
else { |
162
|
2
|
|
|
|
|
4
|
$response_expected = 1; |
163
|
|
|
|
|
|
|
} |
164
|
|
|
|
|
|
|
|
165
|
2
|
|
|
|
|
35
|
$self->_send_msg( |
166
|
|
|
|
|
|
|
$res, |
167
|
|
|
|
|
|
|
%opts, |
168
|
|
|
|
|
|
|
type => 'METHOD_CALL', |
169
|
|
|
|
|
|
|
); |
170
|
|
|
|
|
|
|
|
171
|
2
|
|
|
|
|
83
|
$serial = $self->{'_last_sent_serial'}; |
172
|
|
|
|
|
|
|
|
173
|
2
|
|
|
|
|
5
|
$on_armageddon_hr->{$serial} = $rej; |
174
|
|
|
|
|
|
|
|
175
|
2
|
|
|
|
|
5
|
$ok = 1; |
176
|
|
|
|
|
|
|
} )->finally( sub { |
177
|
2
|
50
|
|
2
|
|
114
|
delete $on_armageddon_hr->{$serial} if $serial; |
178
|
2
|
|
|
|
|
47
|
} ); |
179
|
|
|
|
|
|
|
|
180
|
2
|
50
|
33
|
|
|
59
|
if ($ok && $response_expected) { |
181
|
|
|
|
|
|
|
# Keep references to $self out of the callback |
182
|
|
|
|
|
|
|
# in order to avoid memory leaks. |
183
|
2
|
|
50
|
|
|
36
|
my $on_return_hr = $self->{'_on_return'} ||= {}; |
184
|
|
|
|
|
|
|
|
185
|
2
|
|
|
|
|
10
|
my $orig_promise = $promise; |
186
|
|
|
|
|
|
|
|
187
|
|
|
|
|
|
|
$promise = $promise->then( sub { |
188
|
|
|
|
|
|
|
|
189
|
|
|
|
|
|
|
return $promise_class->new( sub { |
190
|
2
|
|
|
|
|
37
|
my ($res, $rej) = @_; |
191
|
|
|
|
|
|
|
|
192
|
2
|
|
|
|
|
6
|
$on_armageddon_hr->{$serial} = $rej; |
193
|
|
|
|
|
|
|
|
194
|
|
|
|
|
|
|
$on_return_hr->{$serial} = sub { |
195
|
2
|
50
|
|
|
|
27
|
if ($_[0]->get_type() == _METHOD_RETURN_NUM()) { |
196
|
2
|
|
|
|
|
6
|
$res->($_[0]); |
197
|
|
|
|
|
|
|
} |
198
|
|
|
|
|
|
|
else { |
199
|
0
|
|
|
|
|
0
|
$rej->($_[0]); |
200
|
|
|
|
|
|
|
} |
201
|
2
|
|
|
|
|
21
|
}; |
202
|
2
|
|
|
2
|
|
104
|
} ); |
203
|
2
|
|
|
|
|
17
|
} ); |
204
|
|
|
|
|
|
|
} |
205
|
|
|
|
|
|
|
|
206
|
2
|
|
|
|
|
143
|
return $promise; |
207
|
|
|
|
|
|
|
} |
208
|
|
|
|
|
|
|
|
209
|
|
|
|
|
|
|
=head2 $promise = I->send_return( $ORIG_MSG, %OPTS ) |
210
|
|
|
|
|
|
|
|
211
|
|
|
|
|
|
|
Send a METHOD_RETURN message. |
212
|
|
|
|
|
|
|
|
213
|
|
|
|
|
|
|
The return is a promise that resolves when the message is sent. |
214
|
|
|
|
|
|
|
|
215
|
|
|
|
|
|
|
Arguments are similar to C except for the header differences |
216
|
|
|
|
|
|
|
that the D-Bus specification describes. Also, C is not given |
217
|
|
|
|
|
|
|
directly but is instead inferred from the $ORIG_MSG. (Behavior is |
218
|
|
|
|
|
|
|
undefined if this parameter is given directly.) |
219
|
|
|
|
|
|
|
|
220
|
|
|
|
|
|
|
=cut |
221
|
|
|
|
|
|
|
|
222
|
|
|
|
|
|
|
sub send_return { |
223
|
2
|
|
|
2
|
1
|
189
|
my ($self, $orig_msg, @opts_kv) = @_; |
224
|
|
|
|
|
|
|
|
225
|
|
|
|
|
|
|
return $self->_get_promise_class()->new( sub { |
226
|
2
|
|
|
2
|
|
44
|
my ($res) = @_; |
227
|
|
|
|
|
|
|
|
228
|
2
|
|
|
|
|
8
|
$self->_send_msg( |
229
|
|
|
|
|
|
|
$res, |
230
|
|
|
|
|
|
|
_response_fields_from_orig_msg($orig_msg, \@opts_kv), |
231
|
|
|
|
|
|
|
type => 'METHOD_RETURN', |
232
|
|
|
|
|
|
|
); |
233
|
2
|
|
|
|
|
9
|
} ); |
234
|
|
|
|
|
|
|
} |
235
|
|
|
|
|
|
|
|
236
|
|
|
|
|
|
|
=head2 $promise = I->send_error( $ORIG_MSG, %OPTS ) |
237
|
|
|
|
|
|
|
|
238
|
|
|
|
|
|
|
Like C, but sends an error instead. The |
239
|
|
|
|
|
|
|
C parameter is required. |
240
|
|
|
|
|
|
|
|
241
|
|
|
|
|
|
|
=cut |
242
|
|
|
|
|
|
|
|
243
|
|
|
|
|
|
|
sub send_error { |
244
|
0
|
|
|
0
|
1
|
0
|
my ($self, $orig_msg, @opts_kv) = @_; |
245
|
|
|
|
|
|
|
|
246
|
|
|
|
|
|
|
return $self->_get_promise_class()->new( sub { |
247
|
0
|
|
|
0
|
|
0
|
my ($res) = @_; |
248
|
|
|
|
|
|
|
|
249
|
0
|
|
|
|
|
0
|
$self->_send_msg( |
250
|
|
|
|
|
|
|
$res, |
251
|
|
|
|
|
|
|
_response_fields_from_orig_msg($orig_msg, \@opts_kv), |
252
|
|
|
|
|
|
|
type => 'ERROR', |
253
|
|
|
|
|
|
|
); |
254
|
0
|
|
|
|
|
0
|
} ); |
255
|
|
|
|
|
|
|
} |
256
|
|
|
|
|
|
|
|
257
|
|
|
|
|
|
|
sub _response_fields_from_orig_msg { |
258
|
|
|
|
|
|
|
|
259
|
|
|
|
|
|
|
return ( |
260
|
|
|
|
|
|
|
|
261
|
|
|
|
|
|
|
# This has to honor a passed “destination” |
262
|
|
|
|
|
|
|
# so that we can implement a D-Bus server in tests. |
263
|
|
|
|
|
|
|
destination => $_[0]->get_header('SENDER'), |
264
|
|
|
|
|
|
|
|
265
|
2
|
|
|
2
|
|
28
|
@{ $_[1] }, |
|
2
|
|
|
|
|
37
|
|
266
|
|
|
|
|
|
|
|
267
|
|
|
|
|
|
|
# Reject callers’ attempts to set this one. |
268
|
|
|
|
|
|
|
reply_serial => $_[0]->get_serial(), |
269
|
|
|
|
|
|
|
); |
270
|
|
|
|
|
|
|
} |
271
|
|
|
|
|
|
|
|
272
|
|
|
|
|
|
|
=head2 $promise = I->send_signal( %OPTS ) |
273
|
|
|
|
|
|
|
|
274
|
|
|
|
|
|
|
Like C but sends a signal rather than a method call. |
275
|
|
|
|
|
|
|
|
276
|
|
|
|
|
|
|
=cut |
277
|
|
|
|
|
|
|
|
278
|
|
|
|
|
|
|
sub send_signal { |
279
|
2
|
|
|
2
|
1
|
1895
|
my ($self, @opts_kv) = @_; |
280
|
|
|
|
|
|
|
|
281
|
|
|
|
|
|
|
return $self->_get_promise_class()->new( sub { |
282
|
2
|
|
|
2
|
|
53
|
my ($res) = @_; |
283
|
|
|
|
|
|
|
|
284
|
2
|
|
|
|
|
23
|
$self->_send_msg( |
285
|
|
|
|
|
|
|
$res, |
286
|
|
|
|
|
|
|
@opts_kv, |
287
|
|
|
|
|
|
|
type => 'SIGNAL', |
288
|
|
|
|
|
|
|
); |
289
|
2
|
|
|
|
|
10
|
} ); |
290
|
|
|
|
|
|
|
} |
291
|
|
|
|
|
|
|
|
292
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
293
|
|
|
|
|
|
|
|
294
|
|
|
|
|
|
|
=head2 I->big_endian() |
295
|
|
|
|
|
|
|
|
296
|
|
|
|
|
|
|
Same interface as C, but this sets/gets/toggles whether to send |
297
|
|
|
|
|
|
|
big-endian messages instead of little-endian. |
298
|
|
|
|
|
|
|
|
299
|
|
|
|
|
|
|
By default this library uses the system’s native byte order, so you probably |
300
|
|
|
|
|
|
|
have little need for this function. |
301
|
|
|
|
|
|
|
|
302
|
|
|
|
|
|
|
=cut |
303
|
|
|
|
|
|
|
|
304
|
|
|
|
|
|
|
sub big_endian { |
305
|
0
|
|
|
0
|
1
|
0
|
my ($self) = @_; |
306
|
|
|
|
|
|
|
|
307
|
0
|
0
|
|
|
|
0
|
if (@_ > 1) { |
308
|
0
|
|
|
|
|
0
|
my $old = $self->{'_big_endian'}; |
309
|
0
|
|
|
|
|
0
|
$self->{'_big_endian'} = !!$_[1]; |
310
|
|
|
|
|
|
|
|
311
|
0
|
0
|
|
|
|
0
|
$self->{'_to_str_fn'} = 'to_string_' . ($_[1] ? 'be' : 'le'); |
312
|
|
|
|
|
|
|
|
313
|
0
|
|
|
|
|
0
|
return $self->{'_big_endian'}; |
314
|
|
|
|
|
|
|
} |
315
|
|
|
|
|
|
|
|
316
|
0
|
|
|
|
|
0
|
return !!$self->{'_big_endian'}; |
317
|
|
|
|
|
|
|
} |
318
|
|
|
|
|
|
|
|
319
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
320
|
|
|
|
|
|
|
|
321
|
|
|
|
|
|
|
=head2 I->preserve_variant_signatures() |
322
|
|
|
|
|
|
|
|
323
|
|
|
|
|
|
|
Same interface as C, but when this is enabled |
324
|
|
|
|
|
|
|
variants are given as two-member array references ([ signature => value ]), |
325
|
|
|
|
|
|
|
blessed as C instances. |
326
|
|
|
|
|
|
|
|
327
|
|
|
|
|
|
|
For most Perl applications this is probably counterproductive. |
328
|
|
|
|
|
|
|
|
329
|
|
|
|
|
|
|
=cut |
330
|
|
|
|
|
|
|
|
331
|
|
|
|
|
|
|
sub preserve_variant_signatures { |
332
|
0
|
|
|
0
|
1
|
0
|
my $self = shift; |
333
|
|
|
|
|
|
|
|
334
|
0
|
|
|
|
|
0
|
return $self->{'_parser'}->preserve_variant_signatures(@_); |
335
|
|
|
|
|
|
|
} |
336
|
|
|
|
|
|
|
|
337
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
338
|
|
|
|
|
|
|
|
339
|
|
|
|
|
|
|
=head2 I->blocking() |
340
|
|
|
|
|
|
|
|
341
|
|
|
|
|
|
|
Same interface as L’s method of the same name. |
342
|
|
|
|
|
|
|
|
343
|
|
|
|
|
|
|
=cut |
344
|
|
|
|
|
|
|
|
345
|
|
|
|
|
|
|
sub blocking { |
346
|
0
|
|
|
0
|
1
|
0
|
my $self = shift; |
347
|
|
|
|
|
|
|
|
348
|
|
|
|
|
|
|
# require() is needed on pre-5.14 perls: |
349
|
0
|
0
|
|
|
|
0
|
if ($^V lt v5.14) { |
350
|
0
|
|
|
|
|
0
|
local ($@, $!); |
351
|
0
|
|
|
|
|
0
|
require IO::File; |
352
|
|
|
|
|
|
|
} |
353
|
|
|
|
|
|
|
|
354
|
0
|
|
|
|
|
0
|
return $self->{'_socket'}->blocking(@_); |
355
|
|
|
|
|
|
|
} |
356
|
|
|
|
|
|
|
|
357
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
358
|
|
|
|
|
|
|
|
359
|
|
|
|
|
|
|
=head2 I->fileno() |
360
|
|
|
|
|
|
|
|
361
|
|
|
|
|
|
|
Returns the connection socket’s file descriptor. |
362
|
|
|
|
|
|
|
|
363
|
|
|
|
|
|
|
=cut |
364
|
|
|
|
|
|
|
|
365
|
|
|
|
|
|
|
sub fileno { |
366
|
0
|
|
|
0
|
1
|
0
|
return fileno $_[0]->{'_socket'}; |
367
|
|
|
|
|
|
|
} |
368
|
|
|
|
|
|
|
|
369
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
370
|
|
|
|
|
|
|
|
371
|
|
|
|
|
|
|
=head2 I->pending_send() |
372
|
|
|
|
|
|
|
|
373
|
|
|
|
|
|
|
Returns a boolean that indicates whether there is data queued up to send |
374
|
|
|
|
|
|
|
to the server. |
375
|
|
|
|
|
|
|
|
376
|
|
|
|
|
|
|
=cut |
377
|
|
|
|
|
|
|
|
378
|
|
|
|
|
|
|
sub pending_send { |
379
|
0
|
|
|
0
|
1
|
0
|
return !!$_[0]->{'_io'}->get_write_queue_count(); |
380
|
|
|
|
|
|
|
} |
381
|
|
|
|
|
|
|
|
382
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
383
|
|
|
|
|
|
|
|
384
|
|
|
|
|
|
|
# undocumented |
385
|
|
|
|
|
|
|
sub new { |
386
|
5
|
|
|
5
|
0
|
943199
|
my ($class, $socket) = @_; |
387
|
|
|
|
|
|
|
|
388
|
5
|
|
|
|
|
75
|
my $self = bless { _socket => $socket }, $class; |
389
|
|
|
|
|
|
|
|
390
|
5
|
|
|
|
|
95
|
$self->_set_up_peer_io( $socket ); |
391
|
|
|
|
|
|
|
|
392
|
5
|
|
|
|
|
13
|
return $self; |
393
|
|
|
|
|
|
|
} |
394
|
|
|
|
|
|
|
|
395
|
|
|
|
|
|
|
sub do_armageddon { |
396
|
0
|
|
|
0
|
0
|
0
|
my ($self, $why) = @_; |
397
|
|
|
|
|
|
|
|
398
|
0
|
|
|
|
|
0
|
%{ $self->{'_on_return'} } = (); |
|
0
|
|
|
|
|
0
|
|
399
|
|
|
|
|
|
|
|
400
|
0
|
|
|
|
|
0
|
my $on_armageddon_hr = $self->{'_on_armageddon'}; |
401
|
|
|
|
|
|
|
|
402
|
0
|
|
|
|
|
0
|
my @cbs = delete @{$on_armageddon_hr}{ keys %$on_armageddon_hr }; |
|
0
|
|
|
|
|
0
|
|
403
|
|
|
|
|
|
|
|
404
|
0
|
|
|
|
|
0
|
$_->($why) for @cbs; |
405
|
|
|
|
|
|
|
|
406
|
0
|
|
|
|
|
0
|
return; |
407
|
|
|
|
|
|
|
} |
408
|
|
|
|
|
|
|
|
409
|
|
|
|
|
|
|
#---------------------------------------------------------------------- |
410
|
|
|
|
|
|
|
|
411
|
|
|
|
|
|
|
sub _set_up_peer_io { |
412
|
5
|
|
|
5
|
|
27
|
my ($self, $socket) = @_; |
413
|
|
|
|
|
|
|
|
414
|
5
|
|
|
|
|
226
|
$self->{'_io'} = Protocol::DBus::WriteMsg->new( $socket )->enable_write_queue(); |
415
|
5
|
|
|
|
|
271
|
$self->{'_parser'} = Protocol::DBus::Parser->new( $socket ); |
416
|
|
|
|
|
|
|
|
417
|
5
|
|
|
|
|
15
|
return; |
418
|
|
|
|
|
|
|
} |
419
|
|
|
|
|
|
|
|
420
|
|
|
|
|
|
|
sub _send_msg { |
421
|
6
|
|
|
6
|
|
107
|
my ($self, $on_send, %opts) = @_; |
422
|
|
|
|
|
|
|
|
423
|
6
|
|
|
|
|
30
|
my ($type, $body_ar, $flags) = delete @opts{'type', 'body', 'flags'}; |
424
|
|
|
|
|
|
|
|
425
|
|
|
|
|
|
|
my @hargs = map { |
426
|
6
|
|
|
|
|
24
|
my $k = $_; |
|
28
|
|
|
|
|
36
|
|
427
|
28
|
|
|
|
|
43
|
$k =~ tr; |
428
|
28
|
|
|
|
|
61
|
( $k => $opts{$_} ); |
429
|
|
|
|
|
|
|
} keys %opts; |
430
|
|
|
|
|
|
|
|
431
|
6
|
|
|
|
|
46
|
my $serial = ++$self->{'_last_sent_serial'}; |
432
|
|
|
|
|
|
|
|
433
|
6
|
|
|
|
|
98
|
my $msg = Protocol::DBus::Message->new( |
434
|
|
|
|
|
|
|
type => $type, |
435
|
|
|
|
|
|
|
hfields => \@hargs, |
436
|
|
|
|
|
|
|
flags => $flags, |
437
|
|
|
|
|
|
|
body => $body_ar, |
438
|
|
|
|
|
|
|
serial => $serial, |
439
|
|
|
|
|
|
|
); |
440
|
|
|
|
|
|
|
|
441
|
|
|
|
|
|
|
# Use native byte order by default. |
442
|
6
|
|
100
|
|
|
110
|
$self->{'_endian'} ||= (pack 'n', 1) eq (pack 'l', 1) ? 'be' : 'le'; |
443
|
|
|
|
|
|
|
|
444
|
6
|
|
66
|
|
|
87
|
$self->{'_to_str_fn'} ||= "to_string_$self->{'_endian'}"; |
445
|
|
|
|
|
|
|
|
446
|
6
|
|
|
|
|
81
|
my ($buf_sr, $fds_ar) = $msg->can($self->{'_to_str_fn'})->($msg); |
447
|
|
|
|
|
|
|
|
448
|
6
|
50
|
66
|
|
|
41
|
if ($fds_ar && @$fds_ar && !$self->supports_unix_fd()) { |
|
|
|
33
|
|
|
|
|
449
|
0
|
|
|
|
|
0
|
die "Cannot send file descriptors without UNIX FD support!"; |
450
|
|
|
|
|
|
|
} |
451
|
|
|
|
|
|
|
|
452
|
6
|
|
|
|
|
54
|
$self->{'_io'}->enqueue_message( $buf_sr, $fds_ar, $on_send ); |
453
|
|
|
|
|
|
|
|
454
|
6
|
|
|
|
|
35
|
return $self->{'_io'}->flush_write_queue(); |
455
|
|
|
|
|
|
|
} |
456
|
|
|
|
|
|
|
|
457
|
|
|
|
|
|
|
1; |