This commit fixes a locale problem with locales that use comma as a mantissa
separator. Example: 12.34 en_US = 12,34 pt_BR. Since strtod() is a non-safe
function, virStrToDouble() will have problems to parse double numbers from
kernel settings and other double numbers from static files (XMLs, JSONs, etc).
Resolves:
https://bugzilla.redhat.com/show_bug.cgi?id=1457634
Resolves:
https://bugzilla.redhat.com/show_bug.cgi?id=1457481
Signed-off-by: Julio Faracco <jcfaracco(a)gmail.com>
---
src/util/virstring.c | 18 +++++++++++++++++-
1 file changed, 17 insertions(+), 1 deletion(-)
diff --git a/src/util/virstring.c b/src/util/virstring.c
index 9c12f7b..1bd6777 100644
--- a/src/util/virstring.c
+++ b/src/util/virstring.c
@@ -534,7 +534,13 @@ virLocaleOnceInit(void)
VIR_ONCE_GLOBAL_INIT(virLocale);
#endif
-
+/**
+ * virStrToDouble
+ *
+ * converts string with C locale (thread-safe) to double.
+ *
+ * Returns -1 on error or returns 0 on success.
+ */
int
virStrToDouble(char const *s,
char **end_ptr,
@@ -545,7 +551,17 @@ virStrToDouble(char const *s,
int err;
errno = 0;
+#if HAVE_NEWLOCALE
+ locale_t old_loc;
+ if (virLocaleInitialize() < 0)
+ return -1;
+
+ old_loc = uselocale(virLocale);
+#endif
val = strtod(s, &p); /* exempt from syntax-check */
+#if HAVE_NEWLOCALE
+ uselocale(old_loc);
+#endif
err = (errno || (!end_ptr && *p) || p == s);
if (end_ptr)
*end_ptr = p;
--
2.7.4