andrei          Mon Sep  9 16:05:23 2002 EDT

  Modified files:              
    /php4/ext/standard  array.c 
  Log:
  @- Added ability to extract() variables as references via OR'able EXTR_REFS
  @  flag. (Andrei)
  
  
Index: php4/ext/standard/array.c
diff -u php4/ext/standard/array.c:1.184 php4/ext/standard/array.c:1.185
--- php4/ext/standard/array.c:1.184     Fri Aug 23 21:19:27 2002
+++ php4/ext/standard/array.c   Mon Sep  9 16:05:20 2002
@@ -21,7 +21,7 @@
    +----------------------------------------------------------------------+
 */
 
-/* $Id: array.c,v 1.184 2002/08/24 01:19:27 helly Exp $ */
+/* $Id: array.c,v 1.185 2002/09/09 20:05:20 andrei Exp $ */
 
 #include "php.h"
 #include "php_ini.h"
@@ -60,6 +60,8 @@
 #define        EXTR_PREFIX_IF_EXISTS   5
 #define        EXTR_IF_EXISTS                  6
 
+#define EXTR_REFS                              0x100
+
 #define SORT_REGULAR                   0
 #define SORT_NUMERIC                   1
 #define        SORT_STRING                             2
@@ -86,6 +88,7 @@
        REGISTER_LONG_CONSTANT("EXTR_PREFIX_INVALID", EXTR_PREFIX_INVALID, CONST_CS | 
CONST_PERSISTENT);
        REGISTER_LONG_CONSTANT("EXTR_PREFIX_IF_EXISTS", EXTR_PREFIX_IF_EXISTS, 
CONST_CS | CONST_PERSISTENT);
        REGISTER_LONG_CONSTANT("EXTR_IF_EXISTS", EXTR_IF_EXISTS, CONST_CS | 
CONST_PERSISTENT);
+       REGISTER_LONG_CONSTANT("EXTR_REFS", EXTR_REFS, CONST_CS | CONST_PERSISTENT);
        
        REGISTER_LONG_CONSTANT("SORT_ASC", SORT_ASC, CONST_CS | CONST_PERSISTENT);
        REGISTER_LONG_CONSTANT("SORT_DESC", SORT_DESC, CONST_CS | CONST_PERSISTENT);
@@ -1139,6 +1142,7 @@
        ulong num_key;
        uint var_name_len;
        int var_exists, extract_type, key_type, count = 0;
+       zend_bool extract_refs = 0;
        HashPosition pos;
 
        switch (ZEND_NUM_ARGS()) {
@@ -1155,6 +1159,8 @@
                        }
                        convert_to_long_ex(z_extract_type);
                        extract_type = Z_LVAL_PP(z_extract_type);
+                       extract_refs = (extract_type & EXTR_REFS)>>8;
+                       extract_type &= 0xff;
                        if (extract_type > EXTR_SKIP && extract_type <= 
EXTR_PREFIX_IF_EXISTS) {
                                php_error_docref(NULL TSRMLS_CC, E_WARNING, "Prefix 
expected to be specified");
                                return;
@@ -1167,6 +1173,8 @@
                        }
                        convert_to_long_ex(z_extract_type);
                        extract_type = Z_LVAL_PP(z_extract_type);
+                       extract_refs = (extract_type & EXTR_REFS)>>8;
+                       extract_type &= 0xff;
                        convert_to_string_ex(prefix);
                        break;
 
@@ -1252,11 +1260,28 @@
                if (final_name.len) {
                        smart_str_0(&final_name);
                        if (php_valid_var_name(final_name.c)) {
-                               MAKE_STD_ZVAL(data);
-                               *data = **entry;
-                               zval_copy_ctor(data);
+                               if (extract_refs) {
+                                       zval **orig_var;
+
+                                       (*entry)->is_ref = 1;
+                                       (*entry)->refcount++;
+                                       if (zend_hash_find(EG(active_symbol_table), 
+final_name.c, final_name.len+1, (void **) &orig_var)==SUCCESS
+                                               && PZVAL_IS_REF(*orig_var)) {
+
+                                               (*entry)->refcount += 
+(*orig_var)->refcount-2;
+                                               zval_dtor(*orig_var);
+                                               FREE_ZVAL(*orig_var);
+                                               *orig_var = *entry;
+                                       } else {
+                                               
+zend_hash_update(EG(active_symbol_table), final_name.c, final_name.len+1, entry, 
+sizeof(zval *), NULL);
+                                       }
+                               } else {
+                                       MAKE_STD_ZVAL(data);
+                                       *data = **entry;
+                                       zval_copy_ctor(data);
 
-                               ZEND_SET_SYMBOL(EG(active_symbol_table), final_name.c, 
data);
+                                       ZEND_SET_SYMBOL(EG(active_symbol_table), 
+final_name.c, data);
+                               }
 
                                count++;
                        }



-- 
PHP CVS Mailing List (http://www.php.net/)
To unsubscribe, visit: http://www.php.net/unsub.php

Reply via email to