BSON-XS
view release on metacpan or search on metacpan
bson/bson-decimal128.c view on Meta::CPAN
low;
} _bson_uint128_6464_t;
/**
*-------------------------------------------------------------------------
*
* mul64x64 --
*
* This function multiplies two &uint64_t into a &_bson_uint128_6464_t.
*
* Returns:
* The product of @left and @right.
*
* Side Effects:
* None.
*
*-------------------------------------------------------------------------
*/
static void
_mul_64x64 (uint64_t left, /* IN */
uint64_t right, /* IN */
_bson_uint128_6464_t *product) /* OUT */
{
uint64_t left_high, left_low,
right_high, right_low,
product_high, product_mid, product_mid2, product_low;
_bson_uint128_6464_t rt = { 0 };
if (!left && !right) {
*product = rt;
return;
}
left_high = left >> 32;
left_low = (uint32_t)left;
right_high = right >> 32;
right_low = (uint32_t)right;
product_high = left_high * right_high;
product_mid = left_high * right_low;
product_mid2 = left_low * right_high;
product_low = left_low * right_low;
product_high += product_mid >> 32;
product_mid = (uint32_t)product_mid + product_mid2 + (product_low >> 32);
product_high = product_high + (product_mid >> 32);
product_low = (product_mid << 32) + (uint32_t)product_low;
rt.high = product_high;
rt.low = product_low;
*product = rt;
}
/**
*------------------------------------------------------------------------------
*
* _dec128_tolower --
*
* This function converts the ASCII character @c to lowercase. It is locale
* insensitive (unlike the stdlib tolower).
*
* Returns:
* The lowercased character.
*/
char
_dec128_tolower (char c)
{
if (isupper (c)) {
c += 32;
}
return c;
}
/**
*------------------------------------------------------------------------------
*
* _dec128_istreq --
*
* This function compares the null-terminated *ASCII* strings @a and @b
* for case-insensitive equality.
*
* Returns:
* true if the strings are equal, false otherwise.
*/
bool
_dec128_istreq (const char *a, /* IN */
const char *b /* IN */)
{
while (*a != '\0' || *b != '\0') {
/* strings are different lengths. */
if (*a == '\0' || *b == '\0') {
return false;
}
if (_dec128_tolower (*a) != _dec128_tolower (*b)) {
return false;
}
a++;
b++;
}
return true;
}
/**
*------------------------------------------------------------------------------
*
* bson_decimal128_from_string --
*
* This function converts @string in the format [+-]ddd[.]ddd[E][+-]dddd to
* decimal128. Out of range values are converted to +/-Infinity. Invalid
* strings are converted to NaN.
*
* If more digits are provided than the available precision allows,
* round to the nearest expressable decimal128 with ties going to even will
* occur.
*
( run in 1.022 second using v1.01-cache-2.11-cpan-a5162978ef8 )