From 121d5e5524d9fb0fe7d3555172613c7f1750265f Mon Sep 17 00:00:00 2001 From: Alexandre Duret-Lutz Date: Tue, 24 Jan 2023 15:48:06 +0100 Subject: [PATCH] bin: fix number conversion routines on 32bit On 32bit archetectures, long int = int the current check for detecting values that overflow int will fail. Conversion routings should check errno. * bin/common_conv.cc, bin/common_range.cc: Here. --- bin/common_conv.cc | 12 ++++++++---- bin/common_range.cc | 6 ++++-- 2 files changed, 12 insertions(+), 6 deletions(-) diff --git a/bin/common_conv.cc b/bin/common_conv.cc index 02b1815fd..b23a67c51 100644 --- a/bin/common_conv.cc +++ b/bin/common_conv.cc @@ -25,12 +25,13 @@ int to_int(const char* s, const char* where) { char* endptr; + errno = 0; long int lres = strtol(s, &endptr, 10); if (*endptr) error(2, 0, "failed to parse '%s' as an integer (in argument of %s).", s, where); int res = lres; - if (res != lres) + if (res != lres || errno == ERANGE) error(2, 0, "value '%s' is too large for an int (in argument of %s).", s, where); return res; @@ -49,13 +50,14 @@ unsigned to_unsigned (const char *s, const char* where) { char* endptr; + errno = 0; unsigned long lres = strtoul(s, &endptr, 10); if (*endptr) error(2, 0, "failed to parse '%s' as an unsigned integer (in argument of %s).", s, where); unsigned res = lres; - if (res != lres) + if (res != lres || errno == ERANGE) error(2, 0, "value '%s' is too large for a unsigned int (in argument of %s).", s, where); @@ -66,8 +68,9 @@ float to_float(const char* s, const char* where) { char* endptr; + errno = 0; float res = strtof(s, &endptr); - if (*endptr) + if (*endptr || errno == ERANGE) error(2, 0, "failed to parse '%s' as a float (in argument of %s)", s, where); return res; @@ -89,8 +92,9 @@ to_longs(const char* arg) while (*arg) { char* endptr; + errno = 0; long value = strtol(arg, &endptr, 10); - if (endptr == arg) + if (endptr == arg || errno) error(2, 0, "failed to parse '%s' as an integer.", arg); res.push_back(value); while (*endptr == ' ' || *endptr == ',') diff --git a/bin/common_range.cc b/bin/common_range.cc index 9419cc389..98e568b41 100644 --- a/bin/common_range.cc +++ b/bin/common_range.cc @@ -36,9 +36,10 @@ parse_range(const char* str, int missing_left, int missing_right) { range res; char* end; + errno = 0; long lres = strtol(str, &end, 10); res.min = lres; - if (res.min != lres) + if (res.min != lres || errno == ERANGE) error(2, 0, "start of range '%s' is too large for an int.", str); if (end == str) { @@ -69,9 +70,10 @@ parse_range(const char* str, int missing_left, int missing_right) { // Parse the next integer. char* end2; + errno = 0; lres = strtol(end, &end2, 10); res.max = lres; - if (res.max != lres) + if (res.max != lres || errno == ERANGE) error(2, 0, "end of range '%s' is too large for an int.", str); if (str == end2) error(2, 0, "invalid range '%s' "