asciipack 0.1.3 → 0.2.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.
@@ -1,219 +0,0 @@
1
- module AsciiPack
2
- class Packer
3
- class << self
4
- def pack (obj)
5
- case
6
- when obj.kind_of?(Hash)
7
- map(obj);
8
- when obj.kind_of?(Array)
9
- array(obj);
10
- when obj.kind_of?(Numeric)
11
- if obj.kind_of?(Integer)
12
- if 0 <= obj
13
- if obj < 0x10
14
- positive_fixint obj
15
- elsif obj < 0x100
16
- uint8 obj
17
- elsif obj < 0x10000
18
- uint16 obj
19
- elsif obj < 0x100000000
20
- uint32 obj
21
- elsif obj < 0x10000000000000000
22
- uint64 obj
23
- end
24
- else
25
- if -0x8 <= obj
26
- int4 obj
27
- elsif -0x80 <= obj
28
- int8 obj
29
- elsif -0x8000 <= obj
30
- int16 obj
31
- elsif -0x80000000 <= obj
32
- int32 obj
33
- elsif -0x8000000000000000 <= obj
34
- int64 obj
35
- else
36
- raise "pack size limit over"
37
- end
38
- end
39
- else
40
- float64 obj
41
- end
42
- when obj.kind_of?(String)
43
- case obj.length
44
- when 0...0x10
45
- fixstr obj
46
- when 0x10...0x100
47
- str8 obj
48
- when 0x100...0x10000
49
- str16 obj
50
- when 0x10000...0x100000000
51
- str32 obj
52
- else
53
- raise "pack size limit over"
54
- end
55
- when obj.nil?
56
- "W"
57
- when obj == false
58
- "X"
59
- when obj == true
60
- "Y"
61
- end
62
- end
63
-
64
- private
65
-
66
- def int4 (obj)
67
- "a" + ((obj & 0xf).to_s(16))
68
- end
69
-
70
- def int8 (obj)
71
- "b" + ((obj & 0xff).to_s(16))
72
- end
73
-
74
- def int16 (obj)
75
- "c" + ((obj & 0xffff).to_s(16))
76
- end
77
-
78
- def int16 (obj)
79
- "c" + ((obj & 0xffff).to_s(16))
80
- end
81
-
82
- def int32 (obj)
83
- "d" + ((obj & 0xffffffff).to_s(16))
84
- end
85
-
86
- def int64 (obj)
87
- "e" + ((obj & 0xffffffffffffffff).to_s(16))
88
- end
89
-
90
- def positive_fixint (obj)
91
- obj.to_s(16).upcase
92
- end
93
-
94
- def uint8 (obj)
95
- format_uint("g", 2, obj)
96
- end
97
-
98
- def uint16 (obj)
99
- format_uint("h", 4, obj)
100
- end
101
-
102
- def uint32 (obj)
103
- format_uint("i", 8, obj)
104
- end
105
-
106
- def uint64 (obj)
107
- format_uint("j", 16, obj)
108
- end
109
-
110
- def float64 (obj)
111
- unless obj.finite?
112
- case obj.infinite?
113
- when 1; return "l" + '7ff0000000000000' # +∞
114
- when -1; return "l" + 'fff0000000000000' # -∞
115
- else; return "l" + '7fffffffffffffff' # NAN
116
- end
117
- end
118
-
119
- sign = obj < 0
120
- obj *= -1 if sign
121
- exp = ((Math.log(obj) / Math.log(2, Math::E)) + 1023).to_i
122
- frac = obj * (2**(52 + 1023 - exp))
123
- low = frac.to_i & 0xffffffff
124
- exp |= 0x800 if sign
125
- high = ((frac / 0x100000000).to_i & 0xfffff) | (exp << 20)
126
-
127
- "l" + to_s16([
128
- (high >> 24) & 0xff, (high >> 16) & 0xff,
129
- (high >> 8) & 0xff, (high) & 0xff,
130
- (low >> 24) & 0xff, (low >> 16) & 0xff,
131
- (low >> 8) & 0xff, (low) & 0xff
132
- ])
133
- end
134
-
135
- def fixstr (obj)
136
- (obj.length + 71).chr + obj
137
- end
138
-
139
- def str8 (obj)
140
- format_str "n", 2, obj
141
- end
142
-
143
- def str16 (obj)
144
- format_str "o", 4, obj
145
- end
146
-
147
- def str32 (obj)
148
- format_str "p", 8, obj
149
- end
150
-
151
- def map (obj)
152
- keys = [];
153
- obj.each { |key, value|
154
- keys.push(pack(key) + pack(value))
155
- }
156
- if keys.length < 0x10
157
- f = ["r", 1]
158
- elsif keys.length < 0x100
159
- f = ["s", 2]
160
- elsif keys.length < 0x10000
161
- f = ["t", 4]
162
- elsif keys.length < 0x100000000
163
- f = ["u", 8]
164
- else
165
- raise "pack size limit over"
166
- end
167
- format_uint(f[0], f[1], keys.length) + keys.join('');
168
- end
169
-
170
- def array (obj)
171
- keys = [];
172
- obj.each { |value|
173
- keys.push(pack(value));
174
- }
175
- if keys.length < 0x10
176
- f = ["v", 1]
177
- elsif keys.length < 0x100
178
- f = ["w", 2]
179
- elsif keys.length < 0x10000
180
- f = ["x", 4]
181
- elsif keys.length < 0x100000000
182
- f = ["y", 8]
183
- else
184
- raise "pack size limit over"
185
- end
186
- format_uint(f[0], f[1], keys.length) + keys.join('');
187
- end
188
-
189
- def format_uint (type, length, num)
190
- hex = num.to_s(16);
191
- len = length - hex.length;
192
- zero = '0' * len;
193
- type + zero + hex;
194
- end
195
-
196
- def format_str (type, length, str)
197
- hex = str.length.to_s(16);
198
- len = length - hex.length;
199
- zero = '0' * len;
200
- type + zero + hex + str;
201
- end
202
-
203
- def to_s16 (a)
204
- a.map { |i|
205
- hex = i.to_s(16)
206
- len = hex.length
207
- i = 2 - len
208
- ('0' * i) + hex
209
- }.join('')
210
- end
211
- end
212
- end
213
-
214
- class << self
215
- def pack (obj)
216
- Packer.pack obj
217
- end
218
- end
219
- end
@@ -1,201 +0,0 @@
1
- module AsciiPack
2
- class Unpacker
3
- @@fixmap = {
4
- "0" => 0x0,
5
- "1" => 0x1,
6
- "2" => 0x2,
7
- "3" => 0x3,
8
- "4" => 0x4,
9
- "5" => 0x5,
10
- "6" => 0x6,
11
- "7" => 0x7,
12
- "8" => 0x8,
13
- "9" => 0x9,
14
- "A" => 0xa,
15
- "B" => 0xb,
16
- "C" => 0xc,
17
- "D" => 0xd,
18
- "E" => 0xe,
19
- "F" => 0xf,
20
- "W" => nil,
21
- "X" => false,
22
- "Y" => true,
23
- }.freeze
24
-
25
- def initialize (ap)
26
- @ap = ap
27
- @at = 0
28
- @ch = @ap[0]
29
- end
30
-
31
- def unpack
32
- move
33
-
34
- if @@fixmap.key?(@ch)
35
- return @@fixmap[@ch]
36
- end
37
-
38
- case @ch
39
- when "a"; int4
40
- when "b"; int8
41
- when "c"; int16
42
- when "d"; int32
43
- when "e"; int64
44
- when "g"; uint8
45
- when "h"; uint16
46
- when "i"; uint32
47
- when "j"; uint64
48
- when "l"; float64
49
- when "n"; str8
50
- when "o"; str16
51
- when "p"; str32
52
- when "r"; map4
53
- when "s"; map8
54
- when "t"; map16
55
- when "u"; map32
56
- when "v"; array4
57
- when "w"; array8
58
- when "x"; array16
59
- when "y"; array32
60
- when /[G-V]/; fixstr
61
- else raise "undefined type " + @ch.to_s
62
- end
63
- end
64
-
65
- private
66
-
67
- def move
68
- @ch = @ap[@at]
69
- @at += 1
70
- @ch
71
- end
72
-
73
- def cut (len)
74
- ret = @ap[@at...(@at + len)]
75
- @at += len
76
- @ch = @ap[@at]
77
- ret
78
- end
79
-
80
- def int4
81
- move
82
- i = @ch.to_i(16)
83
- (@ch[0].to_i(16) < 0x8) ? i : i - 0x10;
84
- end
85
-
86
- def int8
87
- c = cut(2)
88
- i = c.to_i(16)
89
- (c[0].to_i(16) < 0x8) ? i : i - 0x100;
90
- end
91
-
92
- def int16
93
- c = cut(4)
94
- i = c.to_i(16)
95
- (c[0].to_i(16) < 0x8) ? i : i - 0x10000;
96
- end
97
-
98
- def int32
99
- c = cut(8)
100
- i = c.to_i(16)
101
- (c[0].to_i(16) < 0x8) ? i : i - 0x100000000;
102
- end
103
-
104
- def int64
105
- c = cut(16)
106
- i = c.to_i(16)
107
- (c[0].to_i(16) < 0x8) ? i : i - 0x10000000000000000;
108
- end
109
-
110
- def uint8
111
- cut(2).to_i(16)
112
- end
113
-
114
- def uint16
115
- cut(4).to_i(16)
116
- end
117
-
118
- def uint32
119
- cut(8).to_i(16)
120
- end
121
-
122
- def uint64
123
- cut(16).to_i(16)
124
- end
125
-
126
- def float64
127
- # IEEE 752 format
128
- hex = cut(3)
129
- num = hex.to_i(16)
130
- sign = num & 0x800
131
- exp = (num & 0x7ff) - 1023
132
- frac = ('1' + cut(13)).to_i(16)
133
-
134
- if hex == '7ff' && frac != 0
135
- return Float.NAN
136
- elsif hex == '7ff' && frac == 0
137
- return Float.INFINITY
138
- elsif hex == 'fff' && frac == 0
139
- return -1 / 0.0
140
- end
141
-
142
- ((sign == 0 ? 1 : -1) * frac * (2**(exp - 52))).to_f
143
- end
144
-
145
- def map (length)
146
- len = cut(length).to_i(16)
147
- hash = {}
148
- len.times {
149
- key = unpack
150
- hash[key] = unpack
151
- }
152
- hash
153
- end
154
-
155
- def map4; map(1) end
156
- def map8; map(2) end
157
- def map16; map(4) end
158
- def map32; map(8) end
159
-
160
- def array (length)
161
- len = cut(length).to_i(16)
162
- array = []
163
- len.times {
164
- array << unpack
165
- }
166
- array
167
- end
168
-
169
- def array4; array(1) end
170
- def array8; array(2) end
171
- def array16; array(4) end
172
- def array32; array(8) end
173
-
174
- def fixstr
175
- len = @ch.ord - 71 # 71 = "G".ord
176
- cut(len)
177
- end
178
-
179
- def str8
180
- len = cut(2).to_i(16)
181
- cut(len)
182
- end
183
-
184
- def str16
185
- len = cut(4).to_i(16)
186
- cut(len)
187
- end
188
-
189
- def str32
190
- len = cut(8).to_i(16)
191
- cut(len)
192
- end
193
- end
194
-
195
- class << self
196
- def unpack (obj)
197
- unpacker = Unpacker.new obj
198
- unpacker.unpack
199
- end
200
- end
201
- end