@@ -297,11 +297,16 @@ pub fn from_u32(n: u32, buffer: &mut [u8]) -> usize {
297
297
/// Optimized jeaiii algorithm for u64.
298
298
#[ inline( always) ]
299
299
#[ allow( clippy:: collapsible_else_if) ] // reason = "branching is fine-tuned for performance"
300
- pub fn from_u64 ( n : u64 , buffer : & mut [ u8 ] ) -> usize {
300
+ fn from_u64_impl ( n : u64 , buffer : & mut [ u8 ] , is_signed : bool ) -> usize {
301
301
// NOTE: Like before, this optimizes better for large and small
302
302
// values if there's a flat comparison with larger values first.
303
303
const FACTOR : u64 = 100_0000_0000 ;
304
- let buffer = & mut buffer[ ..20 ] ;
304
+ // NOTE `i64` takes a max of 19 digits, while `u64` takes a max of 20.
305
+ let buffer = if is_signed {
306
+ & mut buffer[ ..19 ]
307
+ } else {
308
+ & mut buffer[ ..20 ]
309
+ } ;
305
310
if n < 1_0000 {
306
311
// 1 to 4 digits
307
312
if n >= 100 {
@@ -326,7 +331,7 @@ pub fn from_u64(n: u64, buffer: &mut [u8]) -> usize {
326
331
write_digits ! ( @5 -6 buffer, n)
327
332
}
328
333
} else {
329
- // 11-20 digits, can do in 2 steps
334
+ // 11-20 digits, can do in 2 steps (11-19 if is signed).
330
335
// NOTE: `hi` has to be in `[0, 2^31)`, while `lo` is in `[0, 10^11)`
331
336
// So, we can use our `from_u64_small` for hi. For our `lo`, we always
332
337
// need to write 10 digits. However, the `jeaiii` algorithm is too
@@ -340,6 +345,23 @@ pub fn from_u64(n: u64, buffer: &mut [u8]) -> usize {
340
345
}
341
346
}
342
347
348
+ /// Optimized jeaiii algorithm for u64.
349
+ #[ inline( always) ]
350
+ pub fn from_u64 ( n : u64 , buffer : & mut [ u8 ] ) -> usize {
351
+ from_u64_impl ( n, buffer, false )
352
+ }
353
+
354
+ /// Optimized jeaiii algorithm for i64, which must be positive.
355
+ ///
356
+ /// This value **MUST** have originally been from an `i64`, since it
357
+ /// uses `19` for the bounds checked, so this will panic if `>= 10^19`
358
+ /// is passed to the function.
359
+ #[ inline( always) ]
360
+ pub fn from_i64 ( n : u64 , buffer : & mut [ u8 ] ) -> usize {
361
+ debug_assert ! ( n <= 1000_0000_0000_0000_0000u64 ) ;
362
+ from_u64_impl ( n, buffer, true )
363
+ }
364
+
343
365
/// Optimized jeaiii algorithm for u128.
344
366
#[ inline( always) ]
345
367
#[ allow( clippy:: collapsible_else_if) ] // reason = "branching is fine-tuned for performance"
0 commit comments