@@ -97,6 +97,7 @@ PHPAPI zend_class_entry *reflection_enum_ptr;
97
97
PHPAPI zend_class_entry * reflection_enum_unit_case_ptr ;
98
98
PHPAPI zend_class_entry * reflection_enum_backed_case_ptr ;
99
99
PHPAPI zend_class_entry * reflection_fiber_ptr ;
100
+ PHPAPI zend_class_entry * reflection_constant_ptr ;
100
101
101
102
/* Exception throwing macro */
102
103
#define _DO_THROW (msg ) \
@@ -1250,6 +1251,19 @@ static void _zend_extension_string(smart_str *str, zend_extension *extension, ch
1250
1251
}
1251
1252
/* }}} */
1252
1253
1254
+ static void _const_decl_string (smart_str * str , zend_constant * const_ )
1255
+ {
1256
+ smart_str_append_printf (str , "Const [ " );
1257
+ if (ZEND_CONSTANT_FLAGS (const_ ) & CONST_DEPRECATED ) {
1258
+ smart_str_append_printf (str , "<deprecated> " );
1259
+ }
1260
+ smart_str_append_printf (str , "%s = " , ZSTR_VAL (const_ -> name ));
1261
+ if (format_default_value (str , & const_ -> value ) == FAILURE ) {
1262
+ return ;
1263
+ }
1264
+ smart_str_appends (str , " ]\n" );
1265
+ }
1266
+
1253
1267
/* {{{ _function_check_flag */
1254
1268
static void _function_check_flag (INTERNAL_FUNCTION_PARAMETERS , int mask )
1255
1269
{
@@ -7207,6 +7221,140 @@ static zval *_reflection_write_property(zend_object *object, zend_string *name,
7207
7221
}
7208
7222
/* }}} */
7209
7223
7224
+ ZEND_METHOD (ReflectionConstant , __construct )
7225
+ {
7226
+ zend_string * name ;
7227
+
7228
+ zval * object = ZEND_THIS ;
7229
+ reflection_object * intern = Z_REFLECTION_P (object );
7230
+
7231
+ ZEND_PARSE_PARAMETERS_START (1 , 1 )
7232
+ Z_PARAM_STR (name )
7233
+ ZEND_PARSE_PARAMETERS_END ();
7234
+
7235
+ /* Build name with lowercased ns. */
7236
+ bool backslash_prefixed = ZSTR_VAL (name )[0 ] == '\\' ;
7237
+ char * source = ZSTR_VAL (name ) + backslash_prefixed ;
7238
+ size_t source_len = ZSTR_LEN (name ) - backslash_prefixed ;
7239
+ zend_string * lc_name = zend_string_alloc (source_len , /* persistent */ false);
7240
+ const char * ns_end = zend_memrchr (source , '\\' , source_len );
7241
+ size_t ns_len = 0 ;
7242
+ if (ns_end ) {
7243
+ ns_len = ns_end - ZSTR_VAL (name );
7244
+ zend_str_tolower_copy (ZSTR_VAL (lc_name ), source , ns_len );
7245
+ }
7246
+ memcpy (ZSTR_VAL (lc_name ) + ns_len , source + ns_len , source_len - ns_len );
7247
+
7248
+ zend_constant * const_ = zend_get_constant_ptr (lc_name );
7249
+ zend_string_release_ex (lc_name , /* persistent */ false);
7250
+ if (!const_ ) {
7251
+ zend_throw_exception_ex (reflection_exception_ptr , 0 , "Constant \"%s\" does not exist" , ZSTR_VAL (name ));
7252
+ RETURN_THROWS ();
7253
+ }
7254
+
7255
+ intern -> ptr = const_ ;
7256
+ intern -> ref_type = REF_TYPE_OTHER ;
7257
+
7258
+ zval * name_zv = reflection_prop_name (object );
7259
+ zval_ptr_dtor (name_zv );
7260
+ ZVAL_STR_COPY (name_zv , name );
7261
+ }
7262
+
7263
+ ZEND_METHOD (ReflectionConstant , getName )
7264
+ {
7265
+ reflection_object * intern ;
7266
+ zend_constant * const_ ;
7267
+
7268
+ if (zend_parse_parameters_none () == FAILURE ) {
7269
+ RETURN_THROWS ();
7270
+ }
7271
+
7272
+ GET_REFLECTION_OBJECT_PTR (const_ );
7273
+ RETURN_STR_COPY (const_ -> name );
7274
+ }
7275
+
7276
+ ZEND_METHOD (ReflectionConstant , getNamespaceName )
7277
+ {
7278
+ reflection_object * intern ;
7279
+ zend_constant * const_ ;
7280
+
7281
+ if (zend_parse_parameters_none () == FAILURE ) {
7282
+ RETURN_THROWS ();
7283
+ }
7284
+
7285
+ GET_REFLECTION_OBJECT_PTR (const_ );
7286
+
7287
+ const char * backslash = zend_memrchr (ZSTR_VAL (const_ -> name ), '\\' , ZSTR_LEN (const_ -> name ));
7288
+ if (backslash ) {
7289
+ size_t length = backslash - ZSTR_VAL (const_ -> name );
7290
+ RETURN_STRINGL (ZSTR_VAL (const_ -> name ), length );
7291
+ } else {
7292
+ RETURN_EMPTY_STRING ();
7293
+ }
7294
+ }
7295
+
7296
+ ZEND_METHOD (ReflectionConstant , getShortName )
7297
+ {
7298
+ reflection_object * intern ;
7299
+ zend_constant * const_ ;
7300
+
7301
+ if (zend_parse_parameters_none () == FAILURE ) {
7302
+ RETURN_THROWS ();
7303
+ }
7304
+
7305
+ GET_REFLECTION_OBJECT_PTR (const_ );
7306
+
7307
+ const char * backslash = zend_memrchr (ZSTR_VAL (const_ -> name ), '\\' , ZSTR_LEN (const_ -> name ));
7308
+ if (backslash ) {
7309
+ size_t prefix = backslash - ZSTR_VAL (const_ -> name ) + 1 ;
7310
+ size_t length = ZSTR_LEN (const_ -> name ) - prefix ;
7311
+ RETURN_STRINGL (ZSTR_VAL (const_ -> name ) + prefix , length );
7312
+ } else {
7313
+ RETURN_STR_COPY (const_ -> name );
7314
+ }
7315
+ }
7316
+
7317
+ ZEND_METHOD (ReflectionConstant , getValue )
7318
+ {
7319
+ reflection_object * intern ;
7320
+ zend_constant * const_ ;
7321
+
7322
+ if (zend_parse_parameters_none () == FAILURE ) {
7323
+ RETURN_THROWS ();
7324
+ }
7325
+
7326
+ GET_REFLECTION_OBJECT_PTR (const_ );
7327
+ RETURN_COPY (& const_ -> value );
7328
+ }
7329
+
7330
+ ZEND_METHOD (ReflectionConstant , isDeprecated )
7331
+ {
7332
+ reflection_object * intern ;
7333
+ zend_constant * const_ ;
7334
+
7335
+ if (zend_parse_parameters_none () == FAILURE ) {
7336
+ RETURN_THROWS ();
7337
+ }
7338
+
7339
+ GET_REFLECTION_OBJECT_PTR (const_ );
7340
+ RETURN_BOOL (ZEND_CONSTANT_FLAGS (const_ ) & CONST_DEPRECATED );
7341
+ }
7342
+
7343
+ ZEND_METHOD (ReflectionConstant , __toString )
7344
+ {
7345
+ reflection_object * intern ;
7346
+ zend_constant * const_ ;
7347
+ smart_str str = {0 };
7348
+
7349
+ if (zend_parse_parameters_none () == FAILURE ) {
7350
+ RETURN_THROWS ();
7351
+ }
7352
+
7353
+ GET_REFLECTION_OBJECT_PTR (const_ );
7354
+ _const_decl_string (& str , const_ );
7355
+ RETURN_STR (smart_str_extract (& str ));
7356
+ }
7357
+
7210
7358
PHP_MINIT_FUNCTION (reflection ) /* {{{ */
7211
7359
{
7212
7360
memcpy (& reflection_object_handlers , & std_object_handlers , sizeof (zend_object_handlers ));
@@ -7306,6 +7454,10 @@ PHP_MINIT_FUNCTION(reflection) /* {{{ */
7306
7454
reflection_fiber_ptr -> create_object = reflection_objects_new ;
7307
7455
reflection_fiber_ptr -> default_object_handlers = & reflection_object_handlers ;
7308
7456
7457
+ reflection_constant_ptr = register_class_ReflectionConstant (reflector_ptr );
7458
+ reflection_constant_ptr -> create_object = reflection_objects_new ;
7459
+ reflection_constant_ptr -> default_object_handlers = & reflection_object_handlers ;
7460
+
7309
7461
REFLECTION_G (key_initialized ) = 0 ;
7310
7462
7311
7463
return SUCCESS ;
0 commit comments