Skip to content

Commit 9cd0591

Browse files
committed
Refactor RedisArray
Change type of returning value from `char *` to `zend_string *` for `ra_extract_key` and `ra_call_extractor` functions. Store keys as `zend_string *` in RedisArray::mset.
1 parent 2828c2f commit 9cd0591

File tree

2 files changed

+40
-46
lines changed

2 files changed

+40
-46
lines changed

redis_array.c

Lines changed: 7 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1059,9 +1059,9 @@ PHP_METHOD(RedisArray, mset)
10591059
RedisArray *ra;
10601060
int *pos, argc, *argc_each;
10611061
HashTable *h_keys;
1062-
char *key, **keys, kbuf[40];
1063-
int key_len, *key_lens;
1064-
zend_string *zkey;
1062+
char *key, kbuf[40];
1063+
int key_len;
1064+
zend_string **keys, *zkey;
10651065
ulong idx;
10661066

10671067
if ((ra = redis_array_get(getThis() TSRMLS_CC)) == NULL) {
@@ -1084,8 +1084,7 @@ PHP_METHOD(RedisArray, mset)
10841084
}
10851085
argv = emalloc(argc * sizeof(zval*));
10861086
pos = emalloc(argc * sizeof(int));
1087-
keys = emalloc(argc * sizeof(char*));
1088-
key_lens = emalloc(argc * sizeof(int));
1087+
keys = ecalloc(argc, sizeof(zend_string *));
10891088

10901089
argc_each = emalloc(ra->count * sizeof(int));
10911090
memset(argc_each, 0, ra->count * sizeof(int));
@@ -1106,8 +1105,7 @@ PHP_METHOD(RedisArray, mset)
11061105
}
11071106

11081107
argc_each[pos[i]]++; /* count number of keys per node */
1109-
keys[i] = estrndup(key, key_len);
1110-
key_lens[i] = (int)key_len;
1108+
keys[i] = zend_string_init(key, key_len, 0);
11111109
argv[i] = data;
11121110
i++;
11131111
} ZEND_HASH_FOREACH_END();
@@ -1134,7 +1132,7 @@ PHP_METHOD(RedisArray, mset)
11341132
} else {
11351133
ZVAL_ZVAL(z_tmp, argv[i], 1, 0);
11361134
}
1137-
add_assoc_zval_ex(&z_argarray, keys[i], key_lens[i], z_tmp);
1135+
add_assoc_zval_ex(&z_argarray, ZSTR_VAL(keys[i]), ZSTR_LEN(keys[i]), z_tmp);
11381136
found++;
11391137
}
11401138

@@ -1167,12 +1165,11 @@ PHP_METHOD(RedisArray, mset)
11671165

11681166
/* Free any keys that we needed to allocate memory for, because they weren't strings */
11691167
for(i = 0; i < argc; i++) {
1170-
efree(keys[i]);
1168+
zend_string_release(keys[i]);
11711169
}
11721170

11731171
/* cleanup */
11741172
efree(keys);
1175-
efree(key_lens);
11761173
efree(argv);
11771174
efree(pos);
11781175
efree(argc_each);

redis_array_impl.c

Lines changed: 33 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -378,10 +378,10 @@ ra_make_array(HashTable *hosts, zval *z_fun, zval *z_dist, HashTable *hosts_prev
378378

379379

380380
/* call userland key extraction function */
381-
char *
382-
ra_call_extractor(RedisArray *ra, const char *key, int key_len, int *out_len TSRMLS_DC)
381+
zend_string *
382+
ra_call_extractor(RedisArray *ra, const char *key, int key_len TSRMLS_DC)
383383
{
384-
char *out = NULL;
384+
zend_string *out = NULL;
385385
zval z_ret, z_argv;
386386

387387
/* check that we can call the extractor function */
@@ -400,29 +400,30 @@ ra_call_extractor(RedisArray *ra, const char *key, int key_len, int *out_len TSR
400400
call_user_function(EG(function_table), NULL, &ra->z_fun, &z_ret, 1, &z_argv);
401401

402402
if (Z_TYPE(z_ret) == IS_STRING) {
403-
*out_len = Z_STRLEN(z_ret);
404-
out = estrndup(Z_STRVAL(z_ret), *out_len);
403+
#if (PHP_MAJOR_VERSION < 7)
404+
out = zend_string_init(Z_STRVAL(z_ret), Z_STRLEN(z_ret), 0);
405+
#else
406+
out = zval_get_string(&z_ret);
407+
#endif
405408
}
406409

407410
zval_dtor(&z_argv);
408411
zval_dtor(&z_ret);
409412
return out;
410413
}
411414

412-
static char *
413-
ra_extract_key(RedisArray *ra, const char *key, int key_len, int *out_len TSRMLS_DC) {
414-
415+
static zend_string *
416+
ra_extract_key(RedisArray *ra, const char *key, int key_len TSRMLS_DC)
417+
{
415418
char *start, *end;
416-
*out_len = key_len;
417419

418420
if (Z_TYPE(ra->z_fun) != IS_NULL) {
419-
return ra_call_extractor(ra, key, key_len, out_len TSRMLS_CC);
421+
return ra_call_extractor(ra, key, key_len TSRMLS_CC);
420422
} else if ((start = strchr(key, '{')) == NULL || (end = strchr(start + 1, '}')) == NULL) {
421-
return estrndup(key, key_len);
423+
return zend_string_init(key, key_len, 0);
422424
}
423425
/* found substring */
424-
*out_len = end - start - 1;
425-
return estrndup(start + 1, *out_len);
426+
return zend_string_init(start + 1, end - start - 1, 0);
426427
}
427428

428429
/* call userland key distributor function */
@@ -455,39 +456,35 @@ ra_call_distributor(RedisArray *ra, const char *key, int key_len TSRMLS_DC)
455456
}
456457

457458
zval *
458-
ra_find_node(RedisArray *ra, const char *key, int key_len, int *out_pos TSRMLS_DC) {
459-
uint32_t hash;
460-
char *out;
461-
int pos, out_len;
459+
ra_find_node(RedisArray *ra, const char *key, int key_len, int *out_pos TSRMLS_DC)
460+
{
461+
int pos;
462+
zend_string *out;
462463

463464
/* extract relevant part of the key */
464-
out = ra_extract_key(ra, key, key_len, &out_len TSRMLS_CC);
465-
if(!out) return NULL;
465+
if ((out = ra_extract_key(ra, key, key_len TSRMLS_CC)) == NULL) {
466+
return NULL;
467+
}
466468

467-
if (Z_TYPE(ra->z_dist) != IS_NULL) {
468-
pos = ra_call_distributor(ra, key, key_len TSRMLS_CC);
469-
if (pos < 0 || pos >= ra->count) {
470-
efree(out);
471-
return NULL;
472-
}
473-
} else {
474-
uint64_t h64;
469+
if (Z_TYPE(ra->z_dist) == IS_NULL) {
470+
int i;
475471
unsigned long ret = 0xffffffff;
476-
size_t i;
477472

478473
/* hash */
479-
for (i = 0; i < out_len; ++i) {
480-
CRC32(ret, (unsigned char)out[i]);
474+
for (i = 0; i < ZSTR_LEN(out); ++i) {
475+
CRC32(ret, ZSTR_VAL(out)[i]);
481476
}
482-
hash = (ret ^ 0xffffffff);
483477

484478
/* get position on ring */
485-
h64 = hash;
486-
h64 *= ra->count;
487-
h64 /= 0xffffffff;
488-
pos = (int)h64;
479+
pos = (int)((ret ^ 0xffffffff) * ra->count / 0xffffffff);
480+
} else {
481+
pos = ra_call_distributor(ra, key, key_len TSRMLS_CC);
482+
if (pos < 0 || pos >= ra->count) {
483+
zend_string_release(out);
484+
return NULL;
485+
}
489486
}
490-
efree(out);
487+
zend_string_release(out);
491488

492489
if(out_pos) *out_pos = pos;
493490

0 commit comments

Comments
 (0)