diff --git a/ext/bcmath/bcmath.c b/ext/bcmath/bcmath.c index 1b91fba72fe74..f1e298b5cc9b0 100644 --- a/ext/bcmath/bcmath.c +++ b/ext/bcmath/bcmath.c @@ -404,10 +404,16 @@ PHP_FUNCTION(bcpowmod) php_str2num(&second, ZSTR_VAL(right)); php_str2num(&mod, ZSTR_VAL(modulus)); - if (bc_raisemod(first, second, mod, &result, scale) != -1) { - RETVAL_STR(bc_num2str_ex(result, scale)); - } else { - RETVAL_FALSE; + switch (bc_raisemod(first, second, mod, &result, scale)) { + case 0: + RETVAL_STR(bc_num2str_ex(result, scale)); + break; + case -1: + zend_throw_exception_ex(zend_ce_division_by_zero_error, 0, "Modulo by zero"); + break; + case -2: + zend_argument_value_error(2, "must be greater than 0"); + break; } bc_free_num(&first); diff --git a/ext/bcmath/bcmath.stub.php b/ext/bcmath/bcmath.stub.php index 45e75376f0991..97232b0ed7121 100644 --- a/ext/bcmath/bcmath.stub.php +++ b/ext/bcmath/bcmath.stub.php @@ -12,7 +12,7 @@ function bcdiv(string $dividend, string $divisor, ?int $scale = null): string {} function bcmod(string $dividend, string $divisor, ?int $scale = null): string {} -function bcpowmod(string $base, string $exponent, string $modulus, ?int $scale = null): string|false {} +function bcpowmod(string $base, string $exponent, string $modulus, ?int $scale = null): string {} function bcpow(string $base, string $exponent, ?int $scale = null): string {} diff --git a/ext/bcmath/bcmath_arginfo.h b/ext/bcmath/bcmath_arginfo.h index 75f864dc9d36f..46fc5ff9bd3e2 100644 --- a/ext/bcmath/bcmath_arginfo.h +++ b/ext/bcmath/bcmath_arginfo.h @@ -18,7 +18,7 @@ ZEND_END_ARG_INFO() #define arginfo_bcmod arginfo_bcdiv -ZEND_BEGIN_ARG_WITH_RETURN_TYPE_MASK_EX(arginfo_bcpowmod, 0, 3, MAY_BE_STRING|MAY_BE_FALSE) +ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO_EX(arginfo_bcpowmod, 0, 3, IS_STRING, 0) ZEND_ARG_TYPE_INFO(0, base, IS_STRING, 0) ZEND_ARG_TYPE_INFO(0, exponent, IS_STRING, 0) ZEND_ARG_TYPE_INFO(0, modulus, IS_STRING, 0) diff --git a/ext/bcmath/libbcmath/src/raisemod.c b/ext/bcmath/libbcmath/src/raisemod.c index 286590394095f..46dfd7a8a863a 100644 --- a/ext/bcmath/libbcmath/src/raisemod.c +++ b/ext/bcmath/libbcmath/src/raisemod.c @@ -67,7 +67,7 @@ bc_raisemod (bc_num base, bc_num expo, bc_num mod, bc_num *result, int scale) /* Check for correct numbers. */ if (bc_is_zero(mod)) return -1; - if (bc_is_neg(expo)) return -1; + if (bc_is_neg(expo)) return -2; /* Set initial values. */ power = bc_copy_num (base); diff --git a/ext/bcmath/tests/bcpowmod_negative_exponent.phpt b/ext/bcmath/tests/bcpowmod_negative_exponent.phpt new file mode 100644 index 0000000000000..a72b39548b72b --- /dev/null +++ b/ext/bcmath/tests/bcpowmod_negative_exponent.phpt @@ -0,0 +1,16 @@ +--TEST-- +bc_raisemod's expo can't be negative +--CREDITS-- +Gabriel Caruso (carusogabriel34@gmail.com) +--SKIPIF-- + +--FILE-- +getMessage() . \PHP_EOL; +} +?> +--EXPECT-- +bcpowmod(): Argument #2 ($exponent) must be greater than 0 diff --git a/ext/bcmath/tests/bcpowmod_error4.phpt b/ext/bcmath/tests/bcpowmod_zero_modulus.phpt similarity index 50% rename from ext/bcmath/tests/bcpowmod_error4.phpt rename to ext/bcmath/tests/bcpowmod_zero_modulus.phpt index 7c2ba5012b9f5..0b810969c6a79 100644 --- a/ext/bcmath/tests/bcpowmod_error4.phpt +++ b/ext/bcmath/tests/bcpowmod_zero_modulus.phpt @@ -1,10 +1,16 @@ --TEST-- -bc_raisemod's mod can't be zero and expo can't be negative +bc_raisemod's mod can't be zero --CREDITS-- Gabriel Caruso (carusogabriel34@gmail.com) --SKIPIF-- --FILE-- - +getMessage(), PHP_EOL; +} +?> --EXPECT-- -bool(false) +Modulo by zero diff --git a/ext/opcache/Optimizer/zend_func_info.c b/ext/opcache/Optimizer/zend_func_info.c index ff985fc63fae6..1b9e800d7d4cc 100644 --- a/ext/opcache/Optimizer/zend_func_info.c +++ b/ext/opcache/Optimizer/zend_func_info.c @@ -789,7 +789,7 @@ static const func_info_t func_infos[] = { F1("bcmul", MAY_BE_STRING), F1("bcdiv", MAY_BE_STRING), F1("bcmod", MAY_BE_STRING), - F1("bcpowmod", MAY_BE_FALSE | MAY_BE_STRING), + F1("bcpowmod", MAY_BE_STRING), F1("bcpow", MAY_BE_STRING), F1("bcsqrt", MAY_BE_STRING),