Clang 3.9 chokes when calling isnan() on a double variable:
util/virxml.c:153:21: error: implicit conversion increases
floating-point precision: 'double' to
'long double' [-Werror,-Wdouble-promotion]
(isnan(obj->floatval))) {
~~~~~~~~~~~^~~~~~~~~
/usr/include/math.h:360:46: note: expanded from macro 'isnan'
# define isnan(x) __MATH_TG ((x), __isnan, (x))
~~~~~~~~~~~~~~~~~~~~~~~~~~^~~
/usr/include/math.h:295:16: note: expanded from macro '__MATH_TG'
: FUNC ## l ARGS)
~~~~~~~~~ ^~~~
Note how the wrong version of isnan() is being called: isnanl()
is for 'long double's, but obj->floatval is a double and a
suitable version should be called instead.
Cast the value to 'long double' to make the compiler happy.
---
Clang seems to be tripping on the specific way the isnan()
macro is defined in recent glibc versions; more specifically,
if I replace the current definition in <math.h> with the one
that predates the introduction of the __MATH_TG() macro, I
can get the current code to compile. I was not able to find
anything wrong with the __MATH_TG() macro though.
src/util/virxml.c | 10 +++++-----
1 file changed, 5 insertions(+), 5 deletions(-)
diff --git a/src/util/virxml.c b/src/util/virxml.c
index 666024809..076c23c03 100644
--- a/src/util/virxml.c
+++ b/src/util/virxml.c
@@ -150,7 +150,7 @@ virXPathNumber(const char *xpath,
obj = xmlXPathEval(BAD_CAST xpath, ctxt);
ctxt->node = relnode;
if ((obj == NULL) || (obj->type != XPATH_NUMBER) ||
- (isnan(obj->floatval))) {
+ (isnan((long double) obj->floatval))) {
xmlXPathFreeObject(obj);
return -1;
}
@@ -183,7 +183,7 @@ virXPathLongBase(const char *xpath,
if (virStrToLong_l((char *) obj->stringval, NULL, base, value) < 0)
ret = -2;
} else if ((obj != NULL) && (obj->type == XPATH_NUMBER) &&
- (!(isnan(obj->floatval)))) {
+ (!(isnan((long double) obj->floatval)))) {
*value = (long) obj->floatval;
if (*value != obj->floatval)
ret = -2;
@@ -288,7 +288,7 @@ virXPathULongBase(const char *xpath,
if (virStrToLong_ul((char *) obj->stringval, NULL, base, value) < 0)
ret = -2;
} else if ((obj != NULL) && (obj->type == XPATH_NUMBER) &&
- (!(isnan(obj->floatval)))) {
+ (!(isnan((long double) obj->floatval)))) {
*value = (unsigned long) obj->floatval;
if (*value != obj->floatval)
ret = -2;
@@ -404,7 +404,7 @@ virXPathULongLong(const char *xpath,
if (virStrToLong_ull((char *) obj->stringval, NULL, 10, value) < 0)
ret = -2;
} else if ((obj != NULL) && (obj->type == XPATH_NUMBER) &&
- (!(isnan(obj->floatval)))) {
+ (!(isnan((long double) obj->floatval)))) {
*value = (unsigned long long) obj->floatval;
if (*value != obj->floatval)
ret = -2;
@@ -450,7 +450,7 @@ virXPathLongLong(const char *xpath,
if (virStrToLong_ll((char *) obj->stringval, NULL, 10, value) < 0)
ret = -2;
} else if ((obj != NULL) && (obj->type == XPATH_NUMBER) &&
- (!(isnan(obj->floatval)))) {
+ (!(isnan((long double) obj->floatval)))) {
*value = (long long) obj->floatval;
if (*value != obj->floatval)
ret = -2;
--
2.11.0