From 9bb806f3e0173af0d42ba18dd0ad07de5374d3ed Mon Sep 17 00:00:00 2001 From: SakiTakamachi Date: Mon, 16 Jun 2025 21:09:39 +0900 Subject: [PATCH 1/2] use vector in compare --- ext/bcmath/libbcmath/src/compare.c | 32 ++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/ext/bcmath/libbcmath/src/compare.c b/ext/bcmath/libbcmath/src/compare.c index 06ef246782089..aa695b2a6a0c2 100644 --- a/ext/bcmath/libbcmath/src/compare.c +++ b/ext/bcmath/libbcmath/src/compare.c @@ -92,6 +92,38 @@ bcmath_compare_result _bc_do_compare(bc_num n1, bc_num n2, size_t scale, bool us const char *n1ptr = n1->n_value; const char *n2ptr = n2->n_value; + while (count >= sizeof(BC_VECTOR)) { + BC_VECTOR n1bytes; + BC_VECTOR n2bytes; + memcpy(&n1bytes, n1ptr, sizeof(BC_VECTOR)); + memcpy(&n2bytes, n2ptr, sizeof(BC_VECTOR)); + + if (n1bytes != n2bytes) { +#if BC_LITTLE_ENDIAN + n1bytes = BC_BSWAP(n1bytes); + n2bytes = BC_BSWAP(n2bytes); +#endif + if (n1bytes > n2bytes) { + /* Magnitude of n1 > n2. */ + if (!use_sign || n1->n_sign == PLUS) { + return BCMATH_LEFT_GREATER; + } else { + return BCMATH_RIGHT_GREATER; + } + } else { + /* Magnitude of n1 < n2. */ + if (!use_sign || n1->n_sign == PLUS) { + return BCMATH_RIGHT_GREATER; + } else { + return BCMATH_LEFT_GREATER; + } + } + } + count -= sizeof(BC_VECTOR); + n1ptr += sizeof(BC_VECTOR); + n2ptr += sizeof(BC_VECTOR); + } + while ((count > 0) && (*n1ptr == *n2ptr)) { n1ptr++; n2ptr++; From bc316623c5ade1db988429ad7293327a8abc64f9 Mon Sep 17 00:00:00 2001 From: SakiTakamachi Date: Fri, 20 Jun 2025 09:28:08 +0900 Subject: [PATCH 2/2] The duplicated code was refactored into an inline function. --- ext/bcmath/libbcmath/src/compare.c | 67 ++++++++++-------------------- 1 file changed, 22 insertions(+), 45 deletions(-) diff --git a/ext/bcmath/libbcmath/src/compare.c b/ext/bcmath/libbcmath/src/compare.c index aa695b2a6a0c2..76ab794dc874c 100644 --- a/ext/bcmath/libbcmath/src/compare.c +++ b/ext/bcmath/libbcmath/src/compare.c @@ -39,6 +39,25 @@ than N2 and +1 if N1 is greater than N2. If USE_SIGN is false, just compare the magnitudes. */ +static inline bcmath_compare_result bc_compare_get_result_val(bool left_abs_greater, bool use_sign, sign left_sign) +{ + if (left_abs_greater) { + /* Magnitude of left > right. */ + if (!use_sign || left_sign == PLUS) { + return BCMATH_LEFT_GREATER; + } else { + return BCMATH_RIGHT_GREATER; + } + } else { + /* Magnitude of left < right. */ + if (!use_sign || left_sign == PLUS) { + return BCMATH_RIGHT_GREATER; + } else { + return BCMATH_LEFT_GREATER; + } + } +} + bcmath_compare_result _bc_do_compare(bc_num n1, bc_num n2, size_t scale, bool use_sign) { /* First, compare signs. */ @@ -66,21 +85,7 @@ bcmath_compare_result _bc_do_compare(bc_num n1, bc_num n2, size_t scale, bool us /* Now compare the magnitude. */ if (n1->n_len != n2->n_len) { - if (n1->n_len > n2->n_len) { - /* Magnitude of n1 > n2. */ - if (!use_sign || n1->n_sign == PLUS) { - return BCMATH_LEFT_GREATER; - } else { - return BCMATH_RIGHT_GREATER; - } - } else { - /* Magnitude of n1 < n2. */ - if (!use_sign || n1->n_sign == PLUS) { - return BCMATH_RIGHT_GREATER; - } else { - return BCMATH_LEFT_GREATER; - } - } + return bc_compare_get_result_val(n1->n_len > n2->n_len, use_sign, n1->n_sign); } size_t n1_scale = MIN(n1->n_scale, scale); @@ -103,21 +108,7 @@ bcmath_compare_result _bc_do_compare(bc_num n1, bc_num n2, size_t scale, bool us n1bytes = BC_BSWAP(n1bytes); n2bytes = BC_BSWAP(n2bytes); #endif - if (n1bytes > n2bytes) { - /* Magnitude of n1 > n2. */ - if (!use_sign || n1->n_sign == PLUS) { - return BCMATH_LEFT_GREATER; - } else { - return BCMATH_RIGHT_GREATER; - } - } else { - /* Magnitude of n1 < n2. */ - if (!use_sign || n1->n_sign == PLUS) { - return BCMATH_RIGHT_GREATER; - } else { - return BCMATH_LEFT_GREATER; - } - } + return bc_compare_get_result_val(n1bytes > n2bytes, use_sign, n1->n_sign); } count -= sizeof(BC_VECTOR); n1ptr += sizeof(BC_VECTOR); @@ -131,21 +122,7 @@ bcmath_compare_result _bc_do_compare(bc_num n1, bc_num n2, size_t scale, bool us } if (count != 0) { - if (*n1ptr > *n2ptr) { - /* Magnitude of n1 > n2. */ - if (!use_sign || n1->n_sign == PLUS) { - return BCMATH_LEFT_GREATER; - } else { - return BCMATH_RIGHT_GREATER; - } - } else { - /* Magnitude of n1 < n2. */ - if (!use_sign || n1->n_sign == PLUS) { - return BCMATH_RIGHT_GREATER; - } else { - return BCMATH_LEFT_GREATER; - } - } + return bc_compare_get_result_val(*n1ptr > *n2ptr, use_sign, n1->n_sign); } /* They are equal up to the last part of the equal part of the fraction. */