bin-serde 1.6.2 → 1.6.4

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.
Files changed (3) hide show
  1. package/index.ts +40 -7
  2. package/lib/index.js +35 -7
  3. package/package.json +1 -1
package/index.ts CHANGED
@@ -7,6 +7,9 @@ const MAX_POOLED = 4096;
7
7
  let slab: Uint8Array = new Uint8Array(SLAB_SIZE);
8
8
  let slabOffset = 0;
9
9
 
10
+ const f32 = new Float32Array(1);
11
+ const f32u8 = new Uint8Array(f32.buffer);
12
+
10
13
  function allocFromSlab(size: number): Uint8Array {
11
14
  if (size > MAX_POOLED) {
12
15
  // Too large for pool, allocate directly
@@ -53,23 +56,47 @@ export class Writer {
53
56
 
54
57
  writeUVarint(val: number) {
55
58
  if (val < 0x80) {
59
+ // 1 byte: 0-127
56
60
  this.writeUInt8(val);
57
61
  } else if (val < 0x4000) {
62
+ // 2 bytes: 128 - 16,383
58
63
  this.writeUInt16((val & 0x7f) | ((val & 0x3f80) << 1) | 0x8000);
59
64
  } else if (val < 0x200000) {
65
+ // 3 bytes: 16,384 - 2,097,151
60
66
  this.writeUInt8((val >> 14) | 0x80);
61
67
  this.writeUInt16((val & 0x7f) | ((val & 0x3f80) << 1) | 0x8000);
62
68
  } else if (val < 0x10000000) {
69
+ // 4 bytes: 2,097,152 - 268,435,455
63
70
  this.writeUInt32(
64
71
  (val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000
65
72
  );
66
73
  } else if (val < 0x800000000) {
74
+ // 5 bytes: 268,435,456 - 34,359,738,367
67
75
  this.writeUInt8(Math.floor(val / 0x10000000) | 0x80);
68
76
  this.writeUInt32(
69
77
  (val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000
70
78
  );
71
79
  } else if (val < 0x40000000000) {
80
+ // 6 bytes: 34,359,738,368 - 4,398,046,511,103
81
+ const shiftedVal = Math.floor(val / 0x10000000);
82
+ this.writeUInt16((shiftedVal & 0x7f) | ((shiftedVal & 0x3f80) << 1) | 0x8080);
83
+ this.writeUInt32(
84
+ (val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000
85
+ );
86
+ } else if (val < 0x2000000000000) {
87
+ // 7 bytes: 4,398,046,511,104 - 562,949,953,421,311
72
88
  const shiftedVal = Math.floor(val / 0x10000000);
89
+ this.writeUInt8((Math.floor(shiftedVal / 0x4000) & 0x7f) | 0x80);
90
+ this.writeUInt16((shiftedVal & 0x7f) | ((shiftedVal & 0x3f80) << 1) | 0x8080);
91
+ this.writeUInt32(
92
+ (val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000
93
+ );
94
+ } else if (val <= Number.MAX_SAFE_INTEGER) {
95
+ // 8 bytes: 562,949,953,421,312 - 9,007,199,254,740,991 (MAX_SAFE_INTEGER)
96
+ const shiftedVal = Math.floor(val / 0x10000000);
97
+ this.writeUInt16(
98
+ (Math.floor(shiftedVal / 0x4000) & 0x7f) | ((Math.floor(shiftedVal / 0x4000) & 0x3f80) << 1) | 0x8080
99
+ );
73
100
  this.writeUInt16((shiftedVal & 0x7f) | ((shiftedVal & 0x3f80) << 1) | 0x8080);
74
101
  this.writeUInt32(
75
102
  (val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000
@@ -81,13 +108,17 @@ export class Writer {
81
108
  }
82
109
 
83
110
  writeVarint(val: number) {
84
- return this.writeUVarint((val << 1) ^ (val >> 31));
111
+ const encoded = val >= 0 ? val * 2 : val * -2 - 1;
112
+ return this.writeUVarint(encoded);
85
113
  }
86
114
 
87
115
  writeFloat(val: number) {
88
116
  this.ensureSize(4);
89
- this.view.setFloat32(this.pos, val, true);
90
- this.pos += 4;
117
+ f32[0] = val;
118
+ this.bytes[this.pos++] = f32u8[0]!;
119
+ this.bytes[this.pos++] = f32u8[1]!;
120
+ this.bytes[this.pos++] = f32u8[2]!;
121
+ this.bytes[this.pos++] = f32u8[3]!;
91
122
  return this;
92
123
  }
93
124
 
@@ -229,13 +260,15 @@ export class Reader {
229
260
 
230
261
  readVarint() {
231
262
  const val = this.readUVarint();
232
- return (val >>> 1) ^ -(val & 1);
263
+ return val % 2 === 0 ? val / 2 : -(val + 1) / 2;
233
264
  }
234
265
 
235
266
  readFloat() {
236
- const val = this.view.getFloat32(this.pos, true);
237
- this.pos += 4;
238
- return val;
267
+ f32u8[0] = this.bytes[this.pos++];
268
+ f32u8[1] = this.bytes[this.pos++];
269
+ f32u8[2] = this.bytes[this.pos++];
270
+ f32u8[3] = this.bytes[this.pos++];
271
+ return f32[0];
239
272
  }
240
273
 
241
274
  readBits(numBits: number) {
package/lib/index.js CHANGED
@@ -4,6 +4,8 @@ const SLAB_SIZE = 8192;
4
4
  const MAX_POOLED = 4096;
5
5
  let slab = new Uint8Array(SLAB_SIZE);
6
6
  let slabOffset = 0;
7
+ const f32 = new Float32Array(1);
8
+ const f32u8 = new Uint8Array(f32.buffer);
7
9
  function allocFromSlab(size) {
8
10
  if (size > MAX_POOLED) {
9
11
  // Too large for pool, allocate directly
@@ -44,39 +46,63 @@ export class Writer {
44
46
  }
45
47
  writeUVarint(val) {
46
48
  if (val < 0x80) {
49
+ // 1 byte: 0-127
47
50
  this.writeUInt8(val);
48
51
  }
49
52
  else if (val < 0x4000) {
53
+ // 2 bytes: 128 - 16,383
50
54
  this.writeUInt16((val & 0x7f) | ((val & 0x3f80) << 1) | 0x8000);
51
55
  }
52
56
  else if (val < 0x200000) {
57
+ // 3 bytes: 16,384 - 2,097,151
53
58
  this.writeUInt8((val >> 14) | 0x80);
54
59
  this.writeUInt16((val & 0x7f) | ((val & 0x3f80) << 1) | 0x8000);
55
60
  }
56
61
  else if (val < 0x10000000) {
62
+ // 4 bytes: 2,097,152 - 268,435,455
57
63
  this.writeUInt32((val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000);
58
64
  }
59
65
  else if (val < 0x800000000) {
66
+ // 5 bytes: 268,435,456 - 34,359,738,367
60
67
  this.writeUInt8(Math.floor(val / 0x10000000) | 0x80);
61
68
  this.writeUInt32((val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000);
62
69
  }
63
70
  else if (val < 0x40000000000) {
71
+ // 6 bytes: 34,359,738,368 - 4,398,046,511,103
64
72
  const shiftedVal = Math.floor(val / 0x10000000);
65
73
  this.writeUInt16((shiftedVal & 0x7f) | ((shiftedVal & 0x3f80) << 1) | 0x8080);
66
74
  this.writeUInt32((val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000);
67
75
  }
76
+ else if (val < 0x2000000000000) {
77
+ // 7 bytes: 4,398,046,511,104 - 562,949,953,421,311
78
+ const shiftedVal = Math.floor(val / 0x10000000);
79
+ this.writeUInt8((Math.floor(shiftedVal / 0x4000) & 0x7f) | 0x80);
80
+ this.writeUInt16((shiftedVal & 0x7f) | ((shiftedVal & 0x3f80) << 1) | 0x8080);
81
+ this.writeUInt32((val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000);
82
+ }
83
+ else if (val <= Number.MAX_SAFE_INTEGER) {
84
+ // 8 bytes: 562,949,953,421,312 - 9,007,199,254,740,991 (MAX_SAFE_INTEGER)
85
+ const shiftedVal = Math.floor(val / 0x10000000);
86
+ this.writeUInt16((Math.floor(shiftedVal / 0x4000) & 0x7f) | ((Math.floor(shiftedVal / 0x4000) & 0x3f80) << 1) | 0x8080);
87
+ this.writeUInt16((shiftedVal & 0x7f) | ((shiftedVal & 0x3f80) << 1) | 0x8080);
88
+ this.writeUInt32((val & 0x7f) | ((val & 0x3f80) << 1) | ((val & 0x1fc000) << 2) | ((val & 0xfe00000) << 3) | 0x80808000);
89
+ }
68
90
  else {
69
91
  throw new Error("Value out of range");
70
92
  }
71
93
  return this;
72
94
  }
73
95
  writeVarint(val) {
74
- return this.writeUVarint((val << 1) ^ (val >> 31));
96
+ const encoded = val >= 0 ? val * 2 : val * -2 - 1;
97
+ return this.writeUVarint(encoded);
75
98
  }
76
99
  writeFloat(val) {
77
100
  this.ensureSize(4);
78
- this.view.setFloat32(this.pos, val, true);
79
- this.pos += 4;
101
+ f32[0] = val;
102
+ this.bytes[this.pos++] = f32u8[0];
103
+ this.bytes[this.pos++] = f32u8[1];
104
+ this.bytes[this.pos++] = f32u8[2];
105
+ this.bytes[this.pos++] = f32u8[3];
80
106
  return this;
81
107
  }
82
108
  writeBits(bits) {
@@ -203,12 +229,14 @@ export class Reader {
203
229
  }
204
230
  readVarint() {
205
231
  const val = this.readUVarint();
206
- return (val >>> 1) ^ -(val & 1);
232
+ return val % 2 === 0 ? val / 2 : -(val + 1) / 2;
207
233
  }
208
234
  readFloat() {
209
- const val = this.view.getFloat32(this.pos, true);
210
- this.pos += 4;
211
- return val;
235
+ f32u8[0] = this.bytes[this.pos++];
236
+ f32u8[1] = this.bytes[this.pos++];
237
+ f32u8[2] = this.bytes[this.pos++];
238
+ f32u8[3] = this.bytes[this.pos++];
239
+ return f32[0];
212
240
  }
213
241
  readBits(numBits) {
214
242
  const numBytes = Math.ceil(numBits / 8);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "bin-serde",
3
- "version": "1.6.2",
3
+ "version": "1.6.4",
4
4
  "description": "A low level library for efficiently writing and reading binary data in javascript",
5
5
  "type": "module",
6
6
  "main": "lib/index.js",