@@ -696,21 +696,20 @@ static inheritance_status zend_is_type_subtype_of_generic_type(
696
696
ZEND_ASSERT (bound_generic_types && "Have generic type" );
697
697
ZEND_ASSERT (ZEND_TYPE_IS_GENERIC_PARAM_NAME (generic_type ));
698
698
699
- const zend_type * bound_type_ptr = zend_hash_find_ptr (bound_generic_types , ZEND_TYPE_NAME ( generic_type ) );
699
+ const zend_type * bound_type_ptr = zend_hash_index_find_ptr (bound_generic_types , generic_type . generic_param_index );
700
700
ZEND_ASSERT (bound_type_ptr != NULL );
701
701
if (ZEND_TYPE_IS_GENERIC_PARAM_NAME (* bound_type_ptr )) {
702
702
const zend_type concrete_type = * concrete_type_ptr ;
703
703
if (
704
704
ZEND_TYPE_IS_GENERIC_PARAM_NAME (concrete_type )
705
- && zend_string_equals ( ZEND_TYPE_NAME ( concrete_type ), ZEND_TYPE_NAME ( * bound_type_ptr ))
705
+ && concrete_type . generic_param_index == bound_type_ptr -> generic_param_index
706
706
) {
707
707
return INHERITANCE_SUCCESS ;
708
708
} else {
709
709
return INHERITANCE_ERROR ;
710
710
}
711
711
} else {
712
712
/* Generic type must be invariant */
713
- // TODO Use zend_perform_contravariant_type_check()?
714
713
const inheritance_status sub_type_status = zend_perform_covariant_type_check (
715
714
concrete_scope , concrete_type_ptr , generic_type_scope , bound_type_ptr );
716
715
const inheritance_status super_type_status = zend_perform_contravariant_type_check (
@@ -821,43 +820,34 @@ static inheritance_status zend_is_generic_type_subtype_of_generic_type(
821
820
const zend_class_entry * fe_scope , const zend_type * fe_type_ptr ,
822
821
const zend_class_entry * proto_scope , const zend_type * proto_type_ptr
823
822
) {
824
- const zend_type fe_type = * fe_type_ptr ;
825
- const zend_type proto_type = * proto_type_ptr ;
826
-
827
- if (UNEXPECTED (!ZEND_TYPE_IS_GENERIC_PARAM_NAME (proto_type ))) {
823
+ if (UNEXPECTED (!ZEND_TYPE_IS_GENERIC_PARAM_NAME (* proto_type_ptr ))) {
828
824
/* A generic type cannot be a subtype of a concrete one */
829
825
return INHERITANCE_ERROR ;
830
826
}
831
- ZEND_ASSERT (ZEND_TYPE_IS_GENERIC_PARAM_NAME (fe_type ));
827
+ ZEND_ASSERT (ZEND_TYPE_IS_GENERIC_PARAM_NAME (* fe_type_ptr ));
832
828
ZEND_ASSERT (fe_scope -> bound_types );
833
829
834
830
const HashTable * bound_generic_types = zend_hash_find_ptr_lc (fe_scope -> bound_types , proto_scope -> name );
835
831
ZEND_ASSERT (bound_generic_types && "Must have bound generic type" );
836
832
837
- zend_string * proto_type_name = ZEND_TYPE_NAME (proto_type );
838
- ZEND_ASSERT (proto_type_name );
839
-
840
- const zend_type * bound_type_ptr = zend_hash_find_ptr (bound_generic_types , proto_type_name );
833
+ const zend_type * bound_type_ptr = zend_hash_index_find_ptr (bound_generic_types , proto_type_ptr -> generic_param_index );
841
834
ZEND_ASSERT (bound_type_ptr != NULL );
842
835
843
836
const zend_type bound_type = * bound_type_ptr ;
844
837
ZEND_ASSERT (ZEND_TYPE_IS_GENERIC_PARAM_NAME (bound_type ));
845
838
846
- return zend_string_equals ( ZEND_TYPE_NAME ( bound_type ), ZEND_TYPE_NAME ( fe_type )) ? INHERITANCE_SUCCESS : INHERITANCE_ERROR ;
839
+ return bound_type_ptr -> generic_param_index == fe_type_ptr -> generic_param_index ? INHERITANCE_SUCCESS : INHERITANCE_ERROR ;
847
840
}
848
841
849
842
static inheritance_status zend_perform_covariant_type_check (
850
843
zend_class_entry * fe_scope , const zend_type * fe_type_ptr ,
851
844
zend_class_entry * proto_scope , const zend_type * proto_type_ptr
852
845
) {
853
- const zend_type fe_type = * fe_type_ptr ;
854
- const zend_type proto_type = * proto_type_ptr ;
855
-
856
846
/* If we check for concrete return type */
857
- if (ZEND_TYPE_IS_GENERIC_PARAM_NAME (proto_type )) {
847
+ if (ZEND_TYPE_IS_GENERIC_PARAM_NAME (* proto_type_ptr )) {
858
848
return zend_is_type_subtype_of_generic_type (
859
849
fe_scope , fe_type_ptr , proto_scope , proto_type_ptr );
860
- } else if (UNEXPECTED (ZEND_TYPE_IS_GENERIC_PARAM_NAME (fe_type ))) {
850
+ } else if (UNEXPECTED (ZEND_TYPE_IS_GENERIC_PARAM_NAME (* fe_type_ptr ))) {
861
851
/* A generic type cannot be a subtype of a concrete one */
862
852
return INHERITANCE_ERROR ;
863
853
}
@@ -1057,7 +1047,7 @@ static ZEND_COLD zend_string *zend_get_function_declaration(
1057
1047
const zend_generic_parameter param = scope -> generic_parameters [i ];
1058
1048
zend_string * constraint_type_str ;
1059
1049
if (bound_types_to_scope ) {
1060
- const zend_type * constraint = zend_hash_find_ptr (bound_types_to_scope , param . name );
1050
+ const zend_type * constraint = zend_hash_index_find_ptr (bound_types_to_scope , i );
1061
1051
ZEND_ASSERT (constraint != NULL );
1062
1052
constraint_type_str = zend_type_to_string_resolved (* constraint , scope , NULL );
1063
1053
} else {
@@ -2351,23 +2341,19 @@ ZEND_ATTRIBUTE_NONNULL static void bind_generic_types_for_inherited_interfaces(z
2351
2341
false /* TODO depends on internals */
2352
2342
);
2353
2343
ZEND_HASH_FOREACH_KEY_PTR (interface_bound_types_for_inherited_iface , generic_param_index , generic_param_name , bound_type_ptr ) {
2344
+ ZEND_ASSERT (generic_param_name == NULL ); // TODO Change foreach macro;
2354
2345
zend_type bound_type = * bound_type_ptr ;
2355
2346
if (ZEND_TYPE_IS_GENERIC_PARAM_NAME (bound_type )) {
2356
2347
ZEND_ASSERT (ce_bound_types_for_direct_iface != NULL &&
2357
2348
"If a bound type is generic then we must have bound types for the current interface" );
2358
- const zend_type * ce_bound_type_ptr = zend_hash_find_ptr (ce_bound_types_for_direct_iface , ZEND_TYPE_NAME ( bound_type ) );
2349
+ const zend_type * ce_bound_type_ptr = zend_hash_index_find_ptr (ce_bound_types_for_direct_iface , bound_type_ptr -> generic_param_index );
2359
2350
ZEND_ASSERT (ce_bound_type_ptr != NULL );
2360
2351
bound_type = * ce_bound_type_ptr ;
2361
2352
}
2362
2353
2363
2354
zend_type_copy_ctor (& bound_type , true, false /* TODO Depends on internal or not? */ );
2364
- if (generic_param_name ) {
2365
- zend_hash_add_mem (ce_bound_types_for_inherited_iface , generic_param_name ,
2366
- & bound_type , sizeof (bound_type ));
2367
- } else {
2368
- zend_hash_index_add_mem (ce_bound_types_for_inherited_iface , generic_param_index ,
2369
- & bound_type , sizeof (bound_type ));
2370
- }
2355
+ zend_hash_index_add_mem (ce_bound_types_for_inherited_iface , generic_param_index ,
2356
+ & bound_type , sizeof (bound_type ));
2371
2357
} ZEND_HASH_FOREACH_END ();
2372
2358
2373
2359
const HashTable * existing_bound_types_for_inherited_iface = zend_hash_find_ptr (ce -> bound_types , lc_inherited_iface_name );
@@ -2505,13 +2491,6 @@ static void do_interface_implementation(zend_class_entry *ce, zend_class_entry *
2505
2491
return ;
2506
2492
}
2507
2493
}
2508
- /* Deep type copy */
2509
- zend_type bound_type = * bound_type_ptr ;
2510
- zend_type_copy_ctor (& bound_type , true, false);
2511
- zend_hash_add_mem (bound_types , generic_parameter -> name ,
2512
- & bound_type , sizeof (bound_type ));
2513
- ///* Should we change the key from index to generic parameter name? */
2514
- //zend_hash_index_del(bound_types, i);
2515
2494
}
2516
2495
}
2517
2496
bind_generic_types_for_inherited_interfaces (ce , iface );
0 commit comments