Skip to content

Commit 80a6adc

Browse files
committed
Merge branch 'PHP-8.4' into PHP-8.5
* PHP-8.4: Fix EG(current_execute_data) introduced in 1292037
2 parents 1dd866d + a5e1baf commit 80a6adc

File tree

3 files changed

+45
-13
lines changed

3 files changed

+45
-13
lines changed

Zend/tests/oss_fuzz_456317305.phpt

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
--TEST--
2+
OSS-Fuzz #456317305: EG(current_execute_data) NULL pointer violation
3+
--FILE--
4+
<?php
5+
6+
class C {
7+
public function __destruct() {
8+
static $again = true;
9+
if ($again) {
10+
$again = false;
11+
$c = new C;
12+
}
13+
throw new Exception;
14+
}
15+
}
16+
17+
$c = new C;
18+
19+
?>
20+
--EXPECTF--
21+
Fatal error: Uncaught Exception in %s:%d
22+
Stack trace:
23+
#0 [internal function]: C->__destruct()
24+
#1 {main}
25+
thrown in %s on line %d

Zend/zend_generators.c

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -313,9 +313,11 @@ static void zend_generator_dtor_storage(zend_object *object) /* {{{ */
313313
zend_object *old_exception = NULL;
314314
const zend_op *old_opline_before_exception = NULL;
315315
if (EG(exception)) {
316-
EG(current_execute_data)->opline = EG(opline_before_exception);
316+
if (EG(current_execute_data)) {
317+
EG(current_execute_data)->opline = EG(opline_before_exception);
318+
old_opline_before_exception = EG(opline_before_exception);
319+
}
317320
old_exception = EG(exception);
318-
old_opline_before_exception = EG(opline_before_exception);
319321
EG(exception) = NULL;
320322
}
321323

@@ -328,8 +330,10 @@ static void zend_generator_dtor_storage(zend_object *object) /* {{{ */
328330
zend_generator_resume(generator);
329331

330332
if (old_exception) {
331-
EG(current_execute_data)->opline = EG(exception_op);
332-
EG(opline_before_exception) = old_opline_before_exception;
333+
if (EG(current_execute_data)) {
334+
EG(current_execute_data)->opline = EG(exception_op);
335+
EG(opline_before_exception) = old_opline_before_exception;
336+
}
333337
if (EG(exception)) {
334338
zend_exception_set_previous(EG(exception), old_exception);
335339
} else {

Zend/zend_objects.c

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -121,7 +121,7 @@ ZEND_API void zend_objects_destroy_object(zend_object *object)
121121
}
122122

123123
zend_object *old_exception;
124-
const zend_op *old_opline_before_exception;
124+
const zend_op *old_opline_before_exception = NULL;
125125

126126
if (destructor->common.fn_flags & (ZEND_ACC_PRIVATE|ZEND_ACC_PROTECTED)) {
127127
if (EG(current_execute_data)) {
@@ -156,23 +156,26 @@ ZEND_API void zend_objects_destroy_object(zend_object *object)
156156
if (EG(exception) == object) {
157157
zend_error_noreturn(E_CORE_ERROR, "Attempt to destruct pending exception");
158158
} else {
159-
if (EG(current_execute_data)
160-
&& EG(current_execute_data)->func
161-
&& ZEND_USER_CODE(EG(current_execute_data)->func->common.type)) {
162-
zend_rethrow_exception(EG(current_execute_data));
159+
if (EG(current_execute_data)) {
160+
if (EG(current_execute_data)->func
161+
&& ZEND_USER_CODE(EG(current_execute_data)->func->common.type)) {
162+
zend_rethrow_exception(EG(current_execute_data));
163+
}
164+
EG(current_execute_data)->opline = EG(opline_before_exception);
165+
old_opline_before_exception = EG(opline_before_exception);
163166
}
164-
EG(current_execute_data)->opline = EG(opline_before_exception);
165167
old_exception = EG(exception);
166-
old_opline_before_exception = EG(opline_before_exception);
167168
EG(exception) = NULL;
168169
}
169170
}
170171

171172
zend_call_known_instance_method_with_0_params(destructor, object, NULL);
172173

173174
if (old_exception) {
174-
EG(current_execute_data)->opline = EG(exception_op);
175-
EG(opline_before_exception) = old_opline_before_exception;
175+
if (EG(current_execute_data)) {
176+
EG(current_execute_data)->opline = EG(exception_op);
177+
EG(opline_before_exception) = old_opline_before_exception;
178+
}
176179
if (EG(exception)) {
177180
zend_exception_set_previous(EG(exception), old_exception);
178181
} else {

0 commit comments

Comments
 (0)