mochilo 1.2.1 → 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.
@@ -4,21 +4,6 @@ MOAPI mo_value moapi_bytes_new(const char *src, size_t len)
4
4
  return (mo_value)rb_str_new(src, len);
5
5
  }
6
6
 
7
- MOAPI mo_value moapi_sym_new(const char *src, size_t len)
8
- {
9
- char *symbol;
10
-
11
- if (len > 0xFF)
12
- rb_raise(rb_eArgError, "Symbol too long to encode in BananaPack");
13
-
14
- symbol = alloca(len + 1);
15
- memcpy(symbol, src, len);
16
- symbol[len] = '\0';
17
-
18
- return (mo_value)ID2SYM(rb_intern(symbol));
19
- }
20
-
21
- #ifdef HAVE_RUBY_ENCODING_H
22
7
  MOAPI mo_value moapi_str_new(const char *src, size_t len, enum msgpack_enc_t encoding)
23
8
  {
24
9
  int index = 0;
@@ -32,7 +17,6 @@ MOAPI mo_value moapi_str_new(const char *src, size_t len, enum msgpack_enc_t enc
32
17
 
33
18
  return (mo_value)str;
34
19
  }
35
- #endif
36
20
 
37
21
  MOAPI mo_value moapi_array_new(size_t array_size)
38
22
  {
@@ -7,7 +7,7 @@
7
7
 
8
8
  extern VALUE rb_eMochiloPackError;
9
9
 
10
- void mochilo_pack_one(mochilo_buf *buf, VALUE rb_object, int trusted);
10
+ void mochilo_pack_one(mochilo_buf *buf, VALUE rb_object);
11
11
 
12
12
  void mochilo_pack_fixnum(mochilo_buf *buf, VALUE rb_fixnum)
13
13
  {
@@ -75,14 +75,13 @@ void mochilo_pack_bignum(mochilo_buf *buf, VALUE rb_bignum)
75
75
 
76
76
  struct mochilo_hash_pack {
77
77
  mochilo_buf *buf;
78
- int trusted;
79
78
  };
80
79
 
81
80
  static int hash_callback(VALUE key, VALUE val, VALUE opaque)
82
81
  {
83
82
  struct mochilo_hash_pack *hash_pack = (struct mochilo_hash_pack*)opaque;
84
- mochilo_pack_one(hash_pack->buf, key, hash_pack->trusted);
85
- mochilo_pack_one(hash_pack->buf, val, hash_pack->trusted);
83
+ mochilo_pack_one(hash_pack->buf, key);
84
+ mochilo_pack_one(hash_pack->buf, val);
86
85
  return 0;
87
86
  }
88
87
 
@@ -93,13 +92,12 @@ void mochilo_pack_double(mochilo_buf *buf, VALUE rb_double)
93
92
  mochilo_buf_put64be(buf, &d);
94
93
  }
95
94
 
96
- void mochilo_pack_hash(mochilo_buf *buf, VALUE rb_hash, int trusted)
95
+ void mochilo_pack_hash(mochilo_buf *buf, VALUE rb_hash)
97
96
  {
98
97
  struct mochilo_hash_pack hash_pack;
99
98
  long size = RHASH_SIZE(rb_hash);
100
99
 
101
100
  hash_pack.buf = buf;
102
- hash_pack.trusted = trusted;
103
101
 
104
102
  if (size < 0x10) {
105
103
  uint8_t lead = 0x80 | size;
@@ -124,46 +122,26 @@ void mochilo_pack_bytes(mochilo_buf *buf, VALUE rb_bytes)
124
122
  {
125
123
  long size = RSTRING_LEN(rb_bytes);
126
124
 
127
- if (size < 0x20) {
128
- uint8_t lead = 0xA0 | size;
125
+ if (size < 0x100) {
126
+ uint8_t lead = size;
127
+ mochilo_buf_putc(buf, MSGPACK_T_BIN8);
129
128
  mochilo_buf_putc(buf, lead);
130
- }
131
-
132
- else if (size < 0x10000) {
129
+ } else if (size < 0x10000) {
133
130
  uint16_t lead = size;
134
- mochilo_buf_putc(buf, MSGPACK_T_RAW16);
131
+ mochilo_buf_putc(buf, MSGPACK_T_BIN16);
135
132
  mochilo_buf_put16be(buf, &lead);
136
- }
137
-
138
- else {
139
- mochilo_buf_putc(buf, MSGPACK_T_RAW32);
133
+ } else if (size < 0x100000000) {
134
+ mochilo_buf_putc(buf, MSGPACK_T_BIN32);
140
135
  mochilo_buf_put32be(buf, &size);
141
- }
142
-
143
- mochilo_buf_put(buf, RSTRING_PTR(rb_bytes), size);
144
- }
145
-
146
- void mochilo_pack_symbol(mochilo_buf *buf, VALUE rb_symbol)
147
- {
148
- long size;
149
- const char *name;
150
-
151
- name = rb_id2name(SYM2ID(rb_symbol));
152
- size = strlen(name);
153
-
154
- if (size < 0x100) {
155
- uint8_t lead = size;
156
- mochilo_buf_putc(buf, MSGPACK_T_SYM);
157
- mochilo_buf_putc(buf, lead);
158
136
  } else {
137
+ // there is no bin 64
159
138
  rb_raise(rb_eMochiloPackError,
160
- "Symbol too long: must be under %d bytes, %ld given", 0x100, size);
139
+ "Binary string cannot be larger than %ld bytes", 0x100000000);
161
140
  }
162
141
 
163
- mochilo_buf_put(buf, name, size);
142
+ mochilo_buf_put(buf, RSTRING_PTR(rb_bytes), size);
164
143
  }
165
144
 
166
- #ifdef HAVE_RUBY_ENCODING_H
167
145
  void mochilo_pack_str(mochilo_buf *buf, VALUE rb_str)
168
146
  {
169
147
  long size = RSTRING_LEN(rb_str);
@@ -172,27 +150,57 @@ void mochilo_pack_str(mochilo_buf *buf, VALUE rb_str)
172
150
  const struct mochilo_enc_map *enc2id;
173
151
  const char *enc_name;
174
152
 
175
- if (size < 0x10000) {
176
- uint16_t lead = size;
177
- mochilo_buf_putc(buf, MSGPACK_T_STR16);
178
- mochilo_buf_put16be(buf, &lead);
179
- }
180
-
181
- else {
182
- mochilo_buf_putc(buf, MSGPACK_T_STR32);
183
- mochilo_buf_put32be(buf, &size);
184
- }
185
-
186
153
  encoding = rb_enc_get(rb_str);
187
154
  enc_name = rb_enc_name(encoding);
188
- enc2id = mochilo_encoding_to_id(enc_name, (unsigned int)strlen(enc_name));
189
155
 
190
- mochilo_buf_putc(buf, enc2id ? enc2id->id : 0);
156
+ if (encoding == rb_utf8_encoding()) {
157
+ // use str type from msgpack spec
158
+ if (size < 0x20) {
159
+ uint8_t lead = 0xa0 | size;
160
+ mochilo_buf_putc(buf, lead);
161
+ } else if (size < 0x100) {
162
+ uint8_t lead = size;
163
+ mochilo_buf_putc(buf, MSGPACK_T_STR8);
164
+ mochilo_buf_putc(buf, lead);
165
+ } else if (size < 0x10000) {
166
+ uint16_t lead = size;
167
+ mochilo_buf_putc(buf, MSGPACK_T_STR16);
168
+ mochilo_buf_put16be(buf, &lead);
169
+ } else if (size < 0x100000000) {
170
+ mochilo_buf_putc(buf, MSGPACK_T_STR32);
171
+ mochilo_buf_put32be(buf, &size);
172
+ } else {
173
+ // there is no str 64
174
+ rb_raise(rb_eMochiloPackError,
175
+ "String cannot be larger than %ld bytes", 0x100000000);
176
+ }
177
+ } else {
178
+ // if another encoding is used we need to use our custom types
179
+ if (size < 0x100) {
180
+ uint8_t lead = size;
181
+ mochilo_buf_putc(buf, MSGPACK_T_ENC8);
182
+ mochilo_buf_putc(buf, lead);
183
+ } else if (size < 0x10000) {
184
+ uint16_t lead = size;
185
+ mochilo_buf_putc(buf, MSGPACK_T_ENC16);
186
+ mochilo_buf_put16be(buf, &lead);
187
+ } else if (size < 0x100000000) {
188
+ mochilo_buf_putc(buf, MSGPACK_T_ENC32);
189
+ mochilo_buf_put32be(buf, &size);
190
+ } else {
191
+ // there is no ext 64
192
+ rb_raise(rb_eMochiloPackError,
193
+ "String cannot be larger than %ld bytes", 0x100000000);
194
+ }
195
+
196
+ enc2id = mochilo_encoding_to_id(enc_name, (unsigned int)strlen(enc_name));
197
+ mochilo_buf_putc(buf, enc2id ? enc2id->id : 0);
198
+ }
199
+
191
200
  mochilo_buf_put(buf, RSTRING_PTR(rb_str), size);
192
201
  }
193
- #endif
194
202
 
195
- void mochilo_pack_array(mochilo_buf *buf, VALUE rb_array, int trusted)
203
+ void mochilo_pack_array(mochilo_buf *buf, VALUE rb_array)
196
204
  {
197
205
  long i, size = RARRAY_LEN(rb_array);
198
206
 
@@ -213,11 +221,11 @@ void mochilo_pack_array(mochilo_buf *buf, VALUE rb_array, int trusted)
213
221
  }
214
222
 
215
223
  for (i = 0; i < size; i++) {
216
- mochilo_pack_one(buf, rb_ary_entry(rb_array, i), trusted);
224
+ mochilo_pack_one(buf, rb_ary_entry(rb_array, i));
217
225
  }
218
226
  }
219
227
 
220
- void mochilo_pack_one(mochilo_buf *buf, VALUE rb_object, int trusted)
228
+ void mochilo_pack_one(mochilo_buf *buf, VALUE rb_object)
221
229
  {
222
230
  switch (rb_type(rb_object)) {
223
231
  case T_NIL:
@@ -236,28 +244,19 @@ void mochilo_pack_one(mochilo_buf *buf, VALUE rb_object, int trusted)
236
244
  mochilo_pack_fixnum(buf, rb_object);
237
245
  return;
238
246
 
239
- case T_SYMBOL:
240
- if (trusted)
241
- mochilo_pack_symbol(buf, rb_object);
242
- else
243
- mochilo_pack_str(buf, rb_obj_as_string(rb_object));
244
- return;
245
-
246
247
  case T_STRING:
247
- #ifdef HAVE_RUBY_ENCODING_H
248
248
  if (ENCODING_GET(rb_object) != 0)
249
249
  mochilo_pack_str(buf, rb_object);
250
250
  else
251
- #endif
252
251
  mochilo_pack_bytes(buf, rb_object);
253
252
  return;
254
253
 
255
254
  case T_HASH:
256
- mochilo_pack_hash(buf, rb_object, trusted);
255
+ mochilo_pack_hash(buf, rb_object);
257
256
  return;
258
257
 
259
258
  case T_ARRAY:
260
- mochilo_pack_array(buf, rb_object, trusted);
259
+ mochilo_pack_array(buf, rb_object);
261
260
  return;
262
261
 
263
262
  case T_FLOAT:
@@ -269,14 +268,8 @@ void mochilo_pack_one(mochilo_buf *buf, VALUE rb_object, int trusted)
269
268
  return;
270
269
 
271
270
  default:
272
- if (rb_respond_to(rb_object, rb_intern("to_bpack"))) {
273
- VALUE bpack = rb_funcall(rb_object, rb_intern("to_bpack"), 0);
274
-
275
- mochilo_buf_put(buf, RSTRING_PTR(bpack), RSTRING_LEN(bpack));
276
- } else {
277
- rb_raise(rb_eMochiloPackError,
278
- "Unsupported object type: %s", rb_obj_classname(rb_object));
279
- }
271
+ rb_raise(rb_eMochiloPackError,
272
+ "Unsupported object type: %s", rb_obj_classname(rb_object));
280
273
  return;
281
274
  }
282
275
  }
@@ -159,14 +159,10 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
159
159
  return unpack_hash(_value, (size_t)length, src);
160
160
  }
161
161
 
162
- case MSGPACK_T_SYM:
162
+ case MSGPACK_T_STR8:
163
163
  {
164
164
  uint8_t length;
165
165
  const char *ptr;
166
-
167
- if (!src->trusted) {
168
- return MSGPACK_EUNSAFE;
169
- }
170
166
 
171
167
  SRC_ENSURE_AVAIL(src, 1);
172
168
  mochilo_src_get8be(src, &length);
@@ -174,12 +170,58 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
174
170
  if (!(ptr = mochilo_src_peek(src, length)))
175
171
  return -1;
176
172
 
177
- *_value = moapi_sym_new(ptr, length);
173
+ *_value = moapi_str_new(ptr, length, MSGPACK_ENC_UTF_8);
178
174
  return 0;
179
175
  }
180
176
 
181
- #ifdef HAVE_RUBY_ENCODING_H
182
177
  case MSGPACK_T_STR16:
178
+ {
179
+ uint16_t length;
180
+ const char *ptr;
181
+
182
+ SRC_ENSURE_AVAIL(src, 2 + 1);
183
+ mochilo_src_get16be(src, &length);
184
+
185
+ if (!(ptr = mochilo_src_peek(src, length)))
186
+ return -1;
187
+
188
+ *_value = moapi_str_new(ptr, length, MSGPACK_ENC_UTF_8);
189
+ return 0;
190
+ }
191
+
192
+ case MSGPACK_T_STR32:
193
+ {
194
+ uint32_t length;
195
+ const char *ptr;
196
+
197
+ SRC_ENSURE_AVAIL(src, 4 + 1);
198
+ mochilo_src_get32be(src, &length);
199
+
200
+ if (!(ptr = mochilo_src_peek(src, length)))
201
+ return -1;
202
+
203
+ *_value = moapi_str_new(ptr, length, MSGPACK_ENC_UTF_8);
204
+ return 0;
205
+ }
206
+
207
+ case MSGPACK_T_ENC8:
208
+ {
209
+ uint8_t length;
210
+ uint8_t encoding;
211
+ const char *ptr;
212
+
213
+ SRC_ENSURE_AVAIL(src, 1 + 1);
214
+ mochilo_src_get8be(src, &length);
215
+ mochilo_src_get8be(src, &encoding);
216
+
217
+ if (!(ptr = mochilo_src_peek(src, length)))
218
+ return -1;
219
+
220
+ *_value = moapi_str_new(ptr, length, encoding);
221
+ return 0;
222
+ }
223
+
224
+ case MSGPACK_T_ENC16:
183
225
  {
184
226
  uint16_t length;
185
227
  uint8_t encoding;
@@ -196,7 +238,7 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
196
238
  return 0;
197
239
  }
198
240
 
199
- case MSGPACK_T_STR32:
241
+ case MSGPACK_T_ENC32:
200
242
  {
201
243
  uint32_t length;
202
244
  uint8_t encoding;
@@ -212,9 +254,23 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
212
254
  *_value = moapi_str_new(ptr, length, encoding);
213
255
  return 0;
214
256
  }
215
- #endif
216
257
 
217
- case MSGPACK_T_RAW16:
258
+ case MSGPACK_T_BIN8:
259
+ {
260
+ uint8_t length;
261
+ const char *ptr;
262
+
263
+ SRC_ENSURE_AVAIL(src, 1);
264
+ mochilo_src_get8be(src, &length);
265
+
266
+ if (!(ptr = mochilo_src_peek(src, length)))
267
+ return -1;
268
+
269
+ *_value = moapi_bytes_new(ptr, length);
270
+ return 0;
271
+ }
272
+
273
+ case MSGPACK_T_BIN16:
218
274
  {
219
275
  uint16_t length;
220
276
  const char *ptr;
@@ -229,7 +285,7 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
229
285
  return 0;
230
286
  }
231
287
 
232
- case MSGPACK_T_RAW32:
288
+ case MSGPACK_T_BIN32:
233
289
  {
234
290
  uint32_t length;
235
291
  const char *ptr;
@@ -268,7 +324,7 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
268
324
  if (!(ptr = mochilo_src_peek(src, length)))
269
325
  return -1;
270
326
 
271
- *_value = moapi_bytes_new(ptr, length);
327
+ *_value = moapi_str_new(ptr, length, MSGPACK_ENC_UTF_8);
272
328
  return 0;
273
329
  }
274
330
 
@@ -276,4 +332,3 @@ int mochilo_unpack_one(mo_value *_value, mochilo_src *src)
276
332
  }
277
333
  }
278
334
  }
279
-
@@ -1,3 +1,3 @@
1
1
  module Mochilo
2
- VERSION = "1.2.1"
2
+ VERSION = "2.0"
3
3
  end
@@ -13,10 +13,12 @@ Gem::Specification.new do |s|
13
13
  s.require_paths = ["lib"]
14
14
  s.rubygems_version = %q{1.4.2}
15
15
  s.summary = %q{A ruby library for BananaPack}
16
- s.test_files = `git ls-files test`.split("\n")
16
+ s.test_files = `git ls-files spec`.split("\n")
17
17
  s.required_ruby_version = ">= 1.9.3"
18
18
 
19
19
  # tests
20
20
  s.add_development_dependency 'rake-compiler', ">= 0.8.1"
21
21
  s.add_development_dependency 'minitest', ">= 4.1.0"
22
+ # benchmarks
23
+ s.add_development_dependency 'msgpack'
22
24
  end
@@ -12,5 +12,5 @@ cd "$(dirname "$0")/.."
12
12
  if bundle check 1>/dev/null 2>&1; then
13
13
  echo "Gem environment up-to-date"
14
14
  else
15
- exec bundle install --binstubs --path vendor/gems --without benchmark "$@"
15
+ exec bundle install --binstubs --path vendor/gems "$@"
16
16
  fi
@@ -4,7 +4,7 @@ require File.expand_path('../setup', __FILE__)
4
4
  require 'mochilo'
5
5
  require 'stringio'
6
6
 
7
- class MochiloPackTest < MiniTest::Unit::TestCase
7
+ class MochiloPackTest < Minitest::Test
8
8
 
9
9
  OBJECTS = [
10
10
  {"hello" => "world"},
@@ -52,122 +52,222 @@ class MochiloPackTest < MiniTest::Unit::TestCase
52
52
  end
53
53
 
54
54
  def test_pack_positive_fixed
55
- assert_equal "\x15", Mochilo.pack(21)
55
+ [0,127].each do |int|
56
+ assert_equal int.chr, Mochilo.pack(int)
57
+ end
56
58
  end
57
59
 
58
60
  def test_pack_negative_fixed
59
- assert_equal "\xEB", Mochilo.pack(-21)
61
+ assert_equal "\xFF", Mochilo.pack(-1)
62
+ assert_equal "\xE0", Mochilo.pack(-32)
60
63
  end
61
64
 
62
65
  def test_pack_uint8
63
- assert_equal "\xCC\xD6", Mochilo.pack(214)
66
+ [128,255].each do |int|
67
+ assert_equal "\xCC#{int.chr}", Mochilo.pack(int)
68
+ end
64
69
  end
65
70
 
66
71
  def test_pack_uint16
67
- assert_equal "\xCDS\xE2", Mochilo.pack(21474)
72
+ [256,((2**16)-1)].each do |int|
73
+ packed = [int].pack("n")
74
+ assert_equal "\xCD#{packed}", Mochilo.pack(int)
75
+ end
68
76
  end
69
77
 
70
78
  def test_pack_uint32
71
- assert_equal "\xCE\x7F\xFF\xFF\xFF", Mochilo.pack(2147483647)
79
+ [(2**16),((2**32)-1)].each do |int|
80
+ packed = [int].pack("N")
81
+ assert_equal "\xCE#{packed}", Mochilo.pack(int)
82
+ end
72
83
  end
73
84
 
74
85
  def test_pack_uint64
75
- assert_equal "\xCF\x00\x00\x00\x04\xFF\xFF\xFF\xFF", Mochilo.pack(21474836479)
86
+ [(2**32),((2**64)-1)].each do |int|
87
+ packed = [int].pack("Q>")
88
+ assert_equal "\xCF#{packed}", Mochilo.pack(int)
89
+ end
76
90
  end
77
91
 
78
92
  def test_pack_int8
79
- assert_equal "\xD0\xDE", Mochilo.pack(-34)
93
+ assert_equal "\xD0\xDF", Mochilo.pack(-33)
94
+ assert_equal "\xD0\x80", Mochilo.pack(-128)
80
95
  end
81
96
 
82
97
  def test_pack_int16
83
- assert_equal "\xD1\xAC\x1E", Mochilo.pack(-21474)
98
+ assert_equal "\xD1\xFF\x7F", Mochilo.pack(-129)
99
+ assert_equal "\xD1\x80\x00", Mochilo.pack(-32768)
84
100
  end
85
101
 
86
102
  def test_pack_int32
87
- assert_equal "\xD2\x80\x00\x00\x01", Mochilo.pack(-2147483647)
103
+ assert_equal "\xD2\xFF\xFF\x7F\xFF", Mochilo.pack(-32769)
104
+ assert_equal "\xD2\x80\x00\x00\x00", Mochilo.pack(-2147483648)
88
105
  end
89
106
 
90
107
  def test_pack_int64
91
- assert_equal "\xD3\xFF\xFF\xFF\xFB\x00\x00\x00\x01", Mochilo.pack(-21474836479)
108
+ assert_equal "\xD3\xFF\xFF\xFF\xFF\x7F\xFF\xFF\xFF", Mochilo.pack(-2147483649)
109
+ assert_equal "\xD3\x80\x00\x00\x00\x00\x00\x00\x00", Mochilo.pack(-9223372036854775808)
92
110
  end
93
111
 
94
- if defined?(Encoding)
95
- def test_pack_str16
96
- str = "this is a test".force_encoding('UTF-8')
97
- assert_equal "\xD8\x00\x0E\x00#{str}", Mochilo.pack(str)
98
- end
112
+ def test_pack_fixed_str
113
+ str = "a".force_encoding('UTF-8')
114
+ assert_equal "\xA1#{str}", Mochilo.pack(str)
115
+
116
+ str = ("a"*31).force_encoding('UTF-8')
117
+ assert_equal "\xBF#{str}", Mochilo.pack(str)
99
118
  end
100
119
 
101
- def xtest_pack_str32
102
- # TODO: not sure how to test this without making a massive 66k string
120
+ def test_pack_str8
121
+ str = ("a"*32).force_encoding('UTF-8')
122
+ assert_equal "\xD9#{str.bytesize.chr}#{str}", Mochilo.pack(str)
123
+
124
+ str = ("a"*255).force_encoding('UTF-8')
125
+ assert_equal "\xD9#{str.bytesize.chr}#{str}", Mochilo.pack(str)
103
126
  end
104
127
 
105
- def test_pack_fixed_raw
106
- str = "this is a test"
107
- assert_equal "\xAE#{str}", Mochilo.pack(str)
128
+ def test_pack_str16
129
+ str = ("a"*256).force_encoding('UTF-8')
130
+ assert_equal "\xDA\x01\x00#{str}", Mochilo.pack(str)
131
+
132
+ str = ("a"*(2**16-1)).force_encoding('UTF-8')
133
+ assert_equal "\xDA\xFF\xFF#{str}", Mochilo.pack(str)
108
134
  end
109
135
 
110
- def test_pack_raw16
111
- str = ("a"*255)
112
- assert_equal "\xDA\x00\xFF#{str}", Mochilo.pack(str)
136
+ def test_pack_str32
137
+ str = ("a"*(2**16)).force_encoding('UTF-8')
138
+ assert_equal "\xDB\x00\x01\x00\x00#{str}", Mochilo.pack(str)
139
+
140
+ # This will create a 4GB string, so let's just skip that ;)
141
+ # str = ("a"*(2**32-1)).force_encoding('UTF-8')
142
+ # assert_equal "\xDB\x00\x01\x00\x00#{str}", Mochilo.pack(str)
113
143
  end
114
144
 
115
- def xtest_pack_raw32
116
- # TODO: not sure how to test this without making a massive 66k string
145
+ def test_pack_enc8
146
+ str = ("a"*32).force_encoding('ISO-8859-1')
147
+ assert_equal "\xC7#{str.bytesize.chr}\x0C#{str}", Mochilo.pack(str)
148
+
149
+ str = ("a"*255).force_encoding('ISO-8859-1')
150
+ assert_equal "\xC7#{str.bytesize.chr}\x0C#{str}", Mochilo.pack(str)
117
151
  end
118
152
 
119
- def test_pack_fixed_array
120
- assert_equal "\x90", Mochilo.pack([])
121
- assert_equal "\x91\x01", Mochilo.pack([1])
153
+ def test_pack_enc16
154
+ str = ("a"*256).force_encoding('ISO-8859-1')
155
+ assert_equal "\xC8\x01\x00\x0C#{str}", Mochilo.pack(str)
156
+
157
+ str = ("a"*(2**16-1)).force_encoding('ISO-8859-1')
158
+ assert_equal "\xC8\xFF\xFF\x0C#{str}", Mochilo.pack(str)
122
159
  end
123
160
 
124
- def test_pack_array16
125
- bytes = ("a"*34).bytes.to_a
126
- assert_equal "\xDC\x00\"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", Mochilo.pack(bytes)
161
+ def test_pack_enc32
162
+ str = ("a"*(2**16)).force_encoding('ISO-8859-1')
163
+ assert_equal "\xC9\x00\x01\x00\x00\x0C#{str}", Mochilo.pack(str)
164
+
165
+ # This would create a 4GB string, so let's just skip that ;)
166
+ # str = ("a"*(2**32-1)).force_encoding('ISO-8859-1')
167
+ # assert_equal "\xC9\x00\x01\x00\x00\x0C#{str}", Mochilo.pack(str)
127
168
  end
128
169
 
129
- def xtest_pack_array32
130
- # TODO: not sure how to test this without making a massive 66k item array
170
+ def test_pack_bin8
171
+ str = ("a"*32).force_encoding('binary')
172
+ assert_equal "\xC4#{str.bytesize.chr}#{str}", Mochilo.pack(str)
173
+
174
+ str = ("a"*255).force_encoding('binary')
175
+ assert_equal "\xC4#{str.bytesize.chr}#{str}", Mochilo.pack(str)
131
176
  end
132
177
 
133
- def test_pack_fixed_map
134
- assert_equal "\x80", Mochilo.pack({})
135
- assert_equal "\x81\x01\x02", Mochilo.pack({1 => 2})
178
+ def test_pack_bin16
179
+ str = ("a"*256).force_encoding('binary')
180
+ assert_equal "\xC5\x01\x00#{str}", Mochilo.pack(str)
181
+
182
+ str = ("a"*(2**16-1)).force_encoding('binary')
183
+ assert_equal "\xC5\xFF\xFF#{str}", Mochilo.pack(str)
136
184
  end
137
185
 
138
- def test_pack_symbol
139
- assert_equal "\xD8\x00\x04\x01test", Mochilo.pack(:test)
140
- assert_equal "\xD4\x04test", Mochilo.pack_unsafe(:test)
186
+ def test_pack_bin32
187
+ str = ("a"*(2**16)).force_encoding('binary')
188
+ assert_equal "\xC6\x00\x01\x00\x00#{str}", Mochilo.pack(str)
189
+
190
+ # This would create a 4GB string, so let's just skip that ;)
191
+ # str = ("a"*(2**32-1)).force_encoding('UTF-8')
192
+ # assert_equal "\xC6\x00\x01\x00\x00#{str}", Mochilo.pack(str)
141
193
  end
142
194
 
143
- def test_pack_symbol_size
144
- too_big = ("a"*0x100).to_sym
145
- fine = ("a"*0xff).to_sym
195
+ def test_pack_fixed_array
196
+ assert_equal "\x90", Mochilo.pack([])
146
197
 
147
- assert_raises Mochilo::PackError do
148
- Mochilo.pack_unsafe(too_big)
149
- end
198
+ arr = (1..15).to_a
199
+ expected = "\x9F"
200
+ arr.each {|i| expected << Mochilo.pack(i)}
201
+ assert_equal expected, Mochilo.pack(arr)
202
+ end
150
203
 
151
- begin
152
- Mochilo.pack_unsafe(fine)
153
- rescue Mochilo::PackError => boom
154
- assert_nil boom, "exception raised, expected nothing"
155
- end
204
+ def test_pack_array16
205
+ arr = (1..16).to_a
206
+ expected = "\xDC\x00\x10"
207
+ arr.each {|i| expected << Mochilo.pack(i)}
208
+ assert_equal expected, Mochilo.pack(arr)
209
+
210
+ arr = (1..2**16-1).to_a
211
+ expected = "\xDC\xFF\xFF"
212
+ arr.each {|i| expected << Mochilo.pack(i)}
213
+ assert_equal expected, Mochilo.pack(arr)
156
214
  end
157
215
 
158
- def test_pack_map16
159
- bytes = ("a"*34).bytes.to_a
160
- assert_equal "\xDC\x00\"aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa", Mochilo.pack(bytes)
216
+ def test_pack_array32
217
+ arr = (1..2**16).to_a
218
+ expected = "\xDD\x00\x01\x00\x00"
219
+ arr.each {|i| expected << Mochilo.pack(i)}
220
+ assert_equal expected, Mochilo.pack(arr)
221
+
222
+ # This would create an array with 4294967295 entries in it, so let's not
223
+ # arr = (1..2**32-1).to_a
224
+ # expected = "\xDD\xFF\xFF\xFF\xFF"
225
+ # arr.each {|i| expected << Mochilo.pack(i)}
226
+ # assert_equal expected, Mochilo.pack(arr)
161
227
  end
162
228
 
163
- def test_pack_map32
164
- # TODO: not sure how to test this without making a massive 66k item hash
229
+ def test_pack_fixed_map
230
+ assert_equal "\x80", Mochilo.pack({})
231
+
232
+ arr = (1..15).to_a
233
+ hash = {}
234
+ arr.each {|i| hash[i] = i }
235
+ expected = "\x8F"
236
+ arr.each {|i| expected << (Mochilo.pack(i) + Mochilo.pack(i))}
237
+ assert_equal expected, Mochilo.pack(hash)
165
238
  end
166
239
 
167
- def test_pack_custom_type
168
- obj = CustomType.new("custom")
240
+ def test_pack_map16
241
+ arr = (1..16).to_a
242
+ hash = {}
243
+ arr.each {|i| hash[i] = i }
244
+ expected = "\xDE\x00\x10"
245
+ arr.each {|i| expected << (Mochilo.pack(i) + Mochilo.pack(i))}
246
+ assert_equal expected, Mochilo.pack(hash)
247
+
248
+ arr = (1..2**16-1).to_a
249
+ hash = {}
250
+ arr.each {|i| hash[i] = i }
251
+ expected = "\xDE\xFF\xFF"
252
+ arr.each {|i| expected << (Mochilo.pack(i) + Mochilo.pack(i))}
253
+ assert_equal expected, Mochilo.pack(hash)
254
+ end
169
255
 
170
- assert_equal "\xA6custom", Mochilo.pack(obj)
256
+ def test_pack_map32
257
+ arr = (1..2**16).to_a
258
+ hash = {}
259
+ arr.each {|i| hash[i] = i }
260
+ expected = "\xDF\x00\x01\x00\x00"
261
+ arr.each {|i| expected << (Mochilo.pack(i) + Mochilo.pack(i))}
262
+ assert_equal expected, Mochilo.pack(hash)
263
+
264
+ # This would create a hash with 4294967295 entries in it, so let's not
265
+ # arr = (1..2**32-1).to_a
266
+ # hash = {}
267
+ # arr.each {|i| hash[i] = i }
268
+ # expected = "\xDF\xFF\xFF\xFF\xFF"
269
+ # arr.each {|i| expected << (Mochilo.pack(i) + Mochilo.pack(i))}
270
+ # assert_equal expected, Mochilo.pack(hash)
171
271
  end
172
272
 
173
273
  def test_pack_unsupported_type
@@ -175,4 +275,10 @@ class MochiloPackTest < MiniTest::Unit::TestCase
175
275
  Mochilo.pack(Object.new)
176
276
  end
177
277
  end
278
+
279
+ def test_pack_symbol_fails
280
+ assert_raises Mochilo::PackError do
281
+ Mochilo.pack(:symbol)
282
+ end
283
+ end
178
284
  end