]> granicus.if.org Git - php/commitdiff
- Simplify code (only implement handlers that are necessary)
authorMarcus Boerger <helly@php.net>
Mon, 21 Mar 2005 00:29:06 +0000 (00:29 +0000)
committerMarcus Boerger <helly@php.net>
Mon, 21 Mar 2005 00:29:06 +0000 (00:29 +0000)
- Fix handling of read only property 'queryString'
- Fix overloading
- Move class init code to their defining .c files for simplification
- Mark class PDORow as final until there's a need to inherit this and
  someone implements the handlers correct then.

ext/pdo/pdo.c
ext/pdo/pdo_dbh.c
ext/pdo/pdo_stmt.c
ext/pdo/php_pdo_int.h

index a925d534d72322eb0ab6cc26ec76fda79da4efee..409d1933376a9856b199fceaf0c2bc70e7a2768d 100755 (executable)
@@ -32,7 +32,6 @@
 #include "php_pdo_driver.h"
 #include "php_pdo_int.h"
 #include "zend_exceptions.h"
-#include "zend_interfaces.h"
 
 #if defined(HAVE_SPL) && ((PHP_MAJOR_VERSION > 5) || (PHP_MAJOR_VERSION == 5 && PHP_MINOR_VERSION >= 1))
 extern PHPAPI zend_class_entry *spl_ce_RuntimeException;
@@ -342,19 +341,8 @@ PHP_MINIT_FUNCTION(pdo)
 #endif
        zend_declare_property_null(pdo_exception_ce, "errorInfo", sizeof("errorInfo")-1, ZEND_ACC_PUBLIC TSRMLS_CC);
 
-       INIT_CLASS_ENTRY(ce, "PDO", pdo_dbh_functions);
-       pdo_dbh_ce = zend_register_internal_class(&ce TSRMLS_CC);
-       pdo_dbh_ce->create_object = pdo_dbh_new;
-
-       INIT_CLASS_ENTRY(ce, "PDOStatement", pdo_dbstmt_functions);
-       pdo_dbstmt_ce = zend_register_internal_class(&ce TSRMLS_CC);
-       pdo_dbstmt_ce->get_iterator = pdo_stmt_iter_get;
-       pdo_dbstmt_ce->create_object = pdo_dbstmt_new;
-       zend_class_implements(pdo_dbstmt_ce TSRMLS_CC, 1, zend_ce_traversable); 
-
-       INIT_CLASS_ENTRY(ce, "PDORow", pdo_row_functions);
-       pdo_row_ce = zend_register_internal_class(&ce TSRMLS_CC);
-       pdo_row_ce->create_object = pdo_row_new;
+       pdo_dbh_init(TSRMLS_C);
+       pdo_stmt_init(TSRMLS_C);
 
        return SUCCESS;
 }
index 6587de1bcea7d8c2b2f694ffaaf98983fac33f58..787db5db86d45197d8ba615ff62a7aa09017bd0e 100755 (executable)
@@ -406,8 +406,17 @@ static zval *pdo_stmt_instantiate(pdo_dbh_t *dbh, zval *object, zend_class_entry
        return object;
 } /* }}} */
 
-static void pdo_stmt_construct(zval *object, zend_class_entry *dbstmt_ce, zval *ctor_args TSRMLS_DC) /* {{{ */
+static void pdo_stmt_construct(pdo_stmt_t *stmt, zval *object, zend_class_entry *dbstmt_ce, zval *ctor_args TSRMLS_DC) /* {{{ */
 {      
+       zval *query_string;
+       zval z_key;
+
+       MAKE_STD_ZVAL(query_string);
+       ZVAL_STRINGL(query_string, stmt->query_string, stmt->query_stringlen, 1);
+       ZVAL_STRINGL(&z_key, "queryString", sizeof("queryString")-1, 0);
+       std_object_handlers.write_property(object, &z_key, query_string TSRMLS_CC);
+       zval_ptr_dtor(&query_string);
+
        if (dbstmt_ce->constructor) {
                zend_fcall_info fci;
                zend_fcall_info_cache fcc;
@@ -493,9 +502,9 @@ static PHP_METHOD(PDO, prepare)
                        PDO_HANDLE_DBH_ERR();
                        RETURN_FALSE;
                }
-               if (dbstmt_ce->constructor && !(dbstmt_ce->constructor->common.fn_flags & ZEND_ACC_PRIVATE)) {
+               if (dbstmt_ce->constructor && !(dbstmt_ce->constructor->common.fn_flags & (ZEND_ACC_PRIVATE|ZEND_ACC_PROTECTED))) {
                        pdo_raise_impl_error(dbh, NULL, "HY000", 
-                               "user-supplied statement class must have a public constructor" TSRMLS_CC);
+                               "user-supplied statement class cannot have a public constructor" TSRMLS_CC);
                        PDO_HANDLE_DBH_ERR();
                        RETURN_FALSE;
                }
@@ -538,7 +547,7 @@ static PHP_METHOD(PDO, prepare)
        ZVAL_NULL(&stmt->lazy_object_ref);
 
        if (dbh->methods->preparer(dbh, statement, statement_len, stmt, options TSRMLS_CC)) {
-               pdo_stmt_construct(return_value, dbstmt_ce, ctor_args TSRMLS_CC);
+               pdo_stmt_construct(stmt, return_value, dbstmt_ce, ctor_args TSRMLS_CC);
                return;
        }
 
@@ -882,7 +891,7 @@ static PHP_METHOD(PDO, query)
                                        stmt->executed = 1;
                                }
                                if (ret) {
-                                       pdo_stmt_construct(return_value, pdo_dbstmt_ce, NULL TSRMLS_CC);
+                                       pdo_stmt_construct(stmt, return_value, pdo_dbstmt_ce, NULL TSRMLS_CC);
                                        return;
                                }
                        }
@@ -947,61 +956,6 @@ function_entry pdo_dbh_functions[] = {
 };
 
 /* {{{ overloaded object handlers for PDO class */
-static zval *dbh_prop_read(zval *object, zval *member, int type TSRMLS_DC)
-{
-       zval *return_value;
-
-       MAKE_STD_ZVAL(return_value);
-       ZVAL_NULL(return_value);
-
-       return return_value;
-}
-
-static void dbh_prop_write(zval *object, zval *member, zval *value TSRMLS_DC)
-{
-       return;
-}
-
-static zval *dbh_read_dim(zval *object, zval *offset, int type TSRMLS_DC)
-{
-       zval *return_value;
-
-       MAKE_STD_ZVAL(return_value);
-       ZVAL_NULL(return_value);
-
-       return return_value;
-}
-
-static void dbh_write_dim(zval *object, zval *offset, zval *value TSRMLS_DC)
-{
-       return;
-}
-
-static int dbh_prop_exists(zval *object, zval *member, int check_empty TSRMLS_DC)
-{
-       return 0;
-}
-
-static int dbh_dim_exists(zval *object, zval *member, int check_empty TSRMLS_DC)
-{
-       return 0;
-}
-
-static void dbh_prop_delete(zval *object, zval *offset TSRMLS_DC)
-{
-       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot delete properties from a PDO DBH");
-}
-
-static void dbh_dim_delete(zval *object, zval *offset TSRMLS_DC)
-{
-       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot delete dimensions from a PDO DBH");
-}
-
-static HashTable *dbh_get_properties(zval *object TSRMLS_DC)
-{
-       return NULL;
-}
-
 int pdo_hash_methods(pdo_dbh_t *dbh, int kind TSRMLS_DC)
 {
        function_entry *funcs;
@@ -1103,65 +1057,26 @@ out:
        return fbc;
 }
 
-static int dbh_call_method(char *method, INTERNAL_FUNCTION_PARAMETERS)
+static int dbh_compare(zval *object1, zval *object2 TSRMLS_DC)
 {
-       return FAILURE;
+       return -1;
 }
 
+static zend_object_handlers pdo_dbh_object_handlers;
 
-static union _zend_function *dbh_get_ctor(zval *object TSRMLS_DC)
+void pdo_dbh_init(TSRMLS_D)
 {
-       static zend_internal_function ctor = {0};
-       ctor.type = ZEND_INTERNAL_FUNCTION;
-       ctor.function_name = "__construct";
-       ctor.scope = pdo_dbh_ce;
-       ctor.handler = ZEND_FN(dbh_constructor);
+       zend_class_entry ce;
 
-       return (union _zend_function*)&ctor;
-}
+       INIT_CLASS_ENTRY(ce, "PDO", pdo_dbh_functions);
+       pdo_dbh_ce = zend_register_internal_class(&ce TSRMLS_CC);
+       pdo_dbh_ce->create_object = pdo_dbh_new;
 
-static zend_class_entry *dbh_get_ce(zval *object TSRMLS_DC)
-{
-       pdo_dbh_t *dbh = zend_object_store_get_object(object TSRMLS_CC);
-       return dbh->ce;
-}
-
-static int dbh_get_classname(zval *object, char **class_name, zend_uint *class_name_len, int parent TSRMLS_DC)
-{
-       *class_name = estrndup("PDO", sizeof("PDO")-1);
-       *class_name_len = sizeof("PDO")-1;
-       return 0;
+       memcpy(&pdo_dbh_object_handlers, &std_object_handlers, sizeof(zend_object_handlers));
+       pdo_dbh_object_handlers.get_method = dbh_method_get;
+       pdo_dbh_object_handlers.compare_objects = dbh_compare;
 }
 
-static int dbh_compare(zval *object1, zval *object2 TSRMLS_DC)
-{
-       return -1;
-}
-
-static zend_object_handlers pdo_dbh_object_handlers = {
-       ZEND_OBJECTS_STORE_HANDLERS,
-       dbh_prop_read,
-       dbh_prop_write,
-       dbh_read_dim,
-       dbh_write_dim,
-       NULL,
-       NULL,
-       NULL,
-       dbh_prop_exists,
-       dbh_prop_delete,
-       dbh_dim_exists,
-       dbh_dim_delete,
-       dbh_get_properties,
-       dbh_method_get,
-       dbh_call_method,
-       dbh_get_ctor,
-       dbh_get_ce,
-       dbh_get_classname,
-       dbh_compare,
-       NULL, /* cast */
-       NULL
-};
-
 static void dbh_free(pdo_dbh_t *dbh TSRMLS_DC)
 {
        if (--dbh->refcount)
@@ -1184,13 +1099,8 @@ static void dbh_free(pdo_dbh_t *dbh TSRMLS_DC)
        pefree(dbh, dbh->is_persistent);
 }
 
-static void pdo_dbh_free_storage(zend_object *object TSRMLS_DC)
+static void pdo_dbh_free_storage(pdo_dbh_t *dbh TSRMLS_DC)
 {
-       pdo_dbh_t *dbh = (pdo_dbh_t*)object;
-       if (!dbh) {
-               return;
-       }
-
        if (dbh->properties) {
                zend_hash_destroy(dbh->properties);
                efree(dbh->properties);
@@ -1206,16 +1116,19 @@ zend_object_value pdo_dbh_new(zend_class_entry *ce TSRMLS_DC)
 {
        zend_object_value retval;
        pdo_dbh_t *dbh;
+       zval *tmp;
+
        dbh = emalloc(sizeof(*dbh));
        memset(dbh, 0, sizeof(*dbh));
        dbh->ce = ce;
        dbh->refcount = 1;
        ALLOC_HASHTABLE(dbh->properties);
        zend_hash_init(dbh->properties, 0, NULL, ZVAL_PTR_DTOR, 0);
+       zend_hash_copy(dbh->properties, &ce->default_properties, (copy_ctor_func_t) zval_add_ref, (void *) &tmp, sizeof(zval *));
        
-       retval.handle = zend_objects_store_put(dbh, (zend_objects_store_dtor_t)zend_objects_destroy_object, pdo_dbh_free_storage, NULL TSRMLS_CC);
+       retval.handle = zend_objects_store_put(dbh, (zend_objects_store_dtor_t)zend_objects_destroy_object, (zend_objects_free_object_storage_t)pdo_dbh_free_storage, NULL TSRMLS_CC);
        retval.handlers = &pdo_dbh_object_handlers;
-
+       
        return retval;
 }
 
index 6f0b9e0e337fb061d261e7e344a23c101516b6d2..1e2c6520e1242b772945d07db33a3cec7da449ce 100755 (executable)
@@ -34,6 +34,7 @@
 #include "php_pdo_driver.h"
 #include "php_pdo_int.h"
 #include "zend_exceptions.h"
+#include "zend_interfaces.h"
 #include "php_memory_streams.h"
 
 #if COMPILE_DL_PDO
@@ -1671,66 +1672,30 @@ function_entry pdo_dbstmt_functions[] = {
 };
 
 /* {{{ overloaded handlers for PDOStatement class */
-static zval *dbstmt_prop_read(zval *object, zval *member, int type TSRMLS_DC)
+static void dbstmt_prop_write(zval *object, zval *member, zval *value TSRMLS_DC)
 {
-       zval *return_value;
        pdo_stmt_t * stmt = (pdo_stmt_t *) zend_object_store_get_object(object TSRMLS_CC);
 
        convert_to_string(member);
 
        if(strcmp(Z_STRVAL_P(member), "queryString") == 0) {
-               MAKE_STD_ZVAL(return_value);
-               ZVAL_STRINGL(return_value, stmt->query_string, stmt->query_stringlen, 1);
+               pdo_raise_impl_error(stmt->dbh, stmt, "HY000", "property queryString is read only" TSRMLS_CC);
        } else {
-               MAKE_STD_ZVAL(return_value);
-               ZVAL_NULL(return_value);
+               std_object_handlers.write_property(object, member, value TSRMLS_CC);
        }
-       return return_value;
-}
-
-static void dbstmt_prop_write(zval *object, zval *member, zval *value TSRMLS_DC)
-{
-       return;
-}
-
-static zval *dbstmt_read_dim(zval *object, zval *offset, int type TSRMLS_DC)
-{
-       zval *return_value;
-
-       MAKE_STD_ZVAL(return_value);
-       ZVAL_NULL(return_value);
-
-       return return_value;
-}
-
-static void dbstmt_write_dim(zval *object, zval *offset, zval *value TSRMLS_DC)
-{
-       return;
-}
-
-static int dbstmt_prop_exists(zval *object, zval *member, int check_empty TSRMLS_DC)
-{
-       return 0;
 }
 
-static int dbstmt_dim_exists(zval *object, zval *member, int check_empty TSRMLS_DC)
+static void dbstmt_prop_delete(zval *object, zval *member TSRMLS_DC)
 {
-       return 0;
-}
-
-static void dbstmt_prop_delete(zval *object, zval *offset TSRMLS_DC)
-{
-       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot delete properties from a PDOStatement");
-}
+       pdo_stmt_t * stmt = (pdo_stmt_t *) zend_object_store_get_object(object TSRMLS_CC);
 
-static void dbstmt_dim_delete(zval *object, zval *offset TSRMLS_DC)
-{
-       php_error_docref(NULL TSRMLS_CC, E_WARNING, "Cannot delete dimensions from a PDOStatement");
-}
+       convert_to_string(member);
 
-static HashTable *dbstmt_get_properties(zval *object TSRMLS_DC)
-{
-       return NULL;
+       if(strcmp(Z_STRVAL_P(member), "queryString") == 0) {
+               pdo_raise_impl_error(stmt->dbh, stmt, "HY000", "property queryString is read only" TSRMLS_CC);
+       } else {
+               std_object_handlers.unset_property(object, member TSRMLS_CC);
+       }
 }
 
 static union _zend_function *dbstmt_method_get(
@@ -1776,54 +1741,35 @@ out:
        return fbc;
 }
 
-static int dbstmt_call_method(char *method, INTERNAL_FUNCTION_PARAMETERS)
+static int dbstmt_compare(zval *object1, zval *object2 TSRMLS_DC)
 {
-       return FAILURE;
+       return -1;
 }
 
-static union _zend_function *dbstmt_get_ctor(zval *object TSRMLS_DC)
-{
-       return std_object_handlers.get_constructor(object TSRMLS_CC);
-}
+static zend_object_handlers pdo_dbstmt_object_handlers;
 
-static zend_class_entry *dbstmt_get_ce(zval *object TSRMLS_DC)
+void pdo_stmt_init(TSRMLS_D)
 {
-       return std_object_handlers.get_class_entry(object TSRMLS_CC);
-}
+       zend_class_entry ce;
 
-static int dbstmt_get_classname(zval *object, char **class_name, zend_uint *class_name_len, int parent TSRMLS_DC)
-{
-       return std_object_handlers.get_class_name(object, class_name, class_name_len, parent TSRMLS_CC);
-}
+       INIT_CLASS_ENTRY(ce, "PDOStatement", pdo_dbstmt_functions);
+       pdo_dbstmt_ce = zend_register_internal_class(&ce TSRMLS_CC);
+       pdo_dbstmt_ce->get_iterator = pdo_stmt_iter_get;
+       pdo_dbstmt_ce->create_object = pdo_dbstmt_new;
+       zend_class_implements(pdo_dbstmt_ce TSRMLS_CC, 1, zend_ce_traversable); 
+       zend_declare_property_null(pdo_dbstmt_ce, "queryString", sizeof("queryString")-1, ZEND_ACC_PUBLIC TSRMLS_CC);
 
-static int dbstmt_compare(zval *object1, zval *object2 TSRMLS_DC)
-{
-       return -1;
-}
+       memcpy(&pdo_dbstmt_object_handlers, &std_object_handlers, sizeof(zend_object_handlers));
+       pdo_dbstmt_object_handlers.write_property = dbstmt_prop_write;
+       pdo_dbstmt_object_handlers.unset_property = dbstmt_prop_delete;
+       pdo_dbstmt_object_handlers.get_method = dbstmt_method_get;
+       pdo_dbstmt_object_handlers.compare_objects = dbstmt_compare;
 
-zend_object_handlers pdo_dbstmt_object_handlers = {
-       ZEND_OBJECTS_STORE_HANDLERS,
-       dbstmt_prop_read,
-       dbstmt_prop_write,
-       dbstmt_read_dim,
-       dbstmt_write_dim,
-       NULL,
-       NULL,
-       NULL,
-       dbstmt_prop_exists,
-       dbstmt_prop_delete,
-       dbstmt_dim_exists,
-       dbstmt_dim_delete,
-       dbstmt_get_properties,
-       dbstmt_method_get,
-       dbstmt_call_method,
-       dbstmt_get_ctor,
-       dbstmt_get_ce,
-       dbstmt_get_classname,
-       dbstmt_compare,
-       NULL, /* cast */
-       NULL
-};
+       INIT_CLASS_ENTRY(ce, "PDORow", pdo_row_functions);
+       pdo_row_ce = zend_register_internal_class(&ce TSRMLS_CC);
+       pdo_row_ce->ce_flags |= ZEND_ACC_FINAL_CLASS; /* when removing this a lot of handlers need to be redone */
+       pdo_row_ce->create_object = pdo_row_new;
+}
 
 static void free_statement(pdo_stmt_t *stmt TSRMLS_DC)
 {
@@ -1879,6 +1825,7 @@ void pdo_dbstmt_free_storage(pdo_stmt_t *stmt TSRMLS_DC)
 zend_object_value pdo_dbstmt_new(zend_class_entry *ce TSRMLS_DC)
 {
        zend_object_value retval;
+       zval *tmp;
 
        pdo_stmt_t *stmt;
        stmt = emalloc(sizeof(*stmt));
@@ -1887,6 +1834,7 @@ zend_object_value pdo_dbstmt_new(zend_class_entry *ce TSRMLS_DC)
        stmt->refcount = 1;
        ALLOC_HASHTABLE(stmt->properties);
        zend_hash_init(stmt->properties, 0, NULL, ZVAL_PTR_DTOR, 0);
+       zend_hash_copy(stmt->properties, &ce->default_properties, (copy_ctor_func_t) zval_add_ref, (void *) &tmp, sizeof(zval *));
 
        retval.handle = zend_objects_store_put(stmt, (zend_objects_store_dtor_t)zend_objects_destroy_object, (zend_objects_free_object_storage_t)pdo_dbstmt_free_storage, NULL TSRMLS_CC);
        retval.handlers = &pdo_dbstmt_object_handlers;
@@ -2164,7 +2112,7 @@ static int row_compare(zval *object1, zval *object2 TSRMLS_DC)
        return -1;
 }
 
-zend_object_handlers pdo_row_object_handlers = {
+static zend_object_handlers pdo_row_object_handlers = {
        ZEND_OBJECTS_STORE_HANDLERS,
        row_prop_or_dim_read,
        row_prop_or_dim_write,
index 41b3f1ccf1d9de0c978db67b27bdc62bbbae3bb8..82ccf3826fe3747ad3242e32f5033f856ab4aaa0 100755 (executable)
@@ -25,6 +25,9 @@
 extern zend_class_entry *pdo_exception_ce;
 int php_pdo_list_entry(void);
 
+void pdo_dbh_init(TSRMLS_D);
+void pdo_stmt_init(TSRMLS_D);
+
 extern zend_object_value pdo_dbh_new(zend_class_entry *ce TSRMLS_DC);
 extern function_entry pdo_dbh_functions[];
 extern zend_class_entry *pdo_dbh_ce;