Skip to content

Commit 5f79902

Browse files
committed
ext/standard/array.c: restore helper-based SORT_REGULAR routing
- Make every php_get_*_compare_func{,_reverse,_unstable} return the *_regular variants so the public sort APIs no longer need php_array_sort_regular() - Drop php_array_sort_regular() and the old key/data compare impl helpers now that their logic lives in the generated *_regular comparators - Have array_unique() fetch its unstable comparator exclusively through php_get_data_compare_func_unstable(), matching the rest of the sort entry points
1 parent b6c2308 commit 5f79902

File tree

1 file changed

+7
-110
lines changed

1 file changed

+7
-110
lines changed

ext/standard/array.c

Lines changed: 7 additions & 110 deletions
Original file line numberDiff line numberDiff line change
@@ -149,34 +149,6 @@ static zend_always_inline int php_array_compare_enum_zvals(zval *lhs, zval *rhs)
149149
return lhs_enum ? 1 : -1;
150150
}
151151

152-
static zend_always_inline int php_array_key_compare_impl(Bucket *f, Bucket *s) /* {{{ */
153-
{
154-
zval first;
155-
zval second;
156-
157-
if (f->key == NULL && s->key == NULL) {
158-
return (zend_long)f->h > (zend_long)s->h ? 1 : -1;
159-
} else if (f->key && s->key) {
160-
if ((unsigned char)f->key->val[0] > '9'
161-
&& (unsigned char)s->key->val[0] > '9') {
162-
return zend_compare_non_numeric_strings(f->key, s->key);
163-
}
164-
return zendi_smart_strcmp(f->key, s->key);
165-
}
166-
if (f->key) {
167-
ZVAL_STR(&first, f->key);
168-
} else {
169-
ZVAL_LONG(&first, f->h);
170-
}
171-
if (s->key) {
172-
ZVAL_STR(&second, s->key);
173-
} else {
174-
ZVAL_LONG(&second, s->h);
175-
}
176-
return zend_compare(&first, &second);
177-
}
178-
/* }}} */
179-
180152
static zend_always_inline int php_array_key_compare_numeric_unstable_i(Bucket *f, Bucket *s) /* {{{ */
181153
{
182154
if (f->key == NULL && s->key == NULL) {
@@ -317,32 +289,6 @@ static zend_always_inline int php_array_key_compare_string_locale_unstable_i(Buc
317289
}
318290
/* }}} */
319291

320-
static zend_always_inline int php_array_data_compare_impl(Bucket *f, Bucket *s) /* {{{ */
321-
{
322-
int result = zend_compare(&f->val, &s->val);
323-
/* Special enums handling for array_unique. We don't want to add this logic to zend_compare as
324-
* that would be observable via comparison operators. */
325-
zval *rhs = &s->val;
326-
ZVAL_DEREF(rhs);
327-
if (UNEXPECTED(Z_TYPE_P(rhs) == IS_OBJECT)
328-
&& result == ZEND_UNCOMPARABLE
329-
&& (Z_OBJCE_P(rhs)->ce_flags & ZEND_ACC_ENUM)) {
330-
zval *lhs = &f->val;
331-
ZVAL_DEREF(lhs);
332-
if (Z_TYPE_P(lhs) == IS_OBJECT && (Z_OBJCE_P(lhs)->ce_flags & ZEND_ACC_ENUM)) {
333-
// Order doesn't matter, we just need to group the same enum values
334-
uintptr_t lhs_uintptr = (uintptr_t)Z_OBJ_P(lhs);
335-
uintptr_t rhs_uintptr = (uintptr_t)Z_OBJ_P(rhs);
336-
return lhs_uintptr == rhs_uintptr ? 0 : (lhs_uintptr < rhs_uintptr ? -1 : 1);
337-
} else {
338-
// Shift enums to the end of the array
339-
return -1;
340-
}
341-
}
342-
return result;
343-
}
344-
/* }}} */
345-
346292
static zend_always_inline int php_array_data_compare_numeric_unstable_i(Bucket *f, Bucket *s) /* {{{ */
347293
{
348294
return numeric_compare_function(&f->val, &s->val);
@@ -393,12 +339,10 @@ static int php_array_data_compare_string_locale_unstable_i(Bucket *f, Bucket *s)
393339
}
394340
/* }}} */
395341

396-
DEFINE_SORT_VARIANTS_USING(key_compare, php_array_key_compare_impl);
397342
DEFINE_SORT_VARIANTS(key_compare_numeric);
398343
DEFINE_SORT_VARIANTS(key_compare_string_case);
399344
DEFINE_SORT_VARIANTS(key_compare_string);
400345
DEFINE_SORT_VARIANTS(key_compare_string_locale);
401-
DEFINE_SORT_VARIANTS_USING(data_compare, php_array_data_compare_impl);
402346
DEFINE_SORT_VARIANTS(data_compare_numeric);
403347
DEFINE_SORT_VARIANTS(data_compare_string_case);
404348
DEFINE_SORT_VARIANTS(data_compare_string);
@@ -716,7 +660,7 @@ static bucket_compare_func_t php_get_key_compare_func(zend_long sort_type)
716660

717661
case PHP_SORT_REGULAR:
718662
default:
719-
return php_array_key_compare;
663+
return php_array_key_compare_regular;
720664
}
721665
return NULL;
722666
}
@@ -746,7 +690,7 @@ static bucket_compare_func_t php_get_key_reverse_compare_func(zend_long sort_typ
746690

747691
case PHP_SORT_REGULAR:
748692
default:
749-
return php_array_reverse_key_compare;
693+
return php_array_reverse_key_compare_regular;
750694
}
751695
return NULL;
752696
}
@@ -776,7 +720,7 @@ static bucket_compare_func_t php_get_data_compare_func(zend_long sort_type) /* {
776720

777721
case PHP_SORT_REGULAR:
778722
default:
779-
return php_array_data_compare;
723+
return php_array_data_compare_regular;
780724
}
781725
return NULL;
782726
}
@@ -806,7 +750,7 @@ static bucket_compare_func_t php_get_data_reverse_compare_func(zend_long sort_ty
806750

807751
case PHP_SORT_REGULAR:
808752
default:
809-
return php_array_reverse_data_compare;
753+
return php_array_reverse_data_compare_regular;
810754
}
811755
return NULL;
812756
}
@@ -865,29 +809,16 @@ static bucket_compare_func_t php_get_data_compare_func_unstable(zend_long sort_t
865809
case PHP_SORT_REGULAR:
866810
default:
867811
if (reverse) {
868-
return php_array_reverse_data_compare_unstable;
812+
return php_array_reverse_data_compare_regular_unstable;
869813
} else {
870-
return php_array_data_compare_unstable;
814+
return php_array_data_compare_regular_unstable;
871815
}
872816
break;
873817
}
874818
return NULL;
875819
}
876820
/* }}} */
877821

878-
static void php_array_sort_regular(HashTable *array, bool sort_keys, bool reverse, bool renumber)
879-
{
880-
bucket_compare_func_t cmp;
881-
882-
if (sort_keys) {
883-
cmp = reverse ? php_array_reverse_key_compare_regular : php_array_key_compare_regular;
884-
} else {
885-
cmp = reverse ? php_array_reverse_data_compare_regular : php_array_data_compare_regular;
886-
}
887-
888-
zend_array_sort(array, cmp, renumber);
889-
}
890-
891822
PHPAPI zend_long php_count_recursive(HashTable *ht) /* {{{ */
892823
{
893824
zend_long cnt = 0;
@@ -1031,11 +962,6 @@ PHP_FUNCTION(asort)
1031962
Z_PARAM_LONG(sort_type)
1032963
ZEND_PARSE_PARAMETERS_END();
1033964

1034-
if ((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR) {
1035-
php_array_sort_regular(array, false, false, false);
1036-
RETURN_TRUE;
1037-
}
1038-
1039965
php_array_apply_sort(array, sort_type, php_get_data_compare_func, false);
1040966
RETURN_TRUE;
1041967
}
@@ -1053,11 +979,6 @@ PHP_FUNCTION(arsort)
1053979
Z_PARAM_LONG(sort_type)
1054980
ZEND_PARSE_PARAMETERS_END();
1055981

1056-
if ((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR) {
1057-
php_array_sort_regular(array, false, true, false);
1058-
RETURN_TRUE;
1059-
}
1060-
1061982
php_array_apply_sort(array, sort_type, php_get_data_reverse_compare_func, false);
1062983
RETURN_TRUE;
1063984
}
@@ -1075,11 +996,6 @@ PHP_FUNCTION(sort)
1075996
Z_PARAM_LONG(sort_type)
1076997
ZEND_PARSE_PARAMETERS_END();
1077998

1078-
if ((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR) {
1079-
php_array_sort_regular(array, false, false, true);
1080-
RETURN_TRUE;
1081-
}
1082-
1083999
php_array_apply_sort(array, sort_type, php_get_data_compare_func, true);
10841000
RETURN_TRUE;
10851001
}
@@ -1097,11 +1013,6 @@ PHP_FUNCTION(rsort)
10971013
Z_PARAM_LONG(sort_type)
10981014
ZEND_PARSE_PARAMETERS_END();
10991015

1100-
if ((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR) {
1101-
php_array_sort_regular(array, false, true, true);
1102-
RETURN_TRUE;
1103-
}
1104-
11051016
php_array_apply_sort(array, sort_type, php_get_data_reverse_compare_func, true);
11061017
RETURN_TRUE;
11071018
}
@@ -1119,11 +1030,6 @@ PHP_FUNCTION(krsort)
11191030
Z_PARAM_LONG(sort_type)
11201031
ZEND_PARSE_PARAMETERS_END();
11211032

1122-
if ((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR) {
1123-
php_array_sort_regular(array, true, true, false);
1124-
RETURN_TRUE;
1125-
}
1126-
11271033
php_array_apply_sort(array, sort_type, php_get_key_reverse_compare_func, false);
11281034
RETURN_TRUE;
11291035
}
@@ -1141,11 +1047,6 @@ PHP_FUNCTION(ksort)
11411047
Z_PARAM_LONG(sort_type)
11421048
ZEND_PARSE_PARAMETERS_END();
11431049

1144-
if ((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR) {
1145-
php_array_sort_regular(array, true, false, false);
1146-
RETURN_TRUE;
1147-
}
1148-
11491050
php_array_apply_sort(array, sort_type, php_get_key_compare_func, false);
11501051
RETURN_TRUE;
11511052
}
@@ -5307,11 +5208,7 @@ PHP_FUNCTION(array_unique)
53075208
return;
53085209
}
53095210

5310-
if (UNEXPECTED((sort_type & ~PHP_SORT_FLAG_CASE) == PHP_SORT_REGULAR)) {
5311-
cmp = php_array_data_compare_regular_unstable;
5312-
} else {
5313-
cmp = php_get_data_compare_func_unstable(sort_type, false);
5314-
}
5211+
cmp = php_get_data_compare_func_unstable(sort_type, false);
53155212

53165213
bool in_place = zend_may_modify_arg_in_place(array);
53175214
if (in_place) {

0 commit comments

Comments
 (0)