cbor-x 1.6.4 → 1.6.6

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.
package/dist/index.js CHANGED
@@ -234,13 +234,22 @@
234
234
  }
235
235
  }
236
236
 
237
+ function endOfCBORError() {
238
+ let error = new Error('Unexpected end of CBOR data');
239
+ error.incomplete = true;
240
+ return error
241
+ }
242
+
237
243
  function read() {
244
+ // compared as < so that a NaN position (from a corrupt length) also throws instead of reading undefined
245
+ if (!(position$1 < srcEnd)) throw endOfCBORError()
238
246
  let token = src[position$1++];
239
247
  let majorType = token >> 5;
240
248
  token = token & 0x1f;
241
249
  if (token > 0x17) {
242
250
  switch (token) {
243
251
  case 0x18:
252
+ if (position$1 >= srcEnd) throw endOfCBORError()
244
253
  token = src[position$1++];
245
254
  break
246
255
  case 0x19:
@@ -369,6 +378,9 @@
369
378
  return readFixedString(token)
370
379
  case 4: // array
371
380
  if (token >= maxArraySize) throw new Error(`Array length exceeds ${maxArraySize}`)
381
+ // every element occupies at least one byte, so a length beyond what remains in the source can
382
+ // never be satisfied; check before allocating so a tiny header can not force a huge allocation
383
+ if (token > srcEnd - position$1) throw endOfCBORError()
372
384
  let array = new Array(token);
373
385
  //if (currentDecoder.keyMap) for (let i = 0; i < token; i++) array[i] = currentDecoder.decodeKey(read())
374
386
  //else
@@ -376,6 +388,7 @@
376
388
  return array
377
389
  case 5: // map
378
390
  if (token >= maxMapSize) throw new Error(`Map size exceeds ${maxArraySize}`)
391
+ if (token > (srcEnd - position$1) / 2) throw endOfCBORError() // each entry needs at least two bytes
379
392
  if (currentDecoder.mapsAsObjects) {
380
393
  let object = {};
381
394
  if (currentDecoder.keyMap) for (let i = 0; i < token; i++) object[safeKey(currentDecoder.decodeKey(read()))] = read();
@@ -467,11 +480,7 @@
467
480
  throw new Error('Unknown token ' + token)
468
481
  }
469
482
  default: // negative int
470
- if (isNaN(token)) {
471
- let error = new Error('Unexpected end of CBOR data');
472
- error.incomplete = true;
473
- throw error
474
- }
483
+ if (isNaN(token)) throw endOfCBORError()
475
484
  throw new Error('Unknown CBOR token ' + token)
476
485
  }
477
486
  }
@@ -560,43 +569,49 @@
560
569
  units.push(byte1);
561
570
  } else if ((byte1 & 0xe0) === 0xc0) {
562
571
  // 2 bytes
563
- const byte2 = src[position$1++] & 0x3f;
564
- const codePoint = ((byte1 & 0x1f) << 6) | byte2;
565
- // Reject overlong encoding: 2-byte sequences must encode values >= 0x80
566
- if (codePoint < 0x80) {
567
- units.push(0xFFFD); // replacement character
572
+ if (byte1 < 0xc2 || position$1 >= end || (src[position$1] & 0xc0) !== 0x80) {
573
+ units.push(0xFFFD);
568
574
  } else {
569
- units.push(codePoint);
575
+ const byte2 = src[position$1++] & 0x3f;
576
+ units.push(((byte1 & 0x1f) << 6) | byte2);
570
577
  }
571
578
  } else if ((byte1 & 0xf0) === 0xe0) {
572
579
  // 3 bytes
573
- const byte2 = src[position$1++] & 0x3f;
574
- const byte3 = src[position$1++] & 0x3f;
575
- const codePoint = ((byte1 & 0x1f) << 12) | (byte2 << 6) | byte3;
576
- // Reject overlong encoding: 3-byte sequences must encode values >= 0x800
577
- // Also reject surrogates (0xD800-0xDFFF)
578
- if (codePoint < 0x800 || (codePoint >= 0xD800 && codePoint <= 0xDFFF)) {
579
- units.push(0xFFFD); // replacement character
580
+ const byte2 = position$1 < end ? src[position$1] : 0;
581
+ if (position$1 >= end || (byte2 & 0xc0) !== 0x80 ||
582
+ (byte1 === 0xe0 && byte2 < 0xa0) || (byte1 === 0xed && byte2 >= 0xa0)) {
583
+ units.push(0xFFFD);
580
584
  } else {
581
- units.push(codePoint);
585
+ position$1++;
586
+ if (position$1 >= end || (src[position$1] & 0xc0) !== 0x80) {
587
+ units.push(0xFFFD);
588
+ } else {
589
+ const byte3 = src[position$1++] & 0x3f;
590
+ units.push(((byte1 & 0x1f) << 12) | ((byte2 & 0x3f) << 6) | byte3);
591
+ }
582
592
  }
583
593
  } else if ((byte1 & 0xf8) === 0xf0) {
584
594
  // 4 bytes
585
- const byte2 = src[position$1++] & 0x3f;
586
- const byte3 = src[position$1++] & 0x3f;
587
- const byte4 = src[position$1++] & 0x3f;
588
- let unit = ((byte1 & 0x07) << 0x12) | (byte2 << 0x0c) | (byte3 << 0x06) | byte4;
589
- // Reject overlong encoding: 4-byte sequences must encode values >= 0x10000
590
- // Also reject values > 0x10FFFF (maximum valid Unicode)
591
- if (unit < 0x10000 || unit > 0x10FFFF) {
592
- units.push(0xFFFD); // replacement character
593
- } else if (unit > 0xffff) {
594
- unit -= 0x10000;
595
- units.push(((unit >>> 10) & 0x3ff) | 0xd800);
596
- unit = 0xdc00 | (unit & 0x3ff);
597
- units.push(unit);
595
+ const byte2 = position$1 < end ? src[position$1] : 0;
596
+ if (byte1 > 0xf4 || position$1 >= end || (byte2 & 0xc0) !== 0x80 ||
597
+ (byte1 === 0xf0 && byte2 < 0x90) || (byte1 === 0xf4 && byte2 >= 0x90)) {
598
+ units.push(0xFFFD);
598
599
  } else {
599
- units.push(unit);
600
+ position$1++;
601
+ if (position$1 >= end || (src[position$1] & 0xc0) !== 0x80) {
602
+ units.push(0xFFFD);
603
+ } else {
604
+ const byte3 = src[position$1++] & 0x3f;
605
+ if (position$1 >= end || (src[position$1] & 0xc0) !== 0x80) {
606
+ units.push(0xFFFD);
607
+ } else {
608
+ const byte4 = src[position$1++] & 0x3f;
609
+ let unit = ((byte1 & 0x07) << 0x12) | ((byte2 & 0x3f) << 0x0c) | (byte3 << 0x06) | byte4;
610
+ unit -= 0x10000;
611
+ units.push(((unit >>> 10) & 0x3ff) | 0xd800);
612
+ units.push(0xdc00 | (unit & 0x3ff));
613
+ }
614
+ }
600
615
  }
601
616
  } else {
602
617
  units.push(0xFFFD); // replacement character for invalid lead byte
@@ -1094,10 +1109,12 @@
1094
1109
  }
1095
1110
 
1096
1111
  function readJustLength() {
1112
+ if (!(position$1 < srcEnd)) throw endOfCBORError()
1097
1113
  let token = src[position$1++] & 0x1f;
1098
1114
  if (token > 0x17) {
1099
1115
  switch (token) {
1100
1116
  case 0x18:
1117
+ if (position$1 >= srcEnd) throw endOfCBORError()
1101
1118
  token = src[position$1++];
1102
1119
  break
1103
1120
  case 0x19: