Skip to content

Commit 2cfda99

Browse files
committed
Merge pull request #2 from redboltz/add_bin_support
Added bin format family support.
2 parents da6d906 + caea0e4 commit 2cfda99

File tree

3 files changed

+132
-19
lines changed

3 files changed

+132
-19
lines changed

msgpack.codec.js

+32-4
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,9 @@ var _bin2num = {}, // BinaryStringToNumber { "\00": 0, ... "\ff": 255 }
2323
_isArray = Array.isArray || (function(mix) {
2424
return Object.prototype.toString.call(mix) === "[object Array]";
2525
}),
26+
_isUint8Array = function(mix) {
27+
return Object.prototype.toString.call(mix) === "[object Uint8Array]";
28+
},
2629
_toString = String.fromCharCode, // CharCode/ByteArray to String
2730
_MAX_DEPTH = 512;
2831

@@ -176,6 +179,8 @@ function encode(rv, // @param ByteArray: result
176179

177180
if (size < 32) {
178181
rv[pos] = 0xa0 + size; // rewrite
182+
} else if (size < 0x100) { // 8
183+
rv.splice(pos, 1, 0xd9, size);
179184
} else if (size < 0x10000) { // 16
180185
rv.splice(pos, 1, 0xda, size >> 8, size & 0xff);
181186
} else if (size < 0x100000000) { // 32
@@ -184,7 +189,21 @@ function encode(rv, // @param ByteArray: result
184189
(size >> 8) & 0xff, size & 0xff);
185190
}
186191
break;
187-
default: // array or hash
192+
default: // array, hash, or Uint8Array
193+
if (_isUint8Array(mix)) {
194+
size = mix.length;
195+
196+
if (size < 0x100) { // 8
197+
rv.push(0xc4, size);
198+
} else if (size < 0x10000) { // 16
199+
rv.push(0xc5, size >> 8, size & 0xff);
200+
} else if (size < 0x100000000) { // 32
201+
rv.push(0xc6, size >>> 24, (size >> 16) & 0xff,
202+
(size >> 8) & 0xff, size & 0xff);
203+
}
204+
Array.prototype.push.apply(rv, mix);
205+
break;
206+
}
188207
if (++depth >= _MAX_DEPTH) {
189208
_error = 1; // CYCLIC_REFERENCE_ERROR
190209
return rv = []; // clear
@@ -324,9 +343,10 @@ function decode() { // @return Mix:
324343
return num < 0x8000 ? num : num - 0x10000; // 0x8000 * 2
325344
case 0xd0: num = buf[++_idx];
326345
return num < 0x80 ? num : num - 0x100; // 0x80 * 2
327-
// 0xdb: raw32, 0xda: raw16, 0xa0: raw ( string )
328-
case 0xdb: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
329-
case 0xda: num += (buf[++_idx] << 8) + buf[++_idx];
346+
// 0xdb: str32, 0xda: str16, 0xd9: str8, 0xa0: fixstr
347+
case 0xdb: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
348+
case 0xda: num += buf[++_idx] << 8;
349+
case 0xd9: num += buf[++_idx];
330350
case 0xa0: // utf8.decode
331351
for (ary = [], i = _idx, iz = i + num; i < iz; ) {
332352
c = buf[++i]; // lead byte
@@ -338,6 +358,14 @@ function decode() { // @return Mix:
338358
_idx = i;
339359
return ary.length < 10240 ? _toString.apply(null, ary)
340360
: byteArrayToByteString(ary);
361+
// 0xc6: bin32, 0xc5: bin16, 0xc4: bin8
362+
case 0xc6: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
363+
case 0xc5: num += buf[++_idx] << 8;
364+
case 0xc4: num += buf[++_idx];
365+
var end = ++_idx + num
366+
var ret = buf.slice(_idx, end);
367+
_idx += num;
368+
return ret;
341369
// 0xdf: map32, 0xde: map16, 0x80: map
342370
case 0xdf: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
343371
case 0xde: num += (buf[++_idx] << 8) + buf[++_idx];

msgpack.js

+32-4
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,9 @@ var _ie = /MSIE/.test(navigator.userAgent),
2929
_isArray = Array.isArray || (function(mix) {
3030
return Object.prototype.toString.call(mix) === "[object Array]";
3131
}),
32+
_isUint8Array = function(mix) {
33+
return Object.prototype.toString.call(mix) === "[object Uint8Array]";
34+
},
3235
_toString = String.fromCharCode, // CharCode/ByteArray to String
3336
_MAX_DEPTH = 512;
3437

@@ -191,6 +194,8 @@ function encode(rv, // @param ByteArray: result
191194

192195
if (size < 32) {
193196
rv[pos] = 0xa0 + size; // rewrite
197+
} else if (size < 0x100) { // 8
198+
rv.splice(pos, 1, 0xd9, size);
194199
} else if (size < 0x10000) { // 16
195200
rv.splice(pos, 1, 0xda, size >> 8, size & 0xff);
196201
} else if (size < 0x100000000) { // 32
@@ -199,7 +204,21 @@ function encode(rv, // @param ByteArray: result
199204
(size >> 8) & 0xff, size & 0xff);
200205
}
201206
break;
202-
default: // array or hash
207+
default: // array, hash, or Uint8Array
208+
if (_isUint8Array(mix)) {
209+
size = mix.length;
210+
211+
if (size < 0x100) { // 8
212+
rv.push(0xc4, size);
213+
} else if (size < 0x10000) { // 16
214+
rv.push(0xc5, size >> 8, size & 0xff);
215+
} else if (size < 0x100000000) { // 32
216+
rv.push(0xc6, size >>> 24, (size >> 16) & 0xff,
217+
(size >> 8) & 0xff, size & 0xff);
218+
}
219+
Array.prototype.push.apply(rv, mix);
220+
break;
221+
}
203222
if (++depth >= _MAX_DEPTH) {
204223
_error = 1; // CYCLIC_REFERENCE_ERROR
205224
return rv = []; // clear
@@ -339,9 +358,10 @@ function decode() { // @return Mix:
339358
return num < 0x8000 ? num : num - 0x10000; // 0x8000 * 2
340359
case 0xd0: num = buf[++_idx];
341360
return num < 0x80 ? num : num - 0x100; // 0x80 * 2
342-
// 0xdb: raw32, 0xda: raw16, 0xa0: raw ( string )
343-
case 0xdb: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
344-
case 0xda: num += (buf[++_idx] << 8) + buf[++_idx];
361+
// 0xdb: str32, 0xda: str16, 0xd9: str8, 0xa0: fixstr
362+
case 0xdb: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
363+
case 0xda: num += buf[++_idx] << 8;
364+
case 0xd9: num += buf[++_idx];
345365
case 0xa0: // utf8.decode
346366
for (ary = [], i = _idx, iz = i + num; i < iz; ) {
347367
c = buf[++i]; // lead byte
@@ -353,6 +373,14 @@ function decode() { // @return Mix:
353373
_idx = i;
354374
return ary.length < 10240 ? _toString.apply(null, ary)
355375
: byteArrayToByteString(ary);
376+
// 0xc6: bin32, 0xc5: bin16, 0xc4: bin8
377+
case 0xc6: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
378+
case 0xc5: num += buf[++_idx] << 8;
379+
case 0xc4: num += buf[++_idx];
380+
var end = ++_idx + num
381+
var ret = buf.slice(_idx, end);
382+
_idx += num;
383+
return ret;
356384
// 0xdf: map32, 0xde: map16, 0x80: map
357385
case 0xdf: num += buf[++_idx] * 0x1000000 + (buf[++_idx] << 16);
358386
case 0xde: num += (buf[++_idx] << 8) + buf[++_idx];

test/codec.htm

+68-11
Original file line numberDiff line numberDiff line change
@@ -486,31 +486,52 @@
486486

487487
return [rv, "==", -3.14159565358979, hex(pack)];
488488
},
489-
"Raw (as String)": "",
490-
"String('') -> [0xa0] (FixRaw)": function() {
489+
"Str (as String)": "",
490+
"String('') -> [0xa0] (FixStr)": function() {
491491
var pack = msgpack.pack("");
492492
var rv = msgpack.unpack(pack);
493493

494494
return [rv, "==", "", hex(pack)];
495495
},
496-
"String('abc') -> [0xa3, 0x61, 0x62, 0x63] (FixRaw)": function() {
496+
"String('abc') -> [0xa3, 0x61, 0x62, 0x63] (FixStr)": function() {
497497
var pack = msgpack.pack("abc");
498498
var rv = msgpack.unpack(pack);
499499

500500
return [rv, "==", "abc", hex(pack)];
501501
},
502-
"String('あいう') -> [0xa9, 0xe3, 0x81, 0x82, 0xe3, 0x81, 0x84, 0xe3, 0x81, 0x86] (FixRaw)": function() {
502+
"String('あいう') -> [0xa9, 0xe3, 0x81, 0x82, 0xe3, 0x81, 0x84, 0xe3, 0x81, 0x86] (FixStr)": function() {
503503
var pack = msgpack.pack("あいう");
504504
var rv = msgpack.unpack(pack);
505505

506506
return [rv, "==", "あいう", hex(pack)];
507507
},
508-
"String('カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで') -> [] (Raw16)": function() {
508+
"String('カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで') -> [] (Str8)": function() {
509509
var pack = msgpack.pack("カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで");
510510
var rv = msgpack.unpack(pack);
511511

512512
return [rv, "==", "カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで", hex(pack)];
513513
},
514+
"String('カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで、あとナポリタンと天丼、スープカレーに餃子とチャーハン、それからそれからビーフストロガノフとアクアパッツァ、すき焼きにざるそば') -> [] (Str16)": function() {
515+
var pack = msgpack.pack("カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで、あとナポリタンと天丼、スープカレーに餃子とチャーハン、それからそれからビーフストロガノフとアクアパッツァ、すき焼きにざるそば");
516+
var rv = msgpack.unpack(pack);
517+
518+
return [rv, "==", "カルビx3, ハラミx2, ブタバラ, T-BORNx500g, ライス大盛りで、あとナポリタンと天丼、スープカレーに餃子とチャーハン、それからそれからビーフストロガノフとアクアパッツァ、すき焼きにざるそば", hex(pack)];
519+
},
520+
"Bin (as Uint8Array)": "",
521+
"Uint8Array(1,2,3) -> [1,2,3] (Bin8)": function() {
522+
var pack = msgpack.pack(new Uint8Array([1,2,3]));
523+
var rv = msgpack.unpack(pack);
524+
525+
return [rv, "==", [1,2,3], hex(pack)];
526+
},
527+
"Uint8Array(0..255) -> [0..255] (Bin16)": function() {
528+
var expected = new Array(256);
529+
for (var i = 0; i < 256; ++i) expected[i] = i;
530+
var pack = msgpack.pack(new Uint8Array(expected));
531+
var rv = msgpack.unpack(pack);
532+
533+
return [rv, "==", expected, hex(pack)];
534+
},
514535
"Map (as Hash)": "",
515536
"Hash({}) -> [0x80] (FixMap)": function() {
516537
var pack = msgpack.pack({});
@@ -769,50 +790,86 @@
769790
return [rv, "==", -1.0, hex(result)];
770791
},
771792

772-
'[a1 61] "a" FixRaw': function() {
793+
'[a1 61] "a" FixStr': function() {
773794
var data = unescape('%a1%61');
774795
var result = [0xa1, 0x61];
775796
var rv = msgpack.unpack(data);
776797

777798
return [rv, "==", "a", hex(result)];
778799
},
779-
'[da 00 01 61] "a" raw 16': function() {
800+
'[d9 01 61] "a" str 8': function() {
801+
var data = unescape('%d9%01%61');
802+
var result = [0xda, 0x01, 0x61];
803+
var rv = msgpack.unpack(data);
804+
805+
return [rv, "==", "a", hex(result)];
806+
},
807+
'[da 00 01 61] "a" str 16': function() {
780808
var data = unescape('%da%00%01%61');
781809
var result = [0xda, 0x00, 0x01, 0x61];
782810
var rv = msgpack.unpack(data);
783811

784812
return [rv, "==", "a", hex(result)];
785813
},
786-
'[db 00 00 00 01 61] "a" raw 32': function() {
814+
'[db 00 00 00 01 61] "a" str 32': function() {
787815
var data = unescape('%db%00%00%00%01%61');
788816
var result = [0xdb, 0x00, 0x00, 0x00, 0x01, 0x61];
789817
var rv = msgpack.unpack(data);
790818

791819
return [rv, "==", "a", hex(result)];
792820
},
793821

794-
'[a0] "" FixRaw': function() {
822+
'[a0] "" FixStr': function() {
795823
var data = unescape('%a0');
796824
var result = [0xa0];
797825
var rv = msgpack.unpack(data);
798826

799827
return [rv, "==", "", hex(result)];
800828
},
801-
'[da 00 00] "" raw 16': function() {
829+
'[d9 00] "" str 8': function() {
830+
var data = unescape('%d9%00');
831+
var result = [0xd9, 0x00];
832+
var rv = msgpack.unpack(data);
833+
834+
return [rv, "==", "", hex(result)];
835+
},
836+
'[da 00 00] "" str 16': function() {
802837
var data = unescape('%da%00%00');
803838
var result = [0xda, 0x00, 0x00];
804839
var rv = msgpack.unpack(data);
805840

806841
return [rv, "==", "", hex(result)];
807842
},
808-
'[db 00 00 00 00] "" raw 32': function() {
843+
'[db 00 00 00 00] "" str 32': function() {
809844
var data = unescape('%db%00%00%00%00');
810845
var result = [0xdb, 0x00, 0x00, 0x00, 0x00];
811846
var rv = msgpack.unpack(data);
812847

813848
return [rv, "==", "", hex(result)];
814849
},
815850

851+
'[c4 00] "" bin 8': function() {
852+
var data = unescape('%c4%00');
853+
var result = [0xc4, 0x00];
854+
var rv = msgpack.unpack(data);
855+
856+
return [rv, "==", [], hex(result)];
857+
},
858+
'[c5 00 00] "" bin 16': function() {
859+
var data = unescape('%c5%00%00');
860+
var result = [0xc5, 0x00, 0x00];
861+
var rv = msgpack.unpack(data);
862+
863+
return [rv, "==", [], hex(result)];
864+
},
865+
'[c6 00 00 00 00] "" bin 32': function() {
866+
var data = unescape('%c6%00%00%00%00');
867+
var result = [0xc6, 0x00, 0x00, 0x00, 0x00];
868+
var rv = msgpack.unpack(data);
869+
870+
return [rv, "==", [], hex(result)];
871+
},
872+
816873
'[91 00] [0] FixArray': function() {
817874
var data = unescape('%91%00');
818875
var result = [0x91, 0x00];

0 commit comments

Comments
 (0)