]> granicus.if.org Git - php/commitdiff
* Make the output handling of variables much, much cooler.
authorZeev Suraski <zeev@php.net>
Fri, 11 Jun 1999 10:44:26 +0000 (10:44 +0000)
committerZeev Suraski <zeev@php.net>
Fri, 11 Jun 1999 10:44:26 +0000 (10:44 +0000)
  Uses zend_make_printable_zval() instead of convert_to_string() now:

$foo = true;
print "\$foo is $foo";
will now print
$foo is true
(instead of "$foo is 1", earlier).

Also, with objects, it automatically tries to call __print() and use it as a printing
function.

For example:

class foo {
  function __print() { return "Foo Object"; }
};

$foo = new foo;
print $foo;

will print "Foo Object".

Zend/zend.c
Zend/zend.h
Zend/zend_execute.c
Zend/zend_execute_API.c

index ef9a39451bfdf77cf437b28d07ac601cc6b1b90d..fdc6be4a3fd3c54bb0c96ccbbe5b305a70faab40 100644 (file)
@@ -22,6 +22,7 @@
 #include "modules.h"
 #include "zend_constants.h"
 #include "zend_list.h"
+#include "zend_API.h"
 
 #ifdef ZTS
 #      define GLOBAL_FUNCTION_TABLE    global_function_table
@@ -97,38 +98,72 @@ static void print_hash(HashTable *ht, int indent)
 }
 
 
-ZEND_API int zend_print_zval(zval *expr, int indent)
+ZEND_API void zend_make_printable_zval(zval *expr, zval *expr_copy, int *use_copy)
 {
-       zval expr_copy;
-       int destroy=0;
-
-       if (expr->type != IS_STRING) {
-               if (expr->type == IS_BOOL) {
+       if (expr->type==IS_STRING) {
+               *use_copy = 0;
+               return;
+       }
+       switch (expr->type) {
+               case IS_BOOL:
                        if (expr->value.lval) {
-                               expr_copy.value.str.val = estrndup("true",4);
-                               expr_copy.value.str.len = 4;
+                               expr_copy->value.str.len = sizeof("true")-1;
+                               expr_copy->value.str.val = estrndup("true", expr_copy->value.str.len);
                        } else {
-                               expr_copy.value.str.val = estrndup("false",5);
-                               expr_copy.value.str.len = 5;
+                               expr_copy->value.str.len = sizeof("false")-1;
+                               expr_copy->value.str.val = estrndup("false", expr_copy->value.str.len);
                        }
-                       expr_copy.type = IS_STRING;
-               } else if (expr->type == IS_RESOURCE) {
-                       expr_copy.value.str.val = (char *) emalloc(sizeof("Resource id #")-1 + MAX_LENGTH_OF_LONG);
-                       expr_copy.value.str.len = sprintf(expr_copy.value.str.val, "Resource id #%ld", expr->value.lval);
-                       expr_copy.type = IS_STRING;
-               } else {
-                       expr_copy = *expr;
-                       zval_copy_ctor(&expr_copy);
-                       convert_to_string(&expr_copy);
-               }
+                       break;
+               case IS_RESOURCE:
+                       expr_copy->value.str.val = (char *) emalloc(sizeof("Resource id #")-1 + MAX_LENGTH_OF_LONG);
+                       expr_copy->value.str.len = sprintf(expr_copy->value.str.val, "Resource id #%ld", expr->value.lval);
+                       break;
+               case IS_ARRAY:
+                       expr_copy->value.str.len = sizeof("Array")-1;
+                       expr_copy->value.str.val = estrndup("Array", expr_copy->value.str.len);
+                       break;
+               case IS_OBJECT: {
+                               zval function_name;
+
+                               function_name.value.str.len = sizeof("__print")-1;
+                               function_name.value.str.val = estrndup("__print", function_name.value.str.len);
+                               function_name.type = IS_STRING;
+
+                               if (call_user_function(NULL, expr, &function_name, expr_copy, 0, NULL)==FAILURE) {
+                                       expr_copy->value.str.len = sizeof("Object")-1;
+                                       expr_copy->value.str.val = estrndup("Object", expr_copy->value.str.len);
+                               }
+                               efree(function_name.value.str.val);
+                       }
+                       break;
+               default:
+                       *expr_copy = *expr;
+                       zval_copy_ctor(expr_copy);
+                       convert_to_string(expr_copy);
+                       break;
+       }
+       expr_copy->type = IS_STRING;
+       *use_copy = 1;
+}
+
+
+ZEND_API int zend_print_zval(zval *expr, int indent)
+{
+       zval expr_copy;
+       int use_copy;
+
+       zend_make_printable_zval(expr, &expr_copy, &use_copy);
+       if (use_copy) {
                expr = &expr_copy;
-               destroy=1;
        }
        if (expr->value.str.len==0) { /* optimize away empty strings */
+               if (use_copy) {
+                       zval_dtor(expr);
+               }
                return 0;
        }
        ZEND_WRITE(expr->value.str.val,expr->value.str.len);
-       if (destroy) {
+       if (use_copy) {
                zval_dtor(expr);
        }
        return expr->value.str.len;
index ece884f84a459f55a69019f6c8f98599df9853c0..56fd918bcfe2046f9a5673743f32bb15c0937979 100644 (file)
@@ -180,6 +180,7 @@ ZEND_API void zend_bailout();
 END_EXTERN_C()
 ZEND_API char *get_zend_version();
 
+ZEND_API void zend_make_printable_zval(zval *expr, zval *expr_copy, int *use_copy);
 ZEND_API int zend_print_zval(zval *expr, int indent);
 ZEND_API void zend_print_zval_r(zval *expr, int indent);
 
index b18a8ef27df5a350374ecec2f558fa2f99eba584..e6e7ac3d8ee7d7afd32e2b50e2c54224a82adc11 100644 (file)
@@ -1217,19 +1217,16 @@ binary_assign_op_addr: {
                        case ZEND_ADD_VAR: {
                                        zval *var = get_zval_ptr(&opline->op2, Ts, &free_op2, BP_VAR_R);
                                        zval var_copy;
-                                       int destroy=0;
+                                       int use_copy;
 
-                                       if (var->type != IS_STRING) {
-                                               var_copy = *var;
-                                               zval_copy_ctor(&var_copy);
+                                       zend_make_printable_zval(var, &var_copy, &use_copy);
+                                       if (use_copy) {
                                                var = &var_copy;
-                                               convert_to_string(var);
-                                               destroy=1;
                                        }
                                        add_string_to_string(   &Ts[opline->result.u.var].tmp_var,
                                                                                        get_zval_ptr(&opline->op1, Ts, &free_op1, BP_VAR_NA),
                                                                                        var);
-                                       if (destroy) {
+                                       if (use_copy) {
                                                zval_dtor(var);
                                        }
                                        /* original comment, possibly problematic:
index 5440103d7d60690abba9a2ee08b82077bd9483c1..bce067597d7661a1d55e5dabbe30fcca55f7f9bb 100644 (file)
@@ -276,12 +276,10 @@ int call_user_function(HashTable *function_table, zval *object, zval *function_n
                        return FAILURE;
                }
                function_table = &object->value.obj.ce->function_table;
-               /* unimplemented */
        }
        original_function_state_ptr = EG(function_state_ptr);
        zend_str_tolower(function_name->value.str.val, function_name->value.str.len);
        if (zend_hash_find(function_table, function_name->value.str.val, function_name->value.str.len+1, (void **) &function_state.function)==FAILURE) {
-               zend_error(E_ERROR, "Unknown function:  %s()\n", function_name->value.str.val);
                return FAILURE;
        }