]> granicus.if.org Git - php/commitdiff
* Support getThis() for internal functions.
authorZeev Suraski <zeev@php.net>
Fri, 28 May 1999 12:06:59 +0000 (12:06 +0000)
committerZeev Suraski <zeev@php.net>
Fri, 28 May 1999 12:06:59 +0000 (12:06 +0000)
* Fix 'new object or die' and AiCount issue thoroughly (earlier fix didn't
  work with the optimizer).
* Add new macros for standardized definition of classes.
* Only report AiCount problems if shutdown was not silent.

Zend/zend.h
Zend/zend_API.c
Zend/zend_API.h
Zend/zend_alloc.c
Zend/zend_compile.c
Zend/zend_compile.h
Zend/zend_execute.c
Zend/zend_execute_API.c

index a0e375e53b4c21ad7303892ee697233789d6ceec..6616c4efcb4b83ebca1d5635432b5d8bec78f93a 100644 (file)
@@ -56,8 +56,8 @@
 #include "zend_llist.h"
 
 
-#define INTERNAL_FUNCTION_PARAMETERS int ht, zval *return_value, HashTable *list, HashTable *plist
-#define INTERNAL_FUNCTION_PARAM_PASSTHRU ht, return_value, list, plist
+#define INTERNAL_FUNCTION_PARAMETERS int ht, zval *return_value, HashTable *list, HashTable *plist, zval *this_ptr
+#define INTERNAL_FUNCTION_PARAM_PASSTHRU ht, return_value, list, plist, this_ptr
 
 /*
  * zval
@@ -121,6 +121,7 @@ struct _zend_class_entry {
 
        HashTable function_table;
        HashTable default_properties;
+       zend_function_entry *builtin_functions;
 
        /* handlers */
        void (*handle_function_call)(INTERNAL_FUNCTION_PARAMETERS, zend_property_reference *property_reference);
index 49ed26dbe95ed688b9205776d80746aab381ffde..492289beda0f9d82a4f9dbc3c32791d976018fdd 100644 (file)
@@ -161,22 +161,6 @@ ZEND_API int getParametersArrayEx(int param_count, zval ***argument_array)
 }
 
 
-ZEND_API int getThis(zval **this_ptr)
-{
-       /* NEEDS TO BE IMPLEMENTED FOR ZEND */
-       /*
-       zval *data;
-
-       if (zend_hash_find(function_state.calling_symbol_table, "this", sizeof("this"), (void **)&data) == FAILURE) {
-               return FAILURE;
-       }
-
-       *this = data;
-       */
-       return SUCCESS;
-}
-
-
 ZEND_API int ParameterPassedByReference(int ht, uint n)
 {
        void **p;
@@ -609,13 +593,17 @@ ZEND_API int _register_list_destructors(void (*list_destructor)(void *), void (*
 
 
 /* registers all functions in *library_functions in the function hash */
-int zend_register_functions(zend_function_entry *functions)
+int zend_register_functions(zend_function_entry *functions, HashTable *function_table)
 {
        zend_function_entry *ptr = functions;
        zend_internal_function internal_function;
        int count=0,unload=0;
+       HashTable *target_function_table = function_table;
        CLS_FETCH();
 
+       if (!target_function_table) {
+               target_function_table = CG(function_table);
+       }
        internal_function.type = ZEND_INTERNAL_FUNCTION;
        
        while (ptr->fname) {
@@ -624,10 +612,10 @@ int zend_register_functions(zend_function_entry *functions)
                internal_function.function_name = ptr->fname;
                if (!internal_function.handler) {
                        zend_error(E_CORE_WARNING,"Null function defined as active function");
-                       zend_unregister_functions(functions,count);
+                       zend_unregister_functions(functions, count, target_function_table);
                        return FAILURE;
                }
-               if (zend_hash_add(CG(function_table), ptr->fname, strlen(ptr->fname)+1, &internal_function, sizeof(zend_internal_function), NULL) == FAILURE) {
+               if (zend_hash_add(target_function_table, ptr->fname, strlen(ptr->fname)+1, &internal_function, sizeof(zend_internal_function), NULL) == FAILURE) {
                        unload=1;
                        break;
                }
@@ -636,12 +624,12 @@ int zend_register_functions(zend_function_entry *functions)
        }
        if (unload) { /* before unloading, display all remaining bad function in the module */
                while (ptr->fname) {
-                       if (zend_hash_exists(CG(function_table), ptr->fname, strlen(ptr->fname)+1)) {
-                               zend_error(E_CORE_WARNING,"Module load failed - duplicate function name - %s",ptr->fname);
+                       if (zend_hash_exists(target_function_table, ptr->fname, strlen(ptr->fname)+1)) {
+                               zend_error(E_CORE_WARNING, "Function registration failed - duplicate name - %s",ptr->fname);
                        }
                        ptr++;
                }
-               zend_unregister_functions(functions,count);
+               zend_unregister_functions(functions, count, target_function_table);
                return FAILURE;
        }
        return SUCCESS;
@@ -650,20 +638,24 @@ int zend_register_functions(zend_function_entry *functions)
 /* count=-1 means erase all functions, otherwise, 
  * erase the first count functions
  */
-void zend_unregister_functions(zend_function_entry *functions,int count)
+void zend_unregister_functions(zend_function_entry *functions, int count, HashTable *function_table)
 {
        zend_function_entry *ptr = functions;
        int i=0;
+       HashTable *target_function_table = function_table;
        CLS_FETCH();
 
+       if (!target_function_table) {
+               target_function_table = CG(function_table);
+       }
        while (ptr->fname) {
                if (count!=-1 && i>=count) {
                        break;
                }
 #if 0
-               zend_printf("Unregistering %s()\n",ptr->fname);
+               zend_printf("Unregistering %s()\n", ptr->fname);
 #endif
-               zend_hash_del(CG(function_table),ptr->fname,strlen(ptr->fname)+1);
+               zend_hash_del(target_function_table, ptr->fname, strlen(ptr->fname)+1);
                ptr++;
                i++;
        }
@@ -675,7 +667,7 @@ ZEND_API int zend_register_module(zend_module_entry *module)
 #if 0
        zend_printf("%s:  Registering module %d\n",module->name, module->module_number);
 #endif
-       if (module->functions && zend_register_functions(module->functions)==FAILURE) {
+       if (module->functions && zend_register_functions(module->functions, NULL)==FAILURE) {
                zend_error(E_CORE_WARNING,"%s:  Unable to register functions, unable to load",module->name);
                return FAILURE;
        }
@@ -706,7 +698,7 @@ void module_destructor(zend_module_entry *module)
        }
        module->module_started=0;
        if (module->functions) {
-               zend_unregister_functions(module->functions,-1);
+               zend_unregister_functions(module->functions, -1, NULL);
        }
 
 #if HAVE_LIBDL
@@ -779,6 +771,10 @@ ZEND_API zend_class_entry *register_internal_class(zend_class_entry *class_entry
 
        zend_hash_update(CG(class_table), lowercase_name, class_entry->name_length+1, class_entry, sizeof(zend_class_entry), (void **) &register_class);
        free(lowercase_name);
+       
+       if (class_entry->builtin_functions) {
+               zend_register_functions(class_entry->builtin_functions, &class_entry->function_table);
+       }
        return register_class;
 }
 
index e312e5b2140ca642f59e12eac730121cf2dc4fa0..c1a3edb486e4936f46bf5162aad859d22f061761 100644 (file)
 #define ZEND_FE(name, arg_types) ZEND_NAMED_FE(name, zend_if_##name, arg_types)
 
 
+#define INIT_CLASS_ENTRY(class_container, class_name, functions)       \
+       {                                                                                                                               \
+               class_container.name = strdup(class_name);                                      \
+               class_container.name_length = sizeof(class_name)-1;                     \
+               class_container.builtin_functions = functions;                          \
+               class_container.handle_function_call = NULL;                            \
+               class_container.handle_property_get = NULL;                                     \
+               class_container.handle_property_set = NULL;                                     \
+       }
+
+#define INIT_OVERLOADED_CLASS_ENTRY(class_container, class_name, functions, handle_fcall, handle_propget, handle_propset) \
+       {                                                                                                                       \
+               class_container.name = strdup(class_name);                              \
+               class_container.name_length = sizeof(class_name)-1;             \
+               class_container.builtin_functions = functions;                  \
+               class_container.handle_function_call = handle_fcall;    \
+               class_container.handle_property_get = handle_propget;   \
+               class_container.handle_property_set = handle_propset;   \
+       }
+
+
+
 int zend_next_free_module(void);
 
 ZEND_API int getParameters(int ht, int param_count,...);
@@ -35,17 +57,18 @@ ZEND_API int getParametersArray(int ht, int param_count, zval **argument_array);
 ZEND_API int getParametersEx(int param_count,...);
 ZEND_API int getParametersArrayEx(int param_count, zval ***argument_array);
 
-ZEND_API int getThis(zval **this_ptr);
 ZEND_API int ParameterPassedByReference(int ht, uint n);
 
-int zend_register_functions(zend_function_entry *functions);
-void zend_unregister_functions(zend_function_entry *functions, int count);
+int zend_register_functions(zend_function_entry *functions, HashTable *function_table);
+void zend_unregister_functions(zend_function_entry *functions, int count, HashTable *function_table);
 ZEND_API int zend_register_module(zend_module_entry *module_entry);
 ZEND_API zend_class_entry *register_internal_class(zend_class_entry *class_entry);
 ZEND_API zend_module_entry *zend_get_module(int module_number);
 
 ZEND_API void wrong_param_count(void);
 
+#define getThis() (this_ptr)
+
 #define WRONG_PARAM_COUNT { wrong_param_count(); return; }
 #define WRONG_PARAM_COUNT_WITH_RETVAL(ret) { wrong_param_count(); return ret; }
 #define ARG_COUNT(ht) (ht)
index e82948acf62a36074c8089cb47df2db09c1a73f8..8f022e1325569687be87a44091e68808eb8adb9a 100644 (file)
@@ -389,7 +389,7 @@ ZEND_API void shutdown_memory_manager(int silent, int clean_cache)
        if (had_leaks) {
                ELS_FETCH();
 
-               if (EG(AiCount)!=0) {
+               if (EG(AiCount)!=0 && !silent) {
                        fprintf(stderr, "AiCount did not zero out:  %d\n", EG(AiCount));
                }
        }
index 5224033258be054022d6c436d68dd9947f42f16a..fac2c1db283e9c172443f02de17f05329615d00c 100644 (file)
@@ -734,6 +734,7 @@ void do_begin_dynamic_function_call(znode *function_name CLS_DC)
        
                opline->opcode = ZEND_INIT_FCALL_BY_NAME;
                opline->op2 = *function_name;
+               opline->extended_value = 0;
                SET_UNUSED(opline->op1);
        }
        zend_stack_push(&CG(function_call_stack), (void *) &ptr, sizeof(unsigned char *));
@@ -749,6 +750,7 @@ void do_begin_class_member_function_call(znode *class_name, znode *function_name
        zend_str_tolower(class_name->u.constant.value.str.val, class_name->u.constant.value.str.len);
        opline->op1 = *class_name;
        opline->op2 = *function_name;
+       opline->extended_value = ZEND_MEMBER_FUNC_CALL;
        zval_copy_ctor(&opline->op2.u.constant);
        zend_stack_push(&CG(function_call_stack), (void *) &ptr, sizeof(unsigned char *));
 }
@@ -883,6 +885,7 @@ void do_early_binding(CLS_D)
        opline->opcode = ZEND_NOP;
        SET_UNUSED(opline->op1);
        SET_UNUSED(opline->op2);
+       //CG(active_op_array)->last--;
 }
 
 
@@ -1297,6 +1300,7 @@ void do_begin_new_object(znode *result, znode *variable, znode *new_token, znode
        opline->opcode = ZEND_INIT_FCALL_BY_NAME;
        opline->op1 = *result;
        opline->op2 = *class_name;
+       opline->extended_value = ZEND_MEMBER_FUNC_CALL | ZEND_CTOR_CALL;
        zend_stack_push(&CG(function_call_stack), (void *) &ptr, sizeof(unsigned char *));
 }
 
index e48acf4f2f8470777e89dcaa50b0acbf4493ba8f..a439e352feed0e6536a289379ee90ead9c76ff2f 100644 (file)
@@ -535,4 +535,7 @@ int zendlex(znode *zendlval CLS_DC);
 #define ZEND_FETCH_STANDARD            0
 #define ZEND_FETCH_NO_AI_COUNT 1
 
+#define ZEND_MEMBER_FUNC_CALL  1<<0
+#define ZEND_CTOR_CALL                 1<<1
+
 #endif /* _COMPILE_H */
index b49c69f05afb2819aac6e092b9922f5ce83e582e..f2623b44102cf74628d2cd91a49a6575a4890a22 100644 (file)
@@ -793,7 +793,7 @@ static void call_overloaded_function(int arg_count, zval *return_value, HashTabl
        zend_property_reference *property_reference;
 
        zend_stack_top(&EG(overloaded_objects_stack), (void **) &property_reference);
-       (*(property_reference->object))->value.obj.ce->handle_function_call(arg_count, return_value, list, plist, property_reference);
+       (*(property_reference->object))->value.obj.ce->handle_function_call(arg_count, return_value, list, plist, *property_reference->object, property_reference);
        //(*(property_reference->object))->value.obj.ce->handle_function_call(NULL, NULL, NULL, NULL, NULL);
        zend_llist_destroy(&property_reference->elements_list);
 
@@ -1226,9 +1226,7 @@ binary_assign_op_addr: {
                                        HashTable *active_function_table;
                                        zval tmp;
 
-                                       if ((opline>EG(active_op_array)->opcodes)
-                                               && opline->op1.op_type==IS_VAR
-                                               && (opline-1)->opcode == ZEND_JMP_NO_CTOR) {
+                                       if (opline->extended_value & ZEND_CTOR_CALL) {
                                                /* constructor call */
                                                EG(AiCount)++; /* for op1 */
                                                if (opline->op2.op_type==IS_VAR) {
@@ -1325,7 +1323,7 @@ overloaded_function_call_cont:
                                        zend_ptr_stack_push(&EG(argument_stack), (void *) opline->extended_value);
                                        if (function_state.function->type==ZEND_INTERNAL_FUNCTION) {
                                                var_uninit(&Ts[opline->result.u.var].tmp_var);
-                                               ((zend_internal_function *) function_state.function)->handler(opline->extended_value, &Ts[opline->result.u.var].tmp_var, &EG(regular_list), &EG(persistent_list));
+                                               ((zend_internal_function *) function_state.function)->handler(opline->extended_value, &Ts[opline->result.u.var].tmp_var, &EG(regular_list), &EG(persistent_list), (object_ptr?*object_ptr:NULL));
                                        } else if (function_state.function->type==ZEND_USER_FUNCTION) {
                                                if (EG(symtable_cache_ptr)>=EG(symtable_cache)) {
                                                        //printf("Cache hit!  Reusing %x\n", symtable_cache[symtable_cache_ptr]);
index 6f20f976b045035580ee1bc771f945ea3b8746b6..687068cd76ca19c6a561f8749cb6d6ab3c45afc4 100644 (file)
@@ -335,7 +335,7 @@ int call_user_function(HashTable *function_table, zval *object, zval *function_n
                EG(return_value)=original_return_value;
                EG(opline_ptr) = original_opline_ptr;
        } else {
-               ((zend_internal_function *) function_state.function)->handler(param_count, retval, &EG(regular_list), &EG(persistent_list));
+               ((zend_internal_function *) function_state.function)->handler(param_count, retval, &EG(regular_list), &EG(persistent_list), object);
        }
        zend_ptr_stack_clear_multiple(ELS_C);
        EG(function_state_ptr) = original_function_state_ptr;