Skip to content

Implement deprecations for PHP 8.3 RFC #11615

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Jul 17, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Zend/Optimizer/pass1.c
Original file line number Diff line number Diff line change
Expand Up @@ -164,7 +164,7 @@ void zend_optimizer_pass1(zend_op_array *op_array, zend_optimizer_ctx *ctx)
if (ce) {
zend_class_constant *cc = zend_hash_find_ptr(
&ce->constants_table, Z_STR(ZEND_OP2_LITERAL(opline)));
if (cc && (ZEND_CLASS_CONST_FLAGS(cc) & ZEND_ACC_PPP_MASK) == ZEND_ACC_PUBLIC && !(ce->ce_flags & ZEND_ACC_TRAIT)) {
if (cc && !(ZEND_CLASS_CONST_FLAGS(cc) & ZEND_ACC_DEPRECATED) && (ZEND_CLASS_CONST_FLAGS(cc) & ZEND_ACC_PPP_MASK) == ZEND_ACC_PUBLIC && !(ce->ce_flags & ZEND_ACC_TRAIT)) {
zval *c = &cc->value;
if (Z_TYPE_P(c) == IS_CONSTANT_AST) {
zend_ast *ast = Z_ASTVAL_P(c);
Expand Down
4 changes: 3 additions & 1 deletion Zend/zend_compile.c
Original file line number Diff line number Diff line change
Expand Up @@ -1728,7 +1728,9 @@ static bool zend_try_compile_const_expr_resolve_class_name(zval *zv, zend_ast *c
/* We don't use zend_verify_const_access because we need to deal with unlinked classes. */
static bool zend_verify_ct_const_access(zend_class_constant *c, zend_class_entry *scope)
{
if (c->ce->ce_flags & ZEND_ACC_TRAIT) {
if (ZEND_CLASS_CONST_FLAGS(c) & ZEND_ACC_DEPRECATED) {
return 0;
} else if (c->ce->ce_flags & ZEND_ACC_TRAIT) {
/* This condition is only met on directly accessing trait constants,
* because the ce is replaced to the class entry of the composing class
* on binding. */
Expand Down
8 changes: 8 additions & 0 deletions Zend/zend_constants.c
Original file line number Diff line number Diff line change
Expand Up @@ -347,6 +347,14 @@ ZEND_API zval *zend_get_class_constant_ex(zend_string *class_name, zend_string *
goto failure;
}

if (UNEXPECTED(ZEND_CLASS_CONST_FLAGS(c) & ZEND_ACC_DEPRECATED)) {
if ((flags & ZEND_FETCH_CLASS_SILENT) == 0) {
zend_error(E_DEPRECATED, "Constant %s::%s is deprecated", ZSTR_VAL(class_name), ZSTR_VAL(constant_name));
if (EG(exception)) {
goto failure;
}
}
}
ret_constant = &c->value;
}
}
Expand Down
13 changes: 12 additions & 1 deletion Zend/zend_vm_def.h
Original file line number Diff line number Diff line change
Expand Up @@ -5983,6 +5983,17 @@ ZEND_VM_HANDLER(181, ZEND_FETCH_CLASS_CONSTANT, VAR|CONST|UNUSED|CLASS_FETCH, CO
HANDLE_EXCEPTION();
}

bool is_constant_deprecated = ZEND_CLASS_CONST_FLAGS(c) & ZEND_ACC_DEPRECATED;
if (UNEXPECTED(is_constant_deprecated)) {
zend_error(E_DEPRECATED, "Constant %s::%s is deprecated", ZSTR_VAL(ce->name), ZSTR_VAL(constant_name));

if (EG(exception)) {
ZVAL_UNDEF(EX_VAR(opline->result.var));
FREE_OP2();
HANDLE_EXCEPTION();
}
}

value = &c->value;
// Enums require loading of all class constants to build the backed enum table
if (ce->ce_flags & ZEND_ACC_ENUM && ce->enum_backing_type != IS_UNDEF && ce->type == ZEND_USER_CLASS && !(ce->ce_flags & ZEND_ACC_CONSTANTS_UPDATED)) {
Expand All @@ -5999,7 +6010,7 @@ ZEND_VM_HANDLER(181, ZEND_FETCH_CLASS_CONSTANT, VAR|CONST|UNUSED|CLASS_FETCH, CO
HANDLE_EXCEPTION();
}
}
if (OP2_TYPE == IS_CONST) {
if (OP2_TYPE == IS_CONST && !is_constant_deprecated) {
CACHE_POLYMORPHIC_PTR(opline->extended_value, ce, value);
}
} else {
Expand Down
78 changes: 72 additions & 6 deletions Zend/zend_vm_execute.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions ext/intl/formatter/formatter.stub.php
Original file line number Diff line number Diff line change
Expand Up @@ -392,6 +392,7 @@ class NumberFormatter
public const TYPE_DOUBLE = UNKNOWN;
/**
* @var int
* @deprecated
* @cvalue FORMAT_TYPE_CURRENCY
*/
public const TYPE_CURRENCY = UNKNOWN;
Expand Down
4 changes: 2 additions & 2 deletions ext/intl/formatter/formatter_arginfo.h

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

15 changes: 15 additions & 0 deletions ext/intl/tests/deprecated_number_formater_type_currency.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
--TEST--
NumberFormatter::TYPE_CURRENCY is deprecated
--EXTENSIONS--
intl
--FILE--
<?php
var_dump(NumberFormatter::TYPE_CURRENCY);
var_dump(constant('NumberFormatter::TYPE_CURRENCY'));
?>
--EXPECTF--
Deprecated: Constant NumberFormatter::TYPE_CURRENCY is deprecated in %s on line %d
int(4)

Deprecated: Constant NumberFormatter::TYPE_CURRENCY is deprecated in %s on line %d
int(4)
10 changes: 9 additions & 1 deletion ext/intl/tests/formatter_format_and_parse_errors.phpt
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,20 @@ try {
}

?>
--EXPECT--
--EXPECTF--
numfmt_format(): Argument #3 ($type) must be a NumberFormatter::TYPE_* constant
NumberFormatter::format(): Argument #2 ($type) must be a NumberFormatter::TYPE_* constant
numfmt_parse(): Argument #3 ($type) must be a NumberFormatter::TYPE_* constant
NumberFormatter::parse(): Argument #2 ($type) must be a NumberFormatter::TYPE_* constant

Deprecated: Constant NumberFormatter::TYPE_CURRENCY is deprecated in %s on line %d
numfmt_format(): Argument #3 ($type) cannot be NumberFormatter::TYPE_CURRENCY constant, use numfmt_format_currency() function instead

Deprecated: Constant NumberFormatter::TYPE_CURRENCY is deprecated in %s on line %d
NumberFormatter::format(): Argument #2 ($type) cannot be NumberFormatter::TYPE_CURRENCY constant, use NumberFormatter::formatCurrency() method instead

Deprecated: Constant NumberFormatter::TYPE_CURRENCY is deprecated in %s on line %d
numfmt_parse(): Argument #3 ($type) cannot be NumberFormatter::TYPE_CURRENCY constant, use numfmt_parse_currency() function instead

Deprecated: Constant NumberFormatter::TYPE_CURRENCY is deprecated in %s on line %d
NumberFormatter::parse(): Argument #2 ($type) cannot be NumberFormatter::TYPE_CURRENCY constant, use NumberFormatter::parseCurrency() method instead
2 changes: 2 additions & 0 deletions ext/mbstring/mbstring.c
Original file line number Diff line number Diff line change
Expand Up @@ -2649,6 +2649,8 @@ PHP_FUNCTION(mb_strimwidth)
}

if (width < 0) {
php_error_docref(NULL, E_DEPRECATED,
"passing a negative integer to argument #3 ($width) is deprecated");
width += mb_get_strwidth(str, enc);

if (from > 0) {
Expand Down
27 changes: 18 additions & 9 deletions ext/mbstring/tests/mb_strimwidth.phpt
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,8 @@ testStrimwidth($utf16le, -3, 5, 'UTF-16LE');
// We'll count back 4 characters, then allow a width of ((4 * 2) - 2) = 6
// Since the output will not reach the END of the string, the trim marker
// will have to be added, and will consume a width of 3
testStrimwidth($utf16le, -4, -2, 'UTF-16LE');
// We also suppress the deprecation for negative width as of PHP 8.3
@testStrimwidth($utf16le, -4, -2, 'UTF-16LE');

echo "\n== EUC-JP ==\n";

Expand Down Expand Up @@ -103,22 +104,26 @@ testStrimwidth($euc_jp, 9, 5, 'EUC-JP');

// Skip 15 characters, which leaves a total width of 42. Then trim string down
// to 5 less than that, which is a width of 37.
testStrimwidth($euc_jp, 15, -5, 'EUC-JP');
// We also suppress the deprecation for negative width as of PHP 8.3
@testStrimwidth($euc_jp, 15, -5, 'EUC-JP');

// Take the last 30 characters, which have a width of 54. Trim string down to
// 25 less than that, which is 29.
testStrimwidth($euc_jp, -30, -25, 'EUC-JP');
// We also suppress the deprecation for negative width as of PHP 8.3
@testStrimwidth($euc_jp, -30, -25, 'EUC-JP');

// Skip over 39 characters... but since string is only 39 characters long,
// it takes us to the end of the string, and output is empty
testStrimwidth($euc_jp, 39, 10, 'EUC-JP');

// Take the last 10 characters, which have a width of 20. Trim string down to
// 12 less than that, which is a width of 8.
testStrimwidth($euc_jp, -10, -12, 'EUC-JP');
// We also suppress the deprecation for negative width as of PHP 8.3
@testStrimwidth($euc_jp, -10, -12, 'EUC-JP');

try {
var_dump(mb_strimwidth($euc_jp, 0, -100,'...','EUC-JP'));
// We also suppress the deprecation for negative width as of PHP 8.3
var_dump(@mb_strimwidth($euc_jp, 0, -100,'...','EUC-JP'));
} catch (\ValueError $e) {
echo $e->getMessage() . \PHP_EOL;
}
Expand All @@ -133,7 +138,8 @@ try {
echo $e->getMessage() . \PHP_EOL;
}
try {
var_dump(mb_strimwidth($euc_jp, -10, -21,'...','EUC-JP'));
// We also suppress the deprecation for negative width as of PHP 8.3
var_dump(@mb_strimwidth($euc_jp, -10, -21,'...','EUC-JP'));
} catch (\ValueError $e) {
echo $e->getMessage() . \PHP_EOL;
}
Expand All @@ -147,7 +153,8 @@ for ($from = -5; $from <= 5; $from++) {
// This case is illegal and will throw an exception
$pass = false;
try {
mb_strimwidth($str, $from, $width, '...', 'ASCII');
/* Shut up deprecation notice for now */
@mb_strimwidth($str, $from, $width, '...', 'ASCII');
} catch (\ValueError $e) {
$pass = true;
}
Expand All @@ -156,7 +163,8 @@ for ($from = -5; $from <= 5; $from++) {
continue;
}

$result = mb_strimwidth($str, $from, $width, '...', 'ASCII');
/* Shut up deprecation notice for now */
$result = @mb_strimwidth($str, $from, $width, '...', 'ASCII');

if ($from < 0 && $width < 0 && ($width - $from) <= 3) {
if ($result !== '...')
Expand Down Expand Up @@ -211,7 +219,8 @@ testStrimwidth("日本語abc", -3, 10, 'UTF-8');
// Regression test; old implementation did not handle positive 'from' argument
// combined with negative 'width' argument correctly when portion being skipped
// over included fullwidth characters
testStrimwidth("日本語abcdef", 3, -1, 'UTF-8');
// We also suppress the deprecation for negative width as of PHP 8.3
@testStrimwidth("日本語abcdef", 3, -1, 'UTF-8');

?>
--EXPECT--
Expand Down
11 changes: 11 additions & 0 deletions ext/mbstring/tests/mb_strimwidth_deprecated.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
--TEST--
mb_strimwidth() is deprecated with negative width
--EXTENSIONS--
mbstring
--FILE--
<?php
var_dump(mb_strimwidth("some string", 1, -2, '...', 'ASCII'));
?>
--EXPECTF--
Deprecated: mb_strimwidth(): passing a negative integer to argument #3 ($width) is deprecated in %s on line %d
string(8) "ome s..."