gvariant 0.0.1 → 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/gvariant.rb +127 -11
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e5fee5e459cf887ec7cb21758f5d5639b2aab9a0
|
4
|
+
data.tar.gz: 6217118ee8a4b62eea11b8fa137a6b86a1c4ffca
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: da65060d983455ba3611cf0b86de1490ce6276589460783a8ec8ba94d025f7c3dfd71e326e1be07f20160176bc380a9898cfe48da09f4f0813ea6ebf0c746688
|
7
|
+
data.tar.gz: 4551f98e735677109f132dfd67229283f1c0dba2d7edaf4d7d4ce9914de223960e242cb0901ae8658ce599b03ae24e8666b8bea6da90f8858f464fa8d88af2a3
|
data/lib/gvariant.rb
CHANGED
@@ -2,7 +2,7 @@ class GVariantBasicType
|
|
2
2
|
attr_reader :id, :fixed_size, :default_value, :alignment
|
3
3
|
|
4
4
|
def initialize(id, unpack, alignment, fixed_size, default_value)
|
5
|
-
@id, @
|
5
|
+
@id, @pack_format, @alignment, @fixed_size, @default_value =
|
6
6
|
id, unpack, alignment, fixed_size, default_value
|
7
7
|
end
|
8
8
|
|
@@ -10,9 +10,20 @@ class GVariantBasicType
|
|
10
10
|
(i + @alignment - 1) & ~(@alignment - 1)
|
11
11
|
end
|
12
12
|
|
13
|
+
def pad(buf)
|
14
|
+
l = buf.length
|
15
|
+
(align(l) - l).times do
|
16
|
+
buf.concat(0)
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
13
20
|
def read(buf)
|
14
21
|
return @default_value if @fixed_size && buf.length != @fixed_size
|
15
|
-
buf.unpack(
|
22
|
+
buf.unpack(@pack_format).first
|
23
|
+
end
|
24
|
+
|
25
|
+
def write(value)
|
26
|
+
[value || @default_value].pack(@pack_format)
|
16
27
|
end
|
17
28
|
end
|
18
29
|
|
@@ -73,6 +84,10 @@ class GVariantBooleanType < GVariantBasicType
|
|
73
84
|
b = super(buf)
|
74
85
|
b != false && b != 0
|
75
86
|
end
|
87
|
+
|
88
|
+
def write(value)
|
89
|
+
super((value != 0 && value != false && value != nil) ? 1: 0)
|
90
|
+
end
|
76
91
|
end
|
77
92
|
|
78
93
|
class GVariantStringType < GVariantBasicType
|
@@ -106,6 +121,16 @@ class GVariantMaybeType < GVariantBasicType
|
|
106
121
|
@element.read(buf[0..l - 1])
|
107
122
|
end
|
108
123
|
end
|
124
|
+
|
125
|
+
def write(val)
|
126
|
+
if val
|
127
|
+
buf = @element.write(val)
|
128
|
+
buf.concat(0) unless @element.fixed_size
|
129
|
+
buf
|
130
|
+
else
|
131
|
+
""
|
132
|
+
end
|
133
|
+
end
|
109
134
|
end
|
110
135
|
|
111
136
|
class GVariantVariantType < GVariantBasicType
|
@@ -117,6 +142,12 @@ class GVariantVariantType < GVariantBasicType
|
|
117
142
|
value, sep, type = buf[0..buf.length - 1].rpartition("\x00")
|
118
143
|
{ type: type, value: GVariant.read(type, value) }
|
119
144
|
end
|
145
|
+
|
146
|
+
def write(variant)
|
147
|
+
buf = GVariant.write(variant[:type], variant[:value])
|
148
|
+
buf.concat(0)
|
149
|
+
buf << variant[:type]
|
150
|
+
end
|
120
151
|
end
|
121
152
|
|
122
153
|
class GVariantOffsetType < GVariantBasicType
|
@@ -128,24 +159,47 @@ class GVariantOffsetType < GVariantBasicType
|
|
128
159
|
|
129
160
|
def read_offset(buf, n)
|
130
161
|
l = buf.length
|
162
|
+
determine_offset_type(l)
|
163
|
+
buf.unpack("@#{l + @offset_size * n}#{@offset_pack_format}")[0]
|
164
|
+
end
|
131
165
|
|
166
|
+
def write_offsets(buf, offsets)
|
167
|
+
return buf if offsets.empty?
|
168
|
+
offset_size_prev = nil
|
169
|
+
packed_size = 0
|
170
|
+
packed = ""
|
171
|
+
|
172
|
+
loop do
|
173
|
+
determine_offset_type(buf.length + packed_size)
|
174
|
+
break if @offset_size == offset_size_prev
|
175
|
+
offset_size_prev = @offset_size
|
176
|
+
|
177
|
+
packed_size = offsets.count * @offset_size
|
178
|
+
packed = offsets.pack("#{@offset_pack_format}*")
|
179
|
+
end
|
180
|
+
|
181
|
+
buf << packed
|
182
|
+
end
|
183
|
+
|
184
|
+
private
|
185
|
+
|
186
|
+
def determine_offset_type(l)
|
132
187
|
if @offset_size.nil?
|
133
188
|
if (l < 0xff)
|
134
189
|
@offset_size = 1
|
135
|
-
@
|
190
|
+
@offset_pack_format = 'C'
|
136
191
|
elsif (l <= 0xffff)
|
137
192
|
@offset_size = 2
|
138
|
-
@
|
193
|
+
@offset_pack_format = 'S'
|
139
194
|
elsif (l < 0xffffffff)
|
140
195
|
@offset_size = 4
|
141
|
-
@
|
196
|
+
@offset_pack_format = 'L'
|
142
197
|
else
|
143
198
|
raise ArgumentError.new("Offset range too big.")
|
144
199
|
end
|
145
200
|
end
|
146
|
-
|
147
|
-
buf.unpack("@#{l + @offset_size * n}#{@offset_unpack}")[0]
|
148
201
|
end
|
202
|
+
|
149
203
|
end
|
150
204
|
|
151
205
|
class GVariantDictionaryType < GVariantOffsetType
|
@@ -177,6 +231,28 @@ class GVariantDictionaryType < GVariantOffsetType
|
|
177
231
|
|
178
232
|
Hash[key, value]
|
179
233
|
end
|
234
|
+
|
235
|
+
def write(vals)
|
236
|
+
buf = ""
|
237
|
+
offsets = []
|
238
|
+
|
239
|
+
vals.each_pair do |key, value|
|
240
|
+
@key_element.pad(buf)
|
241
|
+
buf << @key_element.write(key.to_s)
|
242
|
+
unless @key_element.fixed_size
|
243
|
+
offsets << buf.length
|
244
|
+
end
|
245
|
+
|
246
|
+
@value_element.pad(buf)
|
247
|
+
buf << @value_element.write(value)
|
248
|
+
unless @value_element.fixed_size || key == vals.keys.last
|
249
|
+
offsets << buf.length
|
250
|
+
end
|
251
|
+
end
|
252
|
+
|
253
|
+
write_offsets(buf, offsets)
|
254
|
+
buf
|
255
|
+
end
|
180
256
|
end
|
181
257
|
|
182
258
|
class GVariantArrayType < GVariantOffsetType
|
@@ -215,6 +291,21 @@ class GVariantArrayType < GVariantOffsetType
|
|
215
291
|
|
216
292
|
values
|
217
293
|
end
|
294
|
+
|
295
|
+
def write(vals)
|
296
|
+
buf = ""
|
297
|
+
offsets = []
|
298
|
+
|
299
|
+
vals.each do |val|
|
300
|
+
v = @element.write(val)
|
301
|
+
@element.pad(buf)
|
302
|
+
buf << v
|
303
|
+
offsets << buf.length
|
304
|
+
end
|
305
|
+
|
306
|
+
write_offsets(buf, offsets) unless @element.fixed_size
|
307
|
+
buf
|
308
|
+
end
|
218
309
|
end
|
219
310
|
|
220
311
|
class GVariantTupleType < GVariantOffsetType
|
@@ -270,6 +361,27 @@ class GVariantTupleType < GVariantOffsetType
|
|
270
361
|
v
|
271
362
|
end
|
272
363
|
end
|
364
|
+
|
365
|
+
def write(vals)
|
366
|
+
buf = ""
|
367
|
+
offsets = []
|
368
|
+
o = 0
|
369
|
+
i = 0
|
370
|
+
|
371
|
+
@elements.each do |element|
|
372
|
+
b = element.write(vals[i])
|
373
|
+
element.pad(buf)
|
374
|
+
buf << b
|
375
|
+
i += 1
|
376
|
+
|
377
|
+
o += b.length
|
378
|
+
offsets << o unless element.fixed_size || element == @elements.last
|
379
|
+
end
|
380
|
+
|
381
|
+
pad(buf)
|
382
|
+
write_offsets(buf, offsets)
|
383
|
+
buf
|
384
|
+
end
|
273
385
|
end
|
274
386
|
|
275
387
|
class GVariant
|
@@ -340,11 +452,15 @@ class GVariant
|
|
340
452
|
type
|
341
453
|
end
|
342
454
|
|
343
|
-
def self.read(typestr,
|
344
|
-
|
345
|
-
|
455
|
+
def self.read(typestr, buf)
|
456
|
+
buf = buf.pack("C*") if buf.is_a? Array
|
457
|
+
buf.freeze if RUBY_VERSION >= '2.1.0'
|
346
458
|
type = parse_type(typestr)
|
347
|
-
type.read(
|
459
|
+
type.read(buf)
|
348
460
|
end
|
349
461
|
|
462
|
+
def self.write(typestr, value)
|
463
|
+
type = parse_type(typestr)
|
464
|
+
type.write(value)
|
465
|
+
end
|
350
466
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gvariant
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Daniel Mack
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-06-
|
11
|
+
date: 2016-06-11 00:00:00.000000000 Z
|
12
12
|
dependencies: []
|
13
13
|
description: A simple reader and writer for the GVariant serialization format
|
14
14
|
email: github@zonque.org
|