From b11510f4da57707aebde0feba9361557f64a238c Mon Sep 17 00:00:00 2001 From: Danny Milosavljevic Date: Mon, 15 Jun 2020 01:05:35 +0200 Subject: [PATCH] ntoab: Handle LONG_MIN case. * lib/mes/ntoab.c (ntoab): Handle LONG_MIN case. * lib/tests/scaffold/60-math.c (main): Add test for INT_MIN and hex. --- lib/mes/ntoab.c | 25 ++++++++++++++++++++++++- lib/tests/scaffold/60-math.c | 3 +++ 2 files changed, 27 insertions(+), 1 deletion(-) diff --git a/lib/mes/ntoab.c b/lib/mes/ntoab.c index a83b4d31..25780652 100644 --- a/lib/mes/ntoab.c +++ b/lib/mes/ntoab.c @@ -20,6 +20,10 @@ #include #include +#include + +#define STR(x) #x +#define XSTR(s) STR(s) char * ntoab (long x, int base, int signed_p) @@ -34,7 +38,26 @@ ntoab (long x, int base, int signed_p) if (signed_p && x < 0) { sign_p = 1; - u = -x; + if (x == LONG_MIN) + { + /* Cannot do u = (-x), so avoid it. */ + long i; + if (base == 10) + return XSTR(LONG_MIN); + /* We cause the same result as + i = (-x) % base + u = (-x) / base + would in mathematics if x and base were integers. + It will be the case that -base < x <= 0 after the loop. + Because base > 1, the quotient will definitely fit into u. + i will contain the last digit to print. */ + for (u = 0; x <= -base; x += base, ++u) + ; + i = -x; + *p-- = i > 9 ? 'a' + i - 10 : '0' + i; + } + else + u = -x; } else u = x; diff --git a/lib/tests/scaffold/60-math.c b/lib/tests/scaffold/60-math.c index 76e55092..24830e5b 100644 --- a/lib/tests/scaffold/60-math.c +++ b/lib/tests/scaffold/60-math.c @@ -196,6 +196,9 @@ ok1: if (strcmp ("-2147483648", itoa (i))) return 34; + if (strcmp ("-80000000", ntoab (i, 16, 1))) + return 35; + oputs ("t: i = -2147483647\n"); i = -2147483647;