1
1
const Buffer = require ( 'safe-buffer' ) . Buffer ;
2
2
const align = require ( './align' ) . align ;
3
3
const parseSignature = require ( '../lib/signature' ) ;
4
- const Long = require ( 'long' ) ;
4
+ const {
5
+ MAX_INT64 , MIN_INT64 ,
6
+ MAX_UINT64 , MIN_UINT64
7
+ } = require ( './constants' ) ;
8
+
5
9
/**
6
10
* MakeSimpleMarshaller
7
11
* @param signature - the signature of the data you want to check
@@ -178,8 +182,10 @@ var MakeSimpleMarshaller = function(signature) {
178
182
marshaller . marshall = function ( ps , data ) {
179
183
data = this . check ( data ) ;
180
184
align ( ps , 8 ) ;
181
- ps . word32le ( data . low ) ;
182
- ps . word32le ( data . high ) ;
185
+ let word0 = data - ( ( data >> 32n ) << 32n ) ;
186
+ let word1 = data >> 32n ;
187
+ ps . word32le ( Number ( word0 ) ) ;
188
+ ps . word32le ( Number ( word1 ) ) ;
183
189
ps . _offset += 8 ;
184
190
} ;
185
191
break ;
@@ -190,9 +196,22 @@ var MakeSimpleMarshaller = function(signature) {
190
196
} ;
191
197
marshaller . marshall = function ( ps , data ) {
192
198
data = this . check ( data ) ;
199
+ let isNegative = ( data < 0n ) ;
200
+ if ( isNegative ) {
201
+ data *= - 1n ;
202
+ }
203
+
204
+ let word0 = data - ( ( data >> 32n ) << 32n ) ;
205
+ let word1 = data >> 32n ;
206
+
207
+ if ( isNegative ) {
208
+ word1 |= ( 1n << 31n ) ;
209
+ }
210
+
193
211
align ( ps , 8 ) ;
194
- ps . word32le ( data . low ) ;
195
- ps . word32le ( data . high ) ;
212
+ ps . word32le ( Number ( word0 ) ) ;
213
+ ps . word32le ( Number ( word1 ) ) ;
214
+
196
215
ps . _offset += 8 ;
197
216
} ;
198
217
break ;
@@ -243,94 +262,22 @@ var checkBoolean = function(data) {
243
262
throw new Error ( `Data: ${ data } was not of type boolean` ) ;
244
263
} ;
245
264
246
- // This is essentially a tweaked version of 'fromValue' from Long.js with error checking.
247
- // This can take number or string of decimal characters or 'Long' instance (or Long-style object with props low,high,unsigned).
248
- var makeLong = function ( val , signed ) {
249
- if ( val instanceof Long ) return val ;
250
- if ( val instanceof Number ) val = val . valueOf ( ) ;
251
- if ( typeof val === 'number' ) {
252
- try {
253
- // Long.js won't alert you to precision loss in passing more than 53 bit ints through a double number, so we check here
254
- checkInteger ( val ) ;
255
- if ( signed ) {
256
- checkRange ( - 0x1fffffffffffff , 0x1fffffffffffff , val ) ;
257
- } else {
258
- checkRange ( 0 , 0x1fffffffffffff , val ) ;
259
- }
260
- } catch ( e ) {
261
- e . message += ' (Number type can only carry 53 bit integer)' ;
262
- throw e ;
263
- }
264
- try {
265
- return Long . fromNumber ( val , ! signed ) ;
266
- } catch ( e ) {
267
- e . message = `Error converting number to 64bit integer "${ e . message } "` ;
268
- throw e ;
269
- }
270
- }
271
- if ( typeof val === 'string' || val instanceof String ) {
272
- var radix = 10 ;
273
- val = val . trim ( ) . toUpperCase ( ) ; // remove extra whitespace and make uppercase (for hex)
274
- if ( val . substring ( 0 , 2 ) === '0X' ) {
275
- radix = 16 ;
276
- val = val . substring ( 2 ) ;
277
- } else if ( val . substring ( 0 , 3 ) === '-0X' ) {
278
- // unusual, but just in case?
279
- radix = 16 ;
280
- val = `-${ val . substring ( 3 ) } ` ;
281
- }
282
- val = val . replace ( / ^ 0 + (? = \d ) / , '' ) ; // dump leading zeroes
283
- var data ;
284
- try {
285
- data = Long . fromString ( val , ! signed , radix ) ;
286
- } catch ( e ) {
287
- e . message = `Error converting string to 64bit integer '${ e . message } '` ;
288
- throw e ;
289
- }
290
- // If string represents a number outside of 64 bit range, it can quietly overflow.
291
- // We assume if things converted correctly the string coming out of Long should match what went into it.
292
- if ( data . toString ( radix ) . toUpperCase ( ) !== val )
293
- throw new Error (
294
- `Data: '${ val } ' did not convert correctly to ${
295
- signed ? 'signed' : 'unsigned'
296
- } 64 bit`
297
- ) ;
298
- return data ;
299
- }
300
- // Throws for non-objects, converts non-instanceof Long:
301
- try {
302
- return Long . fromBits ( val . low , val . high , val . unsigned ) ;
303
- } catch ( e ) {
304
- e . message = `Error converting object to 64bit integer '${ e . message } '` ;
305
- throw e ;
306
- }
307
- } ;
308
-
309
265
var checkLong = function ( data , signed ) {
310
- if ( ! Long . isLong ( data ) ) {
311
- data = makeLong ( data , signed ) ;
312
- }
266
+ data = BigInt ( data ) ;
313
267
314
- // Do we enforce that Long.js object unsigned/signed match the field even if it is still in range?
315
- // Probably, might help users avoid unintended bugs?
316
268
if ( signed ) {
317
- if ( data . unsigned )
318
- throw new Error (
319
- 'Longjs object is unsigned, but marshalling into signed 64 bit field'
320
- ) ;
321
- if ( data . gt ( Long . MAX_VALUE ) || data . lt ( Long . MIN_VALUE ) ) {
322
- throw new Error ( `Data: ${ data } was out of range (64-bit signed)` ) ;
269
+ if ( data > MAX_INT64 ) {
270
+ throw new Error ( 'data was out of range (greater than max int64)' ) ;
271
+ } else if ( data < MIN_INT64 ) {
272
+ throw new Error ( 'data was out of range (less than min int64)' ) ;
323
273
}
324
274
} else {
325
- if ( ! data . unsigned )
326
- throw new Error (
327
- 'Longjs object is signed, but marshalling into unsigned 64 bit field'
328
- ) ;
329
- // NOTE: data.gt(Long.MAX_UNSIGNED_VALUE) will catch if Long.js object is a signed value but is still within unsigned range!
330
- // Since we are enforcing signed type matching between Long.js object and field, this note should not matter.
331
- if ( data . gt ( Long . MAX_UNSIGNED_VALUE ) || data . lt ( 0 ) ) {
332
- throw new Error ( `Data: ${ data } was out of range (64-bit unsigned)` ) ;
275
+ if ( data > MAX_UINT64 ) {
276
+ throw new Error ( 'data was out of range (greater than max uint64)' ) ;
277
+ } else if ( data < MIN_UINT64 ) {
278
+ throw new Error ( 'data was out of range (less than min uint64)' ) ;
333
279
}
334
280
}
281
+
335
282
return data ;
336
283
} ;
0 commit comments