Skip to content

Commit 075b6b8

Browse files
authored
Set default_object_handlers when registering internal enums
Internal enums can be cloned and compared, unlike user enums, because we didn't set default_object_handlers when registering internal enums. Fix by setting default_object_handlers when registering internal enums. Fixes GH-20914 Closes GH-20915
1 parent 1052270 commit 075b6b8

10 files changed

Lines changed: 136 additions & 1 deletion
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
--TEST--
2+
Enum comparison (internal enum)
3+
--EXTENSIONS--
4+
zend_test
5+
--FILE--
6+
<?php
7+
8+
$foo = ZendTestUnitEnum::Foo;
9+
$bar = ZendTestUnitEnum::Bar;
10+
11+
var_dump($foo === $foo);
12+
var_dump($foo == $foo);
13+
14+
var_dump($foo === $bar);
15+
var_dump($foo == $bar);
16+
17+
var_dump($bar === $foo);
18+
var_dump($bar == $foo);
19+
20+
var_dump($foo > $foo);
21+
var_dump($foo < $foo);
22+
var_dump($foo >= $foo);
23+
var_dump($foo <= $foo);
24+
25+
var_dump($foo > $bar);
26+
var_dump($foo < $bar);
27+
var_dump($foo >= $bar);
28+
var_dump($foo <= $bar);
29+
30+
var_dump($foo > true);
31+
var_dump($foo < true);
32+
var_dump($foo >= true);
33+
var_dump($foo <= true);
34+
35+
?>
36+
--EXPECT--
37+
bool(true)
38+
bool(true)
39+
bool(false)
40+
bool(false)
41+
bool(false)
42+
bool(false)
43+
bool(false)
44+
bool(false)
45+
bool(true)
46+
bool(true)
47+
bool(false)
48+
bool(false)
49+
bool(false)
50+
bool(false)
51+
bool(false)
52+
bool(false)
53+
bool(false)
54+
bool(false)
Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
--TEST--
2+
Enum implements (internal enum)
3+
--EXTENSIONS--
4+
zend_test
5+
--FILE--
6+
<?php
7+
8+
var_dump(ZendTestUnitEnum::Foo instanceof _ZendTestInterface);
9+
var_dump(ZendTestEnumWithInterface::Foo instanceof _ZendTestInterface);
10+
11+
?>
12+
--EXPECT--
13+
bool(false)
14+
bool(true)

Zend/tests/enum/instanceof-backed-enum.phpt

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
--TEST--
22
Auto implement BackedEnum interface
3+
--EXTENSIONS--
4+
zend_test
35
--FILE--
46
<?php
57

@@ -13,8 +15,12 @@ enum Baz: int {
1315

1416
var_dump(Foo::Bar instanceof BackedEnum);
1517
var_dump(Baz::Qux instanceof BackedEnum);
18+
var_dump(ZendTestUnitEnum::Foo instanceof BackedEnum);
19+
var_dump(ZendTestIntEnum::Foo instanceof BackedEnum);
1620

1721
?>
1822
--EXPECT--
1923
bool(false)
2024
bool(true)
25+
bool(false)
26+
bool(true)

Zend/tests/enum/instanceof-unitenum.phpt

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
--TEST--
22
Auto implement UnitEnum interface
3+
--EXTENSIONS--
4+
zend_test
35
--FILE--
46
<?php
57

@@ -11,8 +13,10 @@ class Baz {}
1113

1214
var_dump(Foo::Bar instanceof UnitEnum);
1315
var_dump((new Baz()) instanceof UnitEnum);
16+
var_dump(ZendTestUnitEnum::Foo instanceof UnitEnum);
1417

1518
?>
1619
--EXPECT--
1720
bool(true)
1821
bool(false)
22+
bool(true)
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
--TEST--
2+
Enum disallows cloning (internal enum)
3+
--EXTENSIONS--
4+
zend_test
5+
--FILE--
6+
<?php
7+
8+
try {
9+
var_dump(clone ZendTestIntEnum::Foo);
10+
} catch (Error $e) {
11+
echo $e->getMessage() . "\n";
12+
}
13+
14+
?>
15+
--EXPECT--
16+
Trying to clone an uncloneable object of class ZendTestIntEnum
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
--TEST--
2+
Enum case disallows dynamic properties (internal enum)
3+
--EXTENSIONS--
4+
zend_test
5+
--FILE--
6+
<?php
7+
8+
$bar = ZendTestUnitEnum::Bar;
9+
10+
try {
11+
$bar->baz = 'Baz';
12+
} catch (\Error $e) {
13+
echo $e->getMessage();
14+
}
15+
16+
?>
17+
--EXPECT--
18+
Cannot create dynamic property ZendTestUnitEnum::$baz

Zend/zend_enum.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -528,6 +528,8 @@ ZEND_API zend_class_entry *zend_register_internal_enum(
528528
zend_class_implements(ce, 1, zend_ce_backed_enum);
529529
}
530530

531+
ce->default_object_handlers = &zend_enum_object_handlers;
532+
531533
return ce;
532534
}
533535

ext/zend_test/test.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,7 @@ static zend_class_entry *zend_test_ns2_ns_foo_class;
7474
static zend_class_entry *zend_test_unit_enum;
7575
static zend_class_entry *zend_test_string_enum;
7676
static zend_class_entry *zend_test_int_enum;
77+
static zend_class_entry *zend_test_enum_with_interface;
7778
static zend_class_entry *zend_test_magic_call;
7879
static zend_object_handlers zend_test_class_handlers;
7980

@@ -1318,6 +1319,7 @@ PHP_MINIT_FUNCTION(zend_test)
13181319
zend_test_unit_enum = register_class_ZendTestUnitEnum();
13191320
zend_test_string_enum = register_class_ZendTestStringEnum();
13201321
zend_test_int_enum = register_class_ZendTestIntEnum();
1322+
zend_test_enum_with_interface = register_class_ZendTestEnumWithInterface(zend_test_interface);
13211323

13221324
zend_test_magic_call = register_class__ZendTestMagicCall();
13231325

ext/zend_test/test.stub.php

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -201,6 +201,11 @@ enum ZendTestIntEnum: int {
201201
case Baz = -1;
202202
}
203203

204+
enum ZendTestEnumWithInterface implements _ZendTestInterface {
205+
case Foo;
206+
case Bar;
207+
}
208+
204209
function zend_test_array_return(): array {}
205210

206211
/** @genstubs-expose-comment-block

ext/zend_test/test_arginfo.h

Lines changed: 15 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)