@@ -208,6 +208,7 @@ int redis_key_str_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
208
208
{
209
209
char * key , * val ;
210
210
size_t key_len , val_len ;
211
+ int key_free ;
211
212
212
213
if (zend_parse_parameters (ZEND_NUM_ARGS () TSRMLS_CC , "ss" , & key , & key_len ,
213
214
& val , & val_len )== FAILURE )
@@ -216,7 +217,7 @@ int redis_key_str_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
216
217
}
217
218
218
219
// Prefix key
219
- redis_key_prefix (redis_sock , & key , & key_len );
220
+ key_free = redis_key_prefix (redis_sock , & key , & key_len );
220
221
221
222
// Construct command
222
223
* cmd_len = redis_cmd_format_static (cmd , kw , "ss" , key , key_len , val ,
@@ -225,6 +226,8 @@ int redis_key_str_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
225
226
// Set slot if directed
226
227
CMD_SET_SLOT (slot ,key ,key_len );
227
228
229
+ if (key_free ) efree (key );
230
+
228
231
return SUCCESS ;
229
232
}
230
233
@@ -301,6 +304,8 @@ int redis_key_key_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
301
304
// Construct our command
302
305
* cmd_len = redis_cmd_format_static (cmd , kw , "ss" , key1 , key1_len , key2 ,
303
306
key2_len );
307
+ if (key1_free ) efree (key1 );
308
+ if (key2_free ) efree (key2 );
304
309
305
310
return SUCCESS ;
306
311
}
@@ -336,6 +341,8 @@ int redis_key_long_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
336
341
// Set slot if directed
337
342
CMD_SET_SLOT (slot , key , key_len );
338
343
344
+ if (key_free ) efree (key );
345
+
339
346
// Success!
340
347
return SUCCESS ;
341
348
}
@@ -656,19 +663,11 @@ int redis_zinter_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
656
663
{
657
664
char * key ;
658
665
int key_free ;
659
- zval z_tmp ;
660
- ZVAL_UNDEF (& z_tmp );
661
-
662
- if (Z_TYPE_P (z_ele ) == IS_STRING ) {
663
- key = Z_STRVAL_P (z_ele );
664
- key_len = Z_STRLEN_P (z_ele );
665
- } else {
666
- ZVAL_DUP (& z_tmp , z_ele );
667
- convert_to_string (& z_tmp );
666
+ zend_string * key_zstr ;
668
667
669
- key = Z_STRVAL ( z_tmp );
670
- key_len = Z_STRLEN ( z_tmp );
671
- }
668
+ key_zstr = zval_get_string ( z_ele );
669
+ key = ZSTR_VAL ( key_zstr );
670
+ key_len = ZSTR_LEN ( key_zstr );
672
671
673
672
// Prefix key if necissary
674
673
key_free = redis_key_prefix (redis_sock , & key , & key_len );
@@ -679,9 +678,7 @@ int redis_zinter_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
679
678
"All keys don't hash to the same slot!" );
680
679
efree (cmdstr .c );
681
680
if (key_free ) efree (key );
682
- if (Z_TYPE (z_tmp ) != IS_UNDEF ) {
683
- zval_dtor (& z_tmp );
684
- }
681
+ zend_string_release (key_zstr );
685
682
return FAILURE ;
686
683
}
687
684
@@ -690,9 +687,7 @@ int redis_zinter_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
690
687
691
688
// Cleanup
692
689
if (key_free ) efree (key );
693
- if (Z_TYPE (z_tmp ) != IS_UNDEF ) {
694
- zval_dtor (& z_tmp );
695
- }
690
+ zend_string_release (key_zstr );
696
691
}
697
692
698
693
// Weights
@@ -783,7 +778,7 @@ int redis_subscribe_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
783
778
zend_hash_move_forward_ex (ht_chan , & ptr ))
784
779
{
785
780
// We want to deal with strings here
786
- convert_to_string (z_chan );
781
+ zend_string * z_chan_zstr = zval_get_string (z_chan );
787
782
788
783
// Grab channel name, prefix if required
789
784
key = Z_STRVAL_P (z_chan );
@@ -795,6 +790,7 @@ int redis_subscribe_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
795
790
796
791
// Free our key if it was prefixed
797
792
if (key_free ) efree (key );
793
+ zend_string_release (z_chan_zstr );
798
794
}
799
795
800
796
// Push values out
@@ -963,7 +959,8 @@ int redis_key_varval_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
963
959
smart_string cmdstr = {0 };
964
960
char * arg ;
965
961
int arg_free , i , argc = ZEND_NUM_ARGS ();
966
- size_t arg_len ;
962
+ size_t arg_len ;
963
+ zend_string * lval_key_zstr ;
967
964
968
965
// We at least need a key and one value
969
966
if (argc < 2 ) {
@@ -978,9 +975,9 @@ int redis_key_varval_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
978
975
}
979
976
980
977
// Grab the first argument (our key) as a string
981
- convert_to_string (& z_args [0 ]);
982
- arg = Z_STRVAL ( z_args [ 0 ] );
983
- arg_len = Z_STRLEN ( z_args [ 0 ] );
978
+ lval_key_zstr = zval_get_string (& z_args [0 ]);
979
+ arg = ZSTR_VAL ( lval_key_zstr );
980
+ arg_len = ZSTR_LEN ( lval_key_zstr );
984
981
985
982
// Prefix if required
986
983
arg_free = redis_key_prefix (redis_sock , & arg , & arg_len );
@@ -992,6 +989,7 @@ int redis_key_varval_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
992
989
// Set our slot, free key prefix if we prefixed it
993
990
CMD_SET_SLOT (slot ,arg ,arg_len );
994
991
if (arg_free ) efree (arg );
992
+ zend_string_release (lval_key_zstr );
995
993
996
994
// Add our members
997
995
for (i = 1 ;i < argc ;i ++ ) {
@@ -1116,9 +1114,9 @@ static int gen_varkey_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1116
1114
(z_ele = zend_hash_get_current_data (ht_arr )) != NULL ;
1117
1115
zend_hash_move_forward (ht_arr ))
1118
1116
{
1119
- convert_to_string (z_ele );
1120
- key = Z_STRVAL_P ( z_ele );
1121
- key_len = Z_STRLEN_P ( z_ele );
1117
+ zend_string * z_ele_zstr = zval_get_string (z_ele );
1118
+ key = ZSTR_VAL ( z_ele_zstr );
1119
+ key_len = ZSTR_LEN ( z_ele_zstr );
1122
1120
key_free = redis_key_prefix (redis_sock , & key , & key_len );
1123
1121
1124
1122
// Protect against CROSSLOT errors
@@ -1128,13 +1126,15 @@ static int gen_varkey_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1128
1126
} else if (cluster_hash_key (key ,key_len )!= kslot ) {
1129
1127
php_error_docref (NULL TSRMLS_CC , E_WARNING ,
1130
1128
"Not all keys hash to the same slot!" );
1129
+ zend_string_release (z_ele_zstr );
1131
1130
return FAILURE ;
1132
1131
}
1133
1132
}
1134
1133
1135
1134
// Append this key, free it if we prefixed
1136
1135
redis_cmd_append_sstr (& cmdstr , key , key_len );
1137
1136
if (key_free ) efree (key );
1137
+ zend_string_release (z_ele_zstr );
1138
1138
}
1139
1139
if (has_timeout ) {
1140
1140
redis_cmd_append_sstr_long (& cmdstr , timeout );
@@ -1149,9 +1149,9 @@ static int gen_varkey_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1149
1149
1150
1150
tail = has_timeout ? argc - 1 : argc ;
1151
1151
for (i = 0 ;i < tail ;i ++ ) {
1152
- convert_to_string (& z_args [i ]);
1153
- key = Z_STRVAL ( z_args [ i ] );
1154
- key_len = Z_STRLEN ( z_args [ i ] );
1152
+ zend_string * arg = zval_get_string (& z_args [i ]);
1153
+ key = ZSTR_VAL ( arg );
1154
+ key_len = ZSTR_LEN ( arg );
1155
1155
1156
1156
key_free = redis_key_prefix (redis_sock , & key , & key_len );
1157
1157
@@ -1163,13 +1163,16 @@ static int gen_varkey_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1163
1163
php_error_docref (NULL TSRMLS_CC , E_WARNING ,
1164
1164
"Not all keys hash to the same slot" );
1165
1165
efree (z_args );
1166
+ if (key_free ) efree (key );
1167
+ zend_string_release (arg );
1166
1168
return FAILURE ;
1167
1169
}
1168
1170
}
1169
1171
1170
1172
// Append this key
1171
1173
redis_cmd_append_sstr (& cmdstr , key , key_len );
1172
1174
if (key_free ) efree (key );
1175
+ zend_string_release (arg );
1173
1176
}
1174
1177
if (has_timeout ) {
1175
1178
redis_cmd_append_sstr_long (& cmdstr , Z_LVAL (z_args [tail ]));
@@ -1716,11 +1719,11 @@ int redis_bitop_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1716
1719
// Now iterate over our keys argument
1717
1720
for (i = 1 ;i < argc ;i ++ ) {
1718
1721
// Make sure we've got a string
1719
- convert_to_string (& z_args [i ]);
1722
+ zend_string * key_zstr = zval_get_string (& z_args [i ]);
1720
1723
1721
1724
// Grab this key and length
1722
- key = Z_STRVAL ( z_args [ i ] );
1723
- key_len = Z_STRLEN ( z_args [ i ] );
1725
+ key = ZSTR_VAL ( key_zstr );
1726
+ key_len = ZSTR_LEN ( key_zstr );
1724
1727
1725
1728
// Prefix key, append
1726
1729
key_free = redis_key_prefix (redis_sock , & key , & key_len );
@@ -1733,12 +1736,14 @@ int redis_bitop_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1733
1736
php_error_docref (NULL TSRMLS_CC , E_WARNING ,
1734
1737
"Warning, not all keys hash to the same slot!" );
1735
1738
if (key_free ) efree (key );
1739
+ zend_string_release (key_zstr );
1736
1740
return FAILURE ;
1737
1741
}
1738
1742
* slot = kslot ;
1739
1743
}
1740
1744
1741
1745
if (key_free ) efree (key );
1746
+ zend_string_release (key_zstr );
1742
1747
}
1743
1748
1744
1749
// Free our argument array
@@ -1827,18 +1832,13 @@ static int redis_gen_pf_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1827
1832
(z_ele = zend_hash_get_current_data_ex (ht_arr , & pos )) != NULL ;
1828
1833
zend_hash_move_forward_ex (ht_arr , & pos ))
1829
1834
{
1830
- zval z_tmp ;
1831
- ZVAL_UNDEF (& z_tmp );
1835
+ zend_string * zstr = NULL ;
1832
1836
1833
1837
// Prefix keys, serialize values
1834
1838
if (is_keys ) {
1835
- if (Z_TYPE_P (z_ele ) != IS_STRING ) {
1836
- ZVAL_DUP (& z_tmp , z_ele );
1837
- convert_to_string (& z_tmp );
1838
- z_ele = & z_tmp ;
1839
- }
1840
- mem = Z_STRVAL_P (z_ele );
1841
- mem_len = Z_STRLEN_P (z_ele );
1839
+ zstr = zval_get_string (z_ele );
1840
+ mem = ZSTR_VAL (zstr );
1841
+ mem_len = ZSTR_LEN (zstr );
1842
1842
1843
1843
// Key prefix
1844
1844
mem_free = redis_key_prefix (redis_sock , & mem , & mem_len );
@@ -1847,42 +1847,31 @@ static int redis_gen_pf_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
1847
1847
if (slot && * slot != cluster_hash_key (mem , mem_len )) {
1848
1848
php_error_docref (0 TSRMLS_CC , E_WARNING ,
1849
1849
"All keys must hash to the same slot!" );
1850
- if (key_free ) efree (key );
1851
- if (Z_TYPE (z_tmp ) != IS_UNDEF ) {
1852
- zval_dtor (& z_tmp );
1853
- }
1850
+ if (key_free ) efree (key );
1851
+ zend_string_release (zstr );
1854
1852
return FAILURE ;
1855
1853
}
1856
1854
} else {
1857
1855
mem_free = redis_serialize (redis_sock , z_ele , & mem , & mem_len );
1858
1856
1859
1857
if (!mem_free ) {
1860
- if (Z_TYPE_P (z_ele ) != IS_STRING ) {
1861
- ZVAL_DUP (& z_tmp , z_ele );
1862
- convert_to_string (& z_tmp );
1863
- z_ele = & z_tmp ;
1864
- }
1865
- mem = Z_STRVAL_P (z_ele );
1866
- mem_len = Z_STRLEN_P (z_ele );
1858
+ zstr = zval_get_string (z_ele );
1859
+ mem = ZSTR_VAL (zstr );
1860
+ mem_len = ZSTR_LEN (zstr );
1867
1861
}
1868
1862
}
1869
1863
1870
1864
// Append our key or member
1871
1865
redis_cmd_append_sstr (& cmdstr , mem , mem_len );
1872
1866
1873
- // Clean up our temp val if it was used
1874
- if (Z_TYPE (z_tmp ) != IS_UNDEF ) {
1875
- zval_dtor (& z_tmp );
1876
- }
1877
-
1878
1867
// Clean up prefixed or serialized data
1879
1868
1880
1869
if (mem_free ) {
1881
- if (! is_keys ) {
1882
- efree ( mem );
1883
- } else {
1884
- efree ( mem );
1885
- }
1870
+ efree ( mem );
1871
+ }
1872
+ // Clean up temp zend_string (or decrement refcount) if we created one.
1873
+ if ( zstr != NULL ) {
1874
+ zend_string_release ( zstr );
1886
1875
}
1887
1876
}
1888
1877
@@ -2623,10 +2612,11 @@ int redis_zadd_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
2623
2612
{
2624
2613
zval * z_args ;
2625
2614
char * key , * val ;
2626
- size_t key_len , val_len ;
2615
+ size_t key_len , val_len ;
2627
2616
int key_free , val_free ;
2628
2617
int argc = ZEND_NUM_ARGS (), i ;
2629
2618
smart_string cmdstr = {0 };
2619
+ zend_string * zset_key_zstr ;
2630
2620
2631
2621
z_args = (zval * ) safe_emalloc (sizeof (zval ), argc , 0 );
2632
2622
if (zend_get_parameters_array (ht , argc , z_args )== FAILURE ) {
@@ -2635,15 +2625,16 @@ int redis_zadd_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
2635
2625
}
2636
2626
2637
2627
// Need key, score, value, [score, value...] */
2638
- if (argc > 0 ) convert_to_string (& z_args [0 ]);
2639
- if (argc < 3 || Z_TYPE (z_args [0 ])!= IS_STRING || (argc - 1 )%2 != 0 ) {
2628
+ if (argc < 3 || (argc - 1 )%2 != 0 ) {
2640
2629
efree (z_args );
2641
2630
return FAILURE ;
2642
2631
}
2643
2632
2633
+ zset_key_zstr = zval_get_string (& z_args [0 ]);
2634
+
2644
2635
// Prefix our key
2645
- key = Z_STRVAL ( z_args [ 0 ] );
2646
- key_len = Z_STRLEN ( z_args [ 0 ] );
2636
+ key = ZSTR_VAL ( zset_key_zstr );
2637
+ key_len = ZSTR_LEN ( zset_key_zstr );
2647
2638
key_free = redis_key_prefix (redis_sock , & key , & key_len );
2648
2639
2649
2640
// Start command construction
@@ -2653,6 +2644,8 @@ int redis_zadd_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
2653
2644
// Set our slot, free key if we prefixed it
2654
2645
CMD_SET_SLOT (slot ,key ,key_len );
2655
2646
if (key_free ) efree (key );
2647
+ zend_string_release (zset_key_zstr );
2648
+
2656
2649
2657
2650
// Now the rest of our arguments
2658
2651
for (i = 1 ;i < argc ;i += 2 ) {
@@ -3058,8 +3051,9 @@ int redis_command_cmd(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock,
3058
3051
(z_ele = zend_hash_get_current_data (ht_arr )) != NULL ;
3059
3052
zend_hash_move_forward (ht_arr ))
3060
3053
{
3061
- convert_to_string (z_ele );
3062
- redis_cmd_append_sstr (& cmdstr , Z_STRVAL_P (z_ele ), Z_STRLEN_P (z_ele ));
3054
+ zend_string * z_ele_zstr = zval_get_string (z_ele );
3055
+ redis_cmd_append_sstr (& cmdstr , ZSTR_VAL (z_ele_zstr ), ZSTR_LEN (z_ele_zstr ));
3056
+ zend_string_release (z_ele_zstr );
3063
3057
}
3064
3058
3065
3059
* cmd = cmdstr .c ;
@@ -3198,8 +3192,11 @@ void redis_prefix_handler(INTERNAL_FUNCTION_PARAMETERS, RedisSock *redis_sock) {
3198
3192
}
3199
3193
3200
3194
if (redis_sock -> prefix != NULL && redis_sock -> prefix_len > 0 ) {
3201
- redis_key_prefix (redis_sock , & key , & key_len );
3202
- RETURN_STRINGL (key , key_len );
3195
+ // Set the return value to a copy of the prefixed key, then free the original.
3196
+ redis_key_prefix (redis_sock , & key , & key_len );
3197
+ RETVAL_STRINGL (key , key_len );
3198
+ efree (key );
3199
+ return ;
3203
3200
} else {
3204
3201
RETURN_STRINGL (key , key_len );
3205
3202
}
0 commit comments