Skip to content

Commit eea5ed2

Browse files
committed
re-implementation and refactoring
1 parent 1560a1b commit eea5ed2

316 files changed

Lines changed: 46295 additions & 32618 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

‎ext/date/php_date.c‎

Lines changed: 163 additions & 179 deletions
Large diffs are not rendered by default.

‎ext/random/php_random.h‎

Lines changed: 13 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,19 @@ static inline zend_long GENERATE_SEED(void)
140140
return (zend_long)php_random_generate_fallback_seed();
141141
}
142142

143+
static zend_always_inline uint64_t php_random_splitmix64_mix(uint64_t z)
144+
{
145+
z = (z ^ (z >> 30)) * UINT64_C(0xbf58476d1ce4e5b9);
146+
z = (z ^ (z >> 27)) * UINT64_C(0x94d049bb133111eb);
147+
148+
return z ^ (z >> 31);
149+
}
150+
151+
static zend_always_inline uint64_t php_random_splitmix64(uint64_t *seed)
152+
{
153+
return php_random_splitmix64_mix(*seed += UINT64_C(0x9e3779b97f4a7c15));
154+
}
155+
143156
PHPAPI void *php_random_status_alloc(const php_random_algo *algo, const bool persistent);
144157
PHPAPI void *php_random_status_copy(const php_random_algo *algo, void *old_status, void *new_status);
145158
PHPAPI void php_random_status_free(void *status, const bool persistent);
@@ -160,17 +173,6 @@ static inline php_random_algo_with_state php_random_default_engine(void)
160173
return raws;
161174
}
162175

163-
static inline uint64_t php_random_splitmix64(uint64_t *seed)
164-
{
165-
uint64_t r;
166-
167-
r = (*seed += 0x9e3779b97f4a7c15ULL);
168-
r = (r ^ (r >> 30)) * 0xbf58476d1ce4e5b9ULL;
169-
r = (r ^ (r >> 27)) * 0x94d049bb133111ebULL;
170-
171-
return (r ^ (r >> 31));
172-
}
173-
174176
PHPAPI zend_string *php_random_bin2hex_le(const void *ptr, const size_t len);
175177
PHPAPI bool php_random_hex2bin_le(zend_string *hexstr, void *dest);
176178

‎ext/spl/spl_array.c‎

Lines changed: 45 additions & 35 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,8 @@
1818

1919
#include "php.h"
2020
#include "ext/standard/php_var.h"
21-
21+
#include "zend_attributes.h"
22+
#include "ext/user_cache/php_user_cache.h" /* For user_cache safe direct path */
2223
#include "zend_smart_str.h"
2324
#include "zend_interfaces.h"
2425
#include "zend_exceptions.h"
@@ -29,8 +30,6 @@
2930
#include "spl_exceptions.h"
3031
#include "spl_functions.h" /* For spl_set_private_debug_info_property() */
3132

32-
#include "ext/user_cache/php_user_cache.h" /* For user_cache safe direct path */
33-
3433
/* Defined later in the file */
3534
PHPAPI zend_class_entry *spl_ce_ArrayIterator;
3635
PHPAPI zend_class_entry *spl_ce_RecursiveArrayIterator;
@@ -63,6 +62,12 @@ static inline HashTable **spl_array_get_hash_table_ptr(spl_array_object* intern)
6362
if (intern->ar_flags & SPL_ARRAY_IS_SELF) {
6463
/* rebuild properties */
6564
zend_std_get_properties_ex(&intern->std);
65+
if (GC_REFCOUNT(intern->std.properties) > 1) {
66+
if (EXPECTED(!(GC_FLAGS(intern->std.properties) & IS_ARRAY_IMMUTABLE))) {
67+
GC_DELREF(intern->std.properties);
68+
}
69+
intern->std.properties = zend_array_dup(intern->std.properties);
70+
}
6671
return &intern->std.properties;
6772
} else if (intern->ar_flags & SPL_ARRAY_USE_OTHER) {
6873
spl_array_object *other = Z_SPLARRAY_P(&intern->array);
@@ -1406,8 +1411,6 @@ PHP_METHOD(ArrayObject, unserialize)
14061411

14071412
} /* }}} */
14081413

1409-
/* Builds the state array shared by __serialize() and the user-cache safe-direct
1410-
* path. The members slot only exists in the __serialize() format. */
14111414
static void spl_array_object_serialize_state(zval *object, zval *return_value, bool with_members)
14121415
{
14131416
spl_array_object *intern = Z_SPLARRAY_P(object);
@@ -1449,8 +1452,6 @@ static void spl_array_object_serialize_state(zval *object, zval *return_value, b
14491452
zend_hash_next_index_insert(Z_ARRVAL_P(return_value), &tmp);
14501453
}
14511454

1452-
/* Restores the state array built above. Throws and returns false on malformed
1453-
* data; the caller decides how to propagate the failure. */
14541455
static PHP_UCACHE_HOT bool spl_array_object_unserialize_state(zval *object, HashTable *data, bool with_members)
14551456
{
14561457
spl_array_object *intern = Z_SPLARRAY_P(object);
@@ -1551,11 +1552,11 @@ PHP_METHOD(ArrayObject, __unserialize)
15511552
}
15521553
/* }}} */
15531554

1554-
static bool spl_array_object_copy_user_cache_state(
1555+
static bool spl_array_object_copy_ucache_state(
15551556
void *ctx,
15561557
zend_object *new_obj,
15571558
zend_object *old_obj,
1558-
php_ucache_safe_direct_clone_value_func_t clone_value)
1559+
php_ucache_safe_direct_clone_val_func_t clone_value)
15591560
{
15601561
spl_array_object *old_intern, *new_intern;
15611562
zval new_zv, cloned_storage_zv;
@@ -1579,57 +1580,66 @@ static bool spl_array_object_copy_user_cache_state(
15791580

15801581
result = true;
15811582

1582-
goto bailout;
1583+
goto cleanup;
15831584
}
15841585

15851586
if (!clone_value(ctx, &cloned_storage_zv, &old_intern->array) ||
15861587
(Z_TYPE(cloned_storage_zv) != IS_OBJECT && Z_TYPE(cloned_storage_zv) != IS_ARRAY)
15871588
) {
1588-
goto bailout;
1589+
goto cleanup;
15891590
}
15901591

15911592
spl_array_set_array(&new_zv, new_intern, &cloned_storage_zv, old_intern->ar_flags & SPL_ARRAY_CLONE_MASK, true);
15921593
result = !EG(exception);
15931594

1594-
bailout:
1595-
zval_ptr_dtor(&cloned_storage_zv);
1595+
cleanup:
1596+
if (Z_TYPE(cloned_storage_zv) != IS_UNDEF) {
1597+
zval_ptr_dtor(&cloned_storage_zv);
1598+
}
15961599

15971600
return result;
15981601
}
15991602

1600-
static bool spl_array_object_user_cache_state_has_unstorable(
1601-
void *ctx,
1602-
const zval *object,
1603-
php_ucache_safe_direct_value_has_unstorable_func_t value_has_unstorable)
1603+
static bool spl_array_object_serialize_ucache_state(zval *state, const zval *object)
16041604
{
1605-
spl_array_object *intern = Z_SPLARRAY_P(object);
1605+
zval *storage;
1606+
1607+
ZVAL_UNDEF(state);
1608+
1609+
spl_array_object_serialize_state((zval *) object, state, /* with_members */ false);
1610+
1611+
if (EG(exception) || Z_TYPE_P(state) != IS_ARRAY) {
1612+
if (Z_TYPE_P(state) != IS_UNDEF) {
1613+
zval_ptr_dtor(state);
1614+
}
1615+
1616+
ZVAL_UNDEF(state);
16061617

1607-
if (intern->ar_flags & SPL_ARRAY_IS_SELF) {
16081618
return false;
16091619
}
16101620

1611-
return value_has_unstorable(ctx, &intern->array);
1612-
}
1613-
1614-
static bool spl_array_object_serialize_user_cache_state(zval *state, const zval *object)
1615-
{
1616-
spl_array_object_serialize_state((zval *) object, state, /* with_members */ false);
1621+
storage = zend_hash_index_find(Z_ARRVAL_P(state), 1);
1622+
if (storage != NULL && Z_TYPE_P(storage) == IS_ARRAY) {
1623+
SEPARATE_ARRAY(storage);
1624+
}
16171625

16181626
return true;
16191627
}
16201628

1621-
static PHP_UCACHE_HOT bool spl_array_object_unserialize_user_cache_state(zval *object, zval *state)
1629+
static PHP_UCACHE_HOT bool spl_array_object_unserialize_ucache_state(zval *object, zval *state)
16221630
{
1631+
if (Z_TYPE_P(state) != IS_ARRAY) {
1632+
return false;
1633+
}
1634+
16231635
return spl_array_object_unserialize_state(object, Z_ARRVAL_P(state), /* with_members */ false)
1624-
&& !EG(exception)
1625-
;
1636+
&& !EG(exception);
16261637
}
16271638

1628-
static const php_ucache_safe_direct_handlers_t spl_array_user_cache_handlers = {
1629-
.copy = spl_array_object_copy_user_cache_state,
1630-
.state_has_unstorable = spl_array_object_user_cache_state_has_unstorable,
1631-
.state_serialize = spl_array_object_serialize_user_cache_state,
1632-
.state_unserialize = spl_array_object_unserialize_user_cache_state,
1639+
static const php_ucache_safe_direct_handlers spl_array_ucache_handlers = {
1640+
.copy = spl_array_object_copy_ucache_state,
1641+
.state_serialize = spl_array_object_serialize_ucache_state,
1642+
.state_unserialize = spl_array_object_unserialize_ucache_state,
16331643
};
16341644

16351645
/* {{{ */
@@ -2011,8 +2021,8 @@ PHP_MINIT_FUNCTION(spl_array)
20112021
spl_ce_RecursiveArrayIterator->create_object = spl_array_object_new;
20122022
spl_ce_RecursiveArrayIterator->get_iterator = spl_array_get_iterator;
20132023

2014-
php_ucache_safe_direct_register_class(spl_ce_ArrayObject, &spl_array_user_cache_handlers);
2015-
php_ucache_safe_direct_register_class(spl_ce_ArrayIterator, &spl_array_user_cache_handlers);
2024+
php_ucache_safe_direct_register_class(spl_ce_ArrayObject, &spl_array_ucache_handlers);
2025+
php_ucache_safe_direct_register_class(spl_ce_ArrayIterator, &spl_array_ucache_handlers);
20162026

20172027
return SUCCESS;
20182028
}

‎ext/spl/spl_dllist.c‎

Lines changed: 22 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@
1717
#endif
1818

1919
#include "php.h"
20-
20+
#include "ext/user_cache/php_user_cache.h" /* For user_cache safe direct path */
2121
#include "zend_interfaces.h"
2222
#include "zend_exceptions.h"
2323
#include "zend_hash.h"
@@ -29,8 +29,6 @@
2929
#include "spl_exceptions.h"
3030
#include "spl_functions.h" /* For spl_set_private_debug_info_property() */
3131

32-
#include "ext/user_cache/php_user_cache.h" /* For user_cache safe direct path */
33-
3432
static zend_object_handlers spl_handler_SplDoublyLinkedList;
3533
PHPAPI zend_class_entry *spl_ce_SplDoublyLinkedList;
3634
PHPAPI zend_class_entry *spl_ce_SplQueue;
@@ -1048,8 +1046,6 @@ PHP_METHOD(SplDoublyLinkedList, unserialize)
10481046

10491047
} /* }}} */
10501048

1051-
/* Builds the state array shared by __serialize() and the user-cache safe-direct
1052-
* path. The members slot only exists in the __serialize() format. */
10531049
static void spl_dllist_object_serialize_state(zval *object, zval *return_value, bool with_members)
10541050
{
10551051
spl_dllist_object *intern = Z_SPLDLLIST_P(object);
@@ -1123,24 +1119,27 @@ PHP_METHOD(SplDoublyLinkedList, __unserialize) {
11231119
object_properties_load(&intern->std, Z_ARRVAL_P(members_zv));
11241120
} /* }}} */
11251121

1126-
static bool spl_dllist_object_copy_user_cache_state(
1122+
static bool spl_dllist_object_copy_ucache_state(
11271123
void *ctx,
11281124
zend_object *new_obj,
11291125
zend_object *old_obj,
1130-
php_ucache_safe_direct_clone_value_func_t clone_value)
1126+
php_ucache_safe_direct_clone_val_func_t clone_value)
11311127
{
11321128
spl_dllist_object *old_intern, *new_intern;
11331129
spl_ptr_llist_element *current;
11341130
zval cloned_elem;
11351131

11361132
old_intern = spl_dllist_from_obj(old_obj);
11371133
new_intern = spl_dllist_from_obj(new_obj);
1138-
1139-
ZEND_ASSERT(new_intern->llist->count == 0);
1134+
if (new_intern->llist->count != 0) {
1135+
return false;
1136+
}
11401137

11411138
new_intern->flags = old_intern->flags;
11421139
current = old_intern->llist->head;
11431140
while (current) {
1141+
ZVAL_UNDEF(&cloned_elem);
1142+
11441143
if (!clone_value(ctx, &cloned_elem, &current->data)) {
11451144
return false;
11461145
}
@@ -1155,42 +1154,23 @@ static bool spl_dllist_object_copy_user_cache_state(
11551154
return !EG(exception);
11561155
}
11571156

1158-
static bool spl_dllist_object_user_cache_state_has_unstorable(
1159-
void *ctx,
1160-
const zval *object,
1161-
php_ucache_safe_direct_value_has_unstorable_func_t value_has_unstorable)
1162-
{
1163-
spl_dllist_object *intern;
1164-
spl_ptr_llist_element *current;
1165-
1166-
intern = Z_SPLDLLIST_P((zval *) object);
1167-
current = intern->llist->head;
1168-
while (current) {
1169-
if (value_has_unstorable(ctx, &current->data)) {
1170-
return true;
1171-
}
1172-
1173-
current = current->next;
1174-
}
1175-
1176-
return false;
1177-
}
1178-
1179-
static bool spl_dllist_object_serialize_user_cache_state(zval *state, const zval *object)
1157+
static bool spl_dllist_object_serialize_ucache_state(zval *state, const zval *object)
11801158
{
11811159
spl_dllist_object_serialize_state((zval *) object, state, /* with_members */ false);
11821160

11831161
return true;
11841162
}
11851163

1186-
/* Strict restore for the machine-written user-cache state: validates the flags
1187-
* value. Returns false on malformed data. */
1188-
static bool spl_dllist_object_unserialize_user_cache_state(zval *object, zval *state)
1164+
static bool spl_dllist_object_unserialize_ucache_state(zval *object, zval *state)
11891165
{
11901166
spl_dllist_object *intern = Z_SPLDLLIST_P(object);
11911167
zend_long flags;
11921168
zval *flags_zv, *storage_zv, *elem;
11931169

1170+
if (Z_TYPE_P(state) != IS_ARRAY) {
1171+
return false;
1172+
}
1173+
11941174
flags_zv = zend_hash_index_find(Z_ARRVAL_P(state), 0);
11951175
storage_zv = zend_hash_index_find(Z_ARRVAL_P(state), 1);
11961176
if (!flags_zv ||
@@ -1206,7 +1186,9 @@ static bool spl_dllist_object_unserialize_user_cache_state(zval *object, zval *s
12061186
return false;
12071187
}
12081188

1209-
ZEND_ASSERT(intern->llist->count == 0);
1189+
if (intern->llist->count != 0) {
1190+
return false;
1191+
}
12101192

12111193
intern->flags = (int) flags;
12121194

@@ -1217,11 +1199,10 @@ static bool spl_dllist_object_unserialize_user_cache_state(zval *object, zval *s
12171199
return !EG(exception);
12181200
}
12191201

1220-
static const php_ucache_safe_direct_handlers_t spl_dllist_user_cache_handlers = {
1221-
.copy = spl_dllist_object_copy_user_cache_state,
1222-
.state_has_unstorable = spl_dllist_object_user_cache_state_has_unstorable,
1223-
.state_serialize = spl_dllist_object_serialize_user_cache_state,
1224-
.state_unserialize = spl_dllist_object_unserialize_user_cache_state,
1202+
static const php_ucache_safe_direct_handlers spl_dllist_ucache_handlers = {
1203+
.copy = spl_dllist_object_copy_ucache_state,
1204+
.state_serialize = spl_dllist_object_serialize_ucache_state,
1205+
.state_unserialize = spl_dllist_object_unserialize_ucache_state,
12251206
};
12261207

12271208
/* {{{ Inserts a new entry before the specified $index consisting of $newval. */
@@ -1342,7 +1323,7 @@ PHP_MINIT_FUNCTION(spl_dllist) /* {{{ */
13421323
spl_ce_SplStack->create_object = spl_dllist_object_new;
13431324
spl_ce_SplStack->get_iterator = spl_dllist_get_iterator;
13441325

1345-
php_ucache_safe_direct_register_class(spl_ce_SplDoublyLinkedList, &spl_dllist_user_cache_handlers);
1326+
php_ucache_safe_direct_register_class(spl_ce_SplDoublyLinkedList, &spl_dllist_ucache_handlers);
13461327

13471328
return SUCCESS;
13481329
}

0 commit comments

Comments
 (0)