Added some code to avoid integer overflow for ceil, floor and round
* xpath.c: Added some code to avoid integer overflow for
ceil, floor and round functions (bug 301162)
diff --git a/xpath.c b/xpath.c
index 728ba74..c24c313 100644
--- a/xpath.c
+++ b/xpath.c
@@ -7190,6 +7190,18 @@
xmlXPathFreeObject(cur);
}
+/*
+ * To assure working code on multiple platforms, we want to only depend
+ * upon the characteristic truncation of converting a floating point value
+ * to an integer. Unfortunately, because of the different storage sizes
+ * of our internal floating point value (double) and integer (int), we
+ * can't directly convert (see bug 301162). This macro is a messy
+ * 'workaround'
+ */
+#define XTRUNC(f, v) \
+ f = fmod((v), INT_MAX); \
+ f = (v) - (f) + (double)((int)(f));
+
/**
* xmlXPathFloorFunction:
* @ctxt: the XPath Parser context
@@ -7208,7 +7220,7 @@
CAST_TO_NUMBER;
CHECK_TYPE(XPATH_NUMBER);
- f = (double)((int) ctxt->value->floatval);
+ XTRUNC(f, ctxt->value->floatval);
if (f != ctxt->value->floatval) {
if (ctxt->value->floatval > 0)
ctxt->value->floatval = f;
@@ -7238,7 +7250,7 @@
#if 0
ctxt->value->floatval = ceil(ctxt->value->floatval);
#else
- f = (double)((int) ctxt->value->floatval);
+ XTRUNC(f, ctxt->value->floatval);
if (f != ctxt->value->floatval) {
if (ctxt->value->floatval > 0)
ctxt->value->floatval = f + 1;
@@ -7278,7 +7290,7 @@
(ctxt->value->floatval == 0.0))
return;
- f = (double)((int) ctxt->value->floatval);
+ XTRUNC(f, ctxt->value->floatval);
if (ctxt->value->floatval < 0) {
if (ctxt->value->floatval < f - 0.5)
ctxt->value->floatval = f - 1;