helpers.js 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143
  1. // helpers
  2. //? if (NODE) {
  3. /**
  4. * @type {!Buffer}
  5. * @inner
  6. */
  7. var EMPTY_BUFFER = new Buffer(0);
  8. //? } else {
  9. /**
  10. * @type {!ArrayBuffer}
  11. * @inner
  12. */
  13. var EMPTY_BUFFER = new ArrayBuffer(0);
  14. //? }
  15. //? if (!INLINE) {
  16. /**
  17. * Asserts that a value is an integer and returns the type-safe value.
  18. * @param {number} value Value to assert
  19. * @param {boolean=} unsigned Whether explicitly unsigned
  20. * @returns {number} Type-safe value
  21. * @throws {TypeError} If `value` is not an integer
  22. * @inner
  23. */
  24. function assertInteger(value, unsigned) {
  25. if (typeof value !== 'number' || value % 1 !== 0)
  26. throw TypeError("Illegal value: "+offset+" (not an integer)");
  27. return unsigned ? value >>> 0 : value | 0;
  28. }
  29. /**
  30. * Asserts that a value is an integer or Long.
  31. * @param {number|!Long} value Value to assert
  32. * @param {boolean=} unsigned Whether explicitly unsigned
  33. * @returns {number|!Long} Type-safe value
  34. * @throws {TypeError} If `value` is not an integer or Long
  35. * @inner
  36. */
  37. function assertLong(value, unsigned) {
  38. if (typeof value === 'number') {
  39. return Long.fromNumber(value, unsigned);
  40. } else if (typeof value === 'string') {
  41. return Long.fromString(value, unsigned);
  42. } else if (value && value instanceof Long) {
  43. if (typeof unsigned !== 'undefined') {
  44. if (unsigned && !value.unsigned) return value.toUnsigned();
  45. if (!unsigned && value.unsigned) return value.toSigned();
  46. }
  47. return value;
  48. } else
  49. throw TypeError("Illegal value: "+value+" (not an integer or Long)");
  50. }
  51. /**
  52. * Asserts that `min <= offset <= cap-size` and returns the type-safe offset.
  53. * @param {number} offset Offset to assert
  54. * @param {number} min Minimum offset
  55. * @param {number} cap Cap offset
  56. * @param {number} size Required size in bytes
  57. * @returns {number} Type-safe offset
  58. * @throws {TypeError} If `offset` is not an integer
  59. * @throws {RangeError} If `offset < min || offset > cap-size`
  60. * @inner
  61. */
  62. function assertOffset(offset, min, cap, size) {
  63. if (typeof offset !== 'number' || offset % 1 !== 0)
  64. throw TypeError("Illegal offset: "+offset+" (not an integer)");
  65. offset = offset | 0;
  66. if (offset < min || offset > cap-size)
  67. throw RangeError("Illegal offset: "+min+" <= "+value+" <= "+cap+"-"+size);
  68. return offset;
  69. }
  70. /**
  71. * assertRange return value.
  72. * @type {Array.<number>}
  73. */
  74. var rangeVal = new Array(2);
  75. /**
  76. * Asserts that `min <= begin <= end <= cap`. Updates `rangeVal` with the type-safe range.
  77. * @param {number} begin Begin offset
  78. * @param {number} end End offset
  79. * @param {number} min Minimum offset
  80. * @param {number} cap Cap offset
  81. * @throws {TypeError} If `begin` or `end` is not an integer
  82. * @throws {RangeError} If `begin < min || begin > end || end > cap`
  83. * @inner
  84. */
  85. function assertRange(begin, end, min, cap) {
  86. if (typeof begin !== 'number' || begin % 1 !== 0)
  87. throw TypeError("Illegal begin: "+begin+" (not a number)");
  88. begin = begin | 0;
  89. if (typeof end !== 'number' || end % 1 !== 0)
  90. throw TypeError("Illegal end: "+range[1]+" (not a number)");
  91. end = end | 0;
  92. if (begin < min || begin > end || end > cap)
  93. throw RangeError("Illegal range: "+min+" <= "+begin+" <= "+end+" <= "+cap);
  94. rangeVal[0] = begin; rangeVal[1] = end;
  95. }
  96. //? }
  97. //? if (BASE64 || UTF8) {
  98. /**
  99. * String.fromCharCode reference for compile-time renaming.
  100. * @type {function(...number):string}
  101. * @inner
  102. */
  103. var stringFromCharCode = String.fromCharCode;
  104. /**
  105. * Creates a source function for a string.
  106. * @param {string} s String to read from
  107. * @returns {function():number|null} Source function returning the next char code respectively `null` if there are
  108. * no more characters left.
  109. * @throws {TypeError} If the argument is invalid
  110. * @inner
  111. */
  112. function stringSource(s) {
  113. var i=0; return function() {
  114. return i < s.length ? s.charCodeAt(i++) : null;
  115. };
  116. }
  117. /**
  118. * Creates a destination function for a string.
  119. * @returns {function(number=):undefined|string} Destination function successively called with the next char code.
  120. * Returns the final string when called without arguments.
  121. * @inner
  122. */
  123. function stringDestination() {
  124. var cs = [], ps = []; return function() {
  125. if (arguments.length === 0)
  126. return ps.join('')+stringFromCharCode.apply(String, cs);
  127. if (cs.length + arguments.length > 1024)
  128. ps.push(stringFromCharCode.apply(String, cs)),
  129. cs.length = 0;
  130. Array.prototype.push.apply(cs, arguments);
  131. };
  132. }
  133. //? }