diff options
author | Miran <narimiran@disroot.org> | 2020-09-04 09:23:27 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2020-09-04 09:23:27 +0200 |
commit | 4fb17bc03be3046d8ff619a74eec7cb7ce02b4d2 (patch) | |
tree | 64e1452f63bb3b4c986842b398cafe877a6ebfc6 /lib/pure | |
parent | 48f29972210612b41cb6d98122672b1713edc907 (diff) | |
download | Nim-4fb17bc03be3046d8ff619a74eec7cb7ce02b4d2.tar.gz |
fix #15257, `toHex` couldn't handle large uint64 (#15261) [backport:1.2]
Diffstat (limited to 'lib/pure')
-rw-r--r-- | lib/pure/strutils.nim | 43 |
1 files changed, 31 insertions, 12 deletions
diff --git a/lib/pure/strutils.nim b/lib/pure/strutils.nim index a0a172430..20010ff81 100644 --- a/lib/pure/strutils.nim +++ b/lib/pure/strutils.nim @@ -938,6 +938,31 @@ proc toOct*(x: BiggestInt, len: Positive): string {.noSideEffect, inc shift, 3 mask = mask shl BiggestUInt(3) +proc toHexImpl(x: BiggestUInt, len: Positive, handleNegative: bool): string {.noSideEffect.} = + const + HexChars = "0123456789ABCDEF" + var n = x + result = newString(len) + for j in countdown(len-1, 0): + result[j] = HexChars[int(n and 0xF)] + n = n shr 4 + # handle negative overflow + if n == 0 and handleNegative: n = not(BiggestUInt 0) + +proc toHex*(x: BiggestUInt, len: Positive): string {.noSideEffect.} = + ## Converts `x` to its hexadecimal representation. + ## + ## The resulting string will be exactly `len` characters long. No prefix like + ## ``0x`` is generated. + runnableExamples: + let + a = 62'u64 + b = 4097'u64 + doAssert a.toHex(3) == "03E" + doAssert b.toHex(3) == "001" + doAssert b.toHex(4) == "1001" + toHexImpl(x, len, false) + proc toHex*(x: BiggestInt, len: Positive): string {.noSideEffect, rtl, extern: "nsuToHex".} = ## Converts `x` to its hexadecimal representation. @@ -948,25 +973,19 @@ proc toHex*(x: BiggestInt, len: Positive): string {.noSideEffect, let a = 62 b = 4097 + c = -8 doAssert a.toHex(3) == "03E" doAssert b.toHex(3) == "001" doAssert b.toHex(4) == "1001" - const - HexChars = "0123456789ABCDEF" - var - n = x - result = newString(len) - for j in countdown(len-1, 0): - result[j] = HexChars[int(n and 0xF)] - n = n shr 4 - # handle negative overflow - if n == 0 and x < 0: n = -1 + doAssert c.toHex(6) == "FFFFF8" + toHexImpl(cast[BiggestUInt](x), len, x < 0) -proc toHex*[T: SomeInteger](x: T): string = +proc toHex*[T: SomeInteger](x: T): string {.noSideEffect.} = ## Shortcut for ``toHex(x, T.sizeof * 2)`` runnableExamples: doAssert toHex(1984'i64) == "00000000000007C0" - toHex(BiggestInt(x), T.sizeof * 2) + doAssert toHex(1984'i16) == "07C0" + toHexImpl(cast[BiggestUInt](x), 2*sizeof(T), x < 0) proc toHex*(s: string): string {.noSideEffect, rtl.} = ## Converts a bytes string to its hexadecimal representation. |