Skip to content

Commit dd05c08

Browse files
committed
Add support for declaring class entries in stubs
1 parent e73bf01 commit dd05c08

34 files changed

+927
-179
lines changed

Zend/zend_exceptions.c

Lines changed: 15 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -740,87 +740,49 @@ ZEND_METHOD(Exception, __toString)
740740
}
741741
/* }}} */
742742

743-
static void declare_exception_properties(zend_class_entry *ce)
744-
{
745-
zval val;
746-
747-
zend_declare_property_string(ce, "message", sizeof("message")-1, "", ZEND_ACC_PROTECTED);
748-
zend_declare_property_string(ce, "string", sizeof("string")-1, "", ZEND_ACC_PRIVATE);
749-
zend_declare_property_long(ce, "code", sizeof("code")-1, 0, ZEND_ACC_PROTECTED);
750-
zend_declare_property_null(ce, "file", sizeof("file")-1, ZEND_ACC_PROTECTED);
751-
zend_declare_property_null(ce, "line", sizeof("line")-1, ZEND_ACC_PROTECTED);
752-
753-
ZVAL_EMPTY_ARRAY(&val);
754-
zend_declare_typed_property(
755-
ce, ZSTR_KNOWN(ZEND_STR_TRACE), &val, ZEND_ACC_PRIVATE, NULL,
756-
(zend_type) ZEND_TYPE_INIT_MASK(MAY_BE_ARRAY));
757-
758-
ZVAL_NULL(&val);
759-
zend_declare_typed_property(
760-
ce, ZSTR_KNOWN(ZEND_STR_PREVIOUS), &val, ZEND_ACC_PRIVATE, NULL,
761-
(zend_type) ZEND_TYPE_INIT_CE(zend_ce_throwable, /* allow_null */ 1, 0));
762-
}
763-
764743
void zend_register_default_exception(void) /* {{{ */
765744
{
766-
zend_class_entry ce;
767-
768-
REGISTER_MAGIC_INTERFACE(throwable, Throwable);
769-
zend_class_implements(zend_ce_throwable, 1, zend_ce_stringable);
745+
register_class_Throwable(zend_ce_throwable, zend_ce_stringable);
746+
zend_ce_throwable->interface_gets_implemented = zend_implement_throwable;
770747

771748
memcpy(&default_exception_handlers, &std_object_handlers, sizeof(zend_object_handlers));
772749
default_exception_handlers.clone_obj = NULL;
773750

774-
INIT_CLASS_ENTRY(ce, "Exception", class_Exception_methods);
775-
zend_ce_exception = zend_register_internal_class_ex(&ce, NULL);
751+
register_class_Exception(zend_ce_exception, zend_ce_throwable);
776752
zend_ce_exception->create_object = zend_default_exception_new;
777-
zend_class_implements(zend_ce_exception, 1, zend_ce_throwable);
778-
declare_exception_properties(zend_ce_exception);
779753

780-
INIT_CLASS_ENTRY(ce, "ErrorException", class_ErrorException_methods);
781-
zend_ce_error_exception = zend_register_internal_class_ex(&ce, zend_ce_exception);
754+
register_class_ErrorException(zend_ce_error_exception, zend_ce_exception);
782755
zend_ce_error_exception->create_object = zend_error_exception_new;
783756
zend_declare_property_long(zend_ce_error_exception, "severity", sizeof("severity")-1, E_ERROR, ZEND_ACC_PROTECTED);
784757

785-
INIT_CLASS_ENTRY(ce, "Error", class_Error_methods);
786-
zend_ce_error = zend_register_internal_class_ex(&ce, NULL);
758+
register_class_Error(zend_ce_error, zend_ce_throwable);
787759
zend_ce_error->create_object = zend_default_exception_new;
788-
zend_class_implements(zend_ce_error, 1, zend_ce_throwable);
789-
declare_exception_properties(zend_ce_error);
790760

791-
INIT_CLASS_ENTRY(ce, "CompileError", class_CompileError_methods);
792-
zend_ce_compile_error = zend_register_internal_class_ex(&ce, zend_ce_error);
761+
register_class_CompileError(zend_ce_compile_error, zend_ce_error);
793762
zend_ce_compile_error->create_object = zend_default_exception_new;
794763

795-
INIT_CLASS_ENTRY(ce, "ParseError", class_ParseError_methods);
796-
zend_ce_parse_error = zend_register_internal_class_ex(&ce, zend_ce_compile_error);
764+
register_class_ParseError(zend_ce_parse_error, zend_ce_compile_error);
797765
zend_ce_parse_error->create_object = zend_default_exception_new;
798766

799-
INIT_CLASS_ENTRY(ce, "TypeError", class_TypeError_methods);
800-
zend_ce_type_error = zend_register_internal_class_ex(&ce, zend_ce_error);
767+
register_class_TypeError(zend_ce_type_error, zend_ce_error);
801768
zend_ce_type_error->create_object = zend_default_exception_new;
802769

803-
INIT_CLASS_ENTRY(ce, "ArgumentCountError", class_ArgumentCountError_methods);
804-
zend_ce_argument_count_error = zend_register_internal_class_ex(&ce, zend_ce_type_error);
770+
register_class_ArgumentCountError(zend_ce_argument_count_error, zend_ce_type_error);
805771
zend_ce_argument_count_error->create_object = zend_default_exception_new;
806772

807-
INIT_CLASS_ENTRY(ce, "ValueError", class_ValueError_methods);
808-
zend_ce_value_error = zend_register_internal_class_ex(&ce, zend_ce_error);
773+
register_class_ValueError(zend_ce_value_error, zend_ce_error);
809774
zend_ce_value_error->create_object = zend_default_exception_new;
810775

811-
INIT_CLASS_ENTRY(ce, "ArithmeticError", class_ArithmeticError_methods);
812-
zend_ce_arithmetic_error = zend_register_internal_class_ex(&ce, zend_ce_error);
776+
register_class_ArithmeticError(zend_ce_arithmetic_error, zend_ce_error);
813777
zend_ce_arithmetic_error->create_object = zend_default_exception_new;
814778

815-
INIT_CLASS_ENTRY(ce, "DivisionByZeroError", class_DivisionByZeroError_methods);
816-
zend_ce_division_by_zero_error = zend_register_internal_class_ex(&ce, zend_ce_arithmetic_error);
779+
register_class_DivisionByZeroError(zend_ce_division_by_zero_error, zend_ce_arithmetic_error);
817780
zend_ce_division_by_zero_error->create_object = zend_default_exception_new;
818781

819-
INIT_CLASS_ENTRY(zend_ce_unwind_exit, "UnwindExit", NULL);
820-
821-
INIT_CLASS_ENTRY(ce, "UnhandledMatchError", NULL);
822-
zend_ce_unhandled_match_error = zend_register_internal_class_ex(&ce, zend_ce_error);
782+
register_class_UnhandledMatchError(zend_ce_unhandled_match_error, zend_ce_error);
823783
zend_ce_unhandled_match_error->create_object = zend_default_exception_new;
784+
785+
INIT_CLASS_ENTRY(zend_ce_unwind_exit, "UnwindExit", NULL);
824786
}
825787
/* }}} */
826788

Zend/zend_exceptions.stub.php

Lines changed: 49 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
<?php
22

3-
/** @generate-function-entries */
3+
/**
4+
* @generate-function-entries
5+
* @generate-class-entries
6+
*/
47

58
interface Throwable extends Stringable
69
{
@@ -22,6 +25,21 @@ public function getTraceAsString(): string;
2225

2326
class Exception implements Throwable
2427
{
28+
/** @var string */
29+
protected $message = "";
30+
/** @var string */
31+
private $string = "";
32+
/** @var int */
33+
protected $code = 0;
34+
/** @var string|null */
35+
protected $file = null;
36+
/** @var int|null */
37+
protected $line = null;
38+
/** @known */
39+
private array $trace = [];
40+
/** @known */
41+
private ?Throwable $previous = null;
42+
2543
final private function __clone() {}
2644

2745
public function __construct(string $message = "", int $code = 0, ?Throwable $previous = null) {}
@@ -48,13 +66,38 @@ public function __toString(): string {}
4866

4967
class ErrorException extends Exception
5068
{
51-
public function __construct(string $message = "", int $code = 0, int $severity = E_ERROR, ?string $filename = null, ?int $line = null, ?Throwable $previous = null) {}
69+
/** @var int */
70+
protected $severity = E_ERROR;
71+
72+
public function __construct(
73+
string $message = "",
74+
int $code = 0,
75+
int $severity = E_ERROR,
76+
?string $filename = null,
77+
?int $line = null,
78+
?Throwable $previous = null
79+
) {}
5280

5381
final public function getSeverity(): int {}
5482
}
5583

5684
class Error implements Throwable
5785
{
86+
/** @var string */
87+
protected $message = "";
88+
/** @var string */
89+
private $string = "";
90+
/** @var int */
91+
protected $code = 0;
92+
/** @var string|null */
93+
protected $file = null;
94+
/** @var int|null */
95+
protected $line = null;
96+
/** @known */
97+
private array $trace = [];
98+
/** @known */
99+
private ?Throwable $previous = null;
100+
58101
/** @implementation-alias Exception::__clone */
59102
final private function __clone() {}
60103

@@ -119,3 +162,7 @@ class ArithmeticError extends Error
119162
class DivisionByZeroError extends ArithmeticError
120163
{
121164
}
165+
166+
class UnhandledMatchError extends Error
167+
{
168+
}

Zend/zend_exceptions_arginfo.h

Lines changed: 142 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
/* This is a generated file, edit the .stub.php file instead.
2-
* Stub hash: bc49b326136997660887b12f0c59f8a57b17ecaf */
2+
* Stub hash: 8593bcd9dd8350f84533b9592c3d6a2885e97d07 */
33

44
ZEND_BEGIN_ARG_WITH_RETURN_TYPE_INFO_EX(arginfo_class_Throwable_getMessage, 0, 0, IS_STRING, 0)
55
ZEND_END_ARG_INFO()
@@ -179,3 +179,144 @@ static const zend_function_entry class_ArithmeticError_methods[] = {
179179
static const zend_function_entry class_DivisionByZeroError_methods[] = {
180180
ZEND_FE_END
181181
};
182+
183+
184+
static const zend_function_entry class_UnhandledMatchError_methods[] = {
185+
ZEND_FE_END
186+
};
187+
188+
#define register_class_Throwable(class_entry, class_entry_Stringable) \
189+
{ \
190+
zend_class_entry ce; \
191+
\
192+
INIT_CLASS_ENTRY(ce, "Throwable", class_Throwable_methods); \
193+
class_entry = zend_register_internal_interface(&ce); \
194+
zend_class_implements(class_entry, 1, class_entry_Stringable);
195+
}
196+
197+
#define register_class_Exception(class_entry, class_entry_Throwable) \
198+
{ \
199+
zend_class_entry ce; \
200+
\
201+
INIT_CLASS_ENTRY(ce, "Exception", class_Exception_methods); \
202+
class_entry = zend_register_internal_class_ex(&ce, NULL); \
203+
zend_class_implements(class_entry, 1, class_entry_Throwable); \
204+
\
205+
zend_declare_property_string(class_entry, "message", sizeof("message") - 1, "", ZEND_ACC_PROTECTED); \
206+
\
207+
zend_declare_property_string(class_entry, "string", sizeof("string") - 1, "", ZEND_ACC_PRIVATE); \
208+
\
209+
zend_declare_property_long(class_entry, "code", sizeof("code") - 1, 0, ZEND_ACC_PROTECTED); \
210+
\
211+
zend_declare_property_null(class_entry, "file", sizeof("file") - 1, ZEND_ACC_PROTECTED); \
212+
\
213+
zend_declare_property_null(class_entry, "line", sizeof("line") - 1, ZEND_ACC_PROTECTED); \
214+
\
215+
zval property_trace_default_value; \
216+
ZVAL_EMPTY_ARRAY(&property_trace_default_value); \
217+
zend_declare_typed_property(class_entry, ZSTR_KNOWN(ZEND_STR_TRACE), &property_trace_default_value, ZEND_ACC_PRIVATE, NULL, (zend_type) ZEND_TYPE_INIT_MASK(MAY_BE_ARRAY)); \
218+
\
219+
zval property_previous_default_value; \
220+
ZVAL_NULL(&property_previous_default_value); \
221+
zend_declare_typed_property(class_entry, ZSTR_KNOWN(ZEND_STR_PREVIOUS), &property_previous_default_value, ZEND_ACC_PRIVATE, NULL, (zend_type) ZEND_TYPE_INIT_CE(class_entry_Throwable, 1, 0)); \
222+
}
223+
224+
#define register_class_ErrorException(class_entry, class_entry_Exception) \
225+
{ \
226+
zend_class_entry ce; \
227+
\
228+
INIT_CLASS_ENTRY(ce, "ErrorException", class_ErrorException_methods); \
229+
class_entry = zend_register_internal_class_ex(&ce, class_entry_Exception); \
230+
}
231+
232+
#define register_class_Error(class_entry, class_entry_Throwable) \
233+
{ \
234+
zend_class_entry ce; \
235+
\
236+
INIT_CLASS_ENTRY(ce, "Error", class_Error_methods); \
237+
class_entry = zend_register_internal_class_ex(&ce, NULL); \
238+
zend_class_implements(class_entry, 1, class_entry_Throwable); \
239+
\
240+
zend_declare_property_string(class_entry, "message", sizeof("message") - 1, "", ZEND_ACC_PROTECTED); \
241+
\
242+
zend_declare_property_string(class_entry, "string", sizeof("string") - 1, "", ZEND_ACC_PRIVATE); \
243+
\
244+
zend_declare_property_long(class_entry, "code", sizeof("code") - 1, 0, ZEND_ACC_PROTECTED); \
245+
\
246+
zend_declare_property_null(class_entry, "file", sizeof("file") - 1, ZEND_ACC_PROTECTED); \
247+
\
248+
zend_declare_property_null(class_entry, "line", sizeof("line") - 1, ZEND_ACC_PROTECTED); \
249+
\
250+
zval property_trace_default_value; \
251+
ZVAL_EMPTY_ARRAY(&property_trace_default_value); \
252+
zend_declare_typed_property(class_entry, ZSTR_KNOWN(ZEND_STR_TRACE), &property_trace_default_value, ZEND_ACC_PRIVATE, NULL, (zend_type) ZEND_TYPE_INIT_MASK(MAY_BE_ARRAY)); \
253+
\
254+
zval property_previous_default_value; \
255+
ZVAL_NULL(&property_previous_default_value); \
256+
zend_declare_typed_property(class_entry, ZSTR_KNOWN(ZEND_STR_PREVIOUS), &property_previous_default_value, ZEND_ACC_PRIVATE, NULL, (zend_type) ZEND_TYPE_INIT_CE(class_entry_Throwable, 1, 0)); \
257+
}
258+
259+
#define register_class_CompileError(class_entry, class_entry_Error) \
260+
{ \
261+
zend_class_entry ce; \
262+
\
263+
INIT_CLASS_ENTRY(ce, "CompileError", class_CompileError_methods); \
264+
class_entry = zend_register_internal_class_ex(&ce, class_entry_Error); \
265+
}
266+
267+
#define register_class_ParseError(class_entry, class_entry_CompileError) \
268+
{ \
269+
zend_class_entry ce; \
270+
\
271+
INIT_CLASS_ENTRY(ce, "ParseError", class_ParseError_methods); \
272+
class_entry = zend_register_internal_class_ex(&ce, class_entry_CompileError); \
273+
}
274+
275+
#define register_class_TypeError(class_entry, class_entry_Error) \
276+
{ \
277+
zend_class_entry ce; \
278+
\
279+
INIT_CLASS_ENTRY(ce, "TypeError", class_TypeError_methods); \
280+
class_entry = zend_register_internal_class_ex(&ce, class_entry_Error); \
281+
}
282+
283+
#define register_class_ArgumentCountError(class_entry, class_entry_TypeError) \
284+
{ \
285+
zend_class_entry ce; \
286+
\
287+
INIT_CLASS_ENTRY(ce, "ArgumentCountError", class_ArgumentCountError_methods); \
288+
class_entry = zend_register_internal_class_ex(&ce, class_entry_TypeError); \
289+
}
290+
291+
#define register_class_ValueError(class_entry, class_entry_Error) \
292+
{ \
293+
zend_class_entry ce; \
294+
\
295+
INIT_CLASS_ENTRY(ce, "ValueError", class_ValueError_methods); \
296+
class_entry = zend_register_internal_class_ex(&ce, class_entry_Error); \
297+
}
298+
299+
#define register_class_ArithmeticError(class_entry, class_entry_Error) \
300+
{ \
301+
zend_class_entry ce; \
302+
\
303+
INIT_CLASS_ENTRY(ce, "ArithmeticError", class_ArithmeticError_methods); \
304+
class_entry = zend_register_internal_class_ex(&ce, class_entry_Error); \
305+
}
306+
307+
#define register_class_DivisionByZeroError(class_entry, class_entry_ArithmeticError) \
308+
{ \
309+
zend_class_entry ce; \
310+
\
311+
INIT_CLASS_ENTRY(ce, "DivisionByZeroError", class_DivisionByZeroError_methods); \
312+
class_entry = zend_register_internal_class_ex(&ce, class_entry_ArithmeticError); \
313+
}
314+
315+
#define register_class_UnhandledMatchError(class_entry, class_entry_Error) \
316+
{ \
317+
zend_class_entry ce; \
318+
\
319+
INIT_CLASS_ENTRY(ce, "UnhandledMatchError", class_UnhandledMatchError_methods); \
320+
class_entry = zend_register_internal_class_ex(&ce, class_entry_Error); \
321+
}
322+

0 commit comments

Comments
 (0)