File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / php / ext / mysqli / mysqli_warning.c
Revision 1.1.1.4 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Sun Jun 15 20:03:51 2014 UTC (10 years ago) by misho
Branches: php, MAIN
CVS tags: v5_4_29, HEAD
php 5.4.29

    1: /*
    2:   +----------------------------------------------------------------------+
    3:   | PHP Version 5                                                        |
    4:   +----------------------------------------------------------------------+
    5:   | Copyright (c) 1997-2014 The PHP Group                                |
    6:   +----------------------------------------------------------------------+
    7:   | This source file is subject to version 3.01 of the PHP license,      |
    8:   | that is bundled with this package in the file LICENSE, and is        |
    9:   | available through the world-wide-web at the following url:           |
   10:   | http://www.php.net/license/3_01.txt                                  |
   11:   | If you did not receive a copy of the PHP license and are unable to   |
   12:   | obtain it through the world-wide-web, please send a note to          |
   13:   | license@php.net so we can mail you a copy immediately.               |
   14:   +----------------------------------------------------------------------+
   15:   | Author: Georg Richter <georg@php.net>                                |
   16:   +----------------------------------------------------------------------+
   17: 
   18: */
   19: #ifdef HAVE_CONFIG_H
   20: #include "config.h"
   21: #endif
   22: 
   23: #include <signal.h>
   24: 
   25: #include "php.h"
   26: #include "php_ini.h"
   27: #include "ext/standard/info.h"
   28: #include "php_mysqli_structs.h"
   29: #include "mysqli_priv.h"
   30: 
   31: /* Define these in the PHP5 tree to make merging easy process */
   32: #define ZSTR_DUPLICATE (1<<0)
   33: #define ZSTR_AUTOFREE  (1<<1)
   34: 
   35: #define ZVAL_UTF8_STRING(z, s, flags)          ZVAL_STRING((z), (char*)(s), ((flags) & ZSTR_DUPLICATE))
   36: #define ZVAL_UTF8_STRINGL(z, s, l, flags)      ZVAL_STRINGL((z), (char*)(s), (l), ((flags) & ZSTR_DUPLICATE))
   37: 
   38: 
   39: /* {{{ void php_clear_warnings() */
   40: void php_clear_warnings(MYSQLI_WARNING *w)
   41: {
   42: 	MYSQLI_WARNING *n;
   43: 
   44: 	while (w) {
   45: 		n = w;
   46: 		zval_dtor(&(w->reason));
   47: 		zval_dtor(&(w->sqlstate));
   48: 		w = w->next;
   49: 		efree(n);
   50: 	}
   51: }
   52: /* }}} */
   53: 
   54: 
   55: #ifndef MYSQLI_USE_MYSQLND
   56: /* {{{ MYSQLI_WARNING *php_new_warning */
   57: static
   58: MYSQLI_WARNING *php_new_warning(const char *reason, int errorno TSRMLS_DC)
   59: {
   60: 	MYSQLI_WARNING *w;
   61: 
   62: 	w = (MYSQLI_WARNING *)ecalloc(1, sizeof(MYSQLI_WARNING));
   63: 
   64: 	ZVAL_UTF8_STRING(&(w->reason), reason, ZSTR_DUPLICATE);
   65: 
   66: 	ZVAL_UTF8_STRINGL(&(w->sqlstate), "HY000", sizeof("HY000") - 1,  ZSTR_DUPLICATE);
   67: 
   68: 	w->errorno = errorno;
   69: 
   70: 	return w;
   71: }
   72: /* }}} */
   73: 
   74: 
   75: /* {{{ MYSQLI_WARNING *php_get_warnings(MYSQL *mysql TSRMLS_DC) */
   76: MYSQLI_WARNING *php_get_warnings(MYSQL *mysql TSRMLS_DC)
   77: {
   78: 	MYSQLI_WARNING *w, *first = NULL, *prev = NULL;
   79: 	MYSQL_RES		*result;
   80: 	MYSQL_ROW 		row;
   81: 
   82: 	if (mysql_real_query(mysql, "SHOW WARNINGS", 13)) {
   83: 		return NULL;
   84: 	}
   85: 
   86: 	result = mysql_store_result(mysql);
   87: 
   88: 	while ((row = mysql_fetch_row(result))) {
   89: 		w = php_new_warning(row[2], atoi(row[1]) TSRMLS_CC);
   90: 		if (!first) {
   91: 			first = w;
   92: 		}
   93: 		if (prev) {
   94: 			prev->next = w;
   95: 		}
   96: 		prev = w;
   97: 	}
   98: 	mysql_free_result(result);
   99: 	return first;
  100: }
  101: /* }}} */
  102: #else
  103: /* {{{ MYSQLI_WARNING *php_new_warning */
  104: static
  105: MYSQLI_WARNING *php_new_warning(const zval * reason, int errorno TSRMLS_DC)
  106: {
  107: 	MYSQLI_WARNING *w;
  108: 
  109: 	w = (MYSQLI_WARNING *)ecalloc(1, sizeof(MYSQLI_WARNING));
  110: 
  111: 	w->reason = *reason;
  112: 	zval_copy_ctor(&(w->reason));
  113: 
  114: 	ZVAL_UTF8_STRINGL(&(w->reason),  Z_STRVAL(w->reason), Z_STRLEN(w->reason),  ZSTR_AUTOFREE);
  115: 
  116: 	ZVAL_UTF8_STRINGL(&(w->sqlstate), "HY000", sizeof("HY000") - 1,  ZSTR_DUPLICATE);
  117: 
  118: 	w->errorno = errorno;
  119: 
  120: 	return w;
  121: }
  122: /* }}} */
  123: 
  124: 
  125: /* {{{ MYSQLI_WARNING *php_get_warnings(MYSQL *mysql TSRMLS_DC) */
  126: MYSQLI_WARNING * php_get_warnings(MYSQLND_CONN_DATA * mysql TSRMLS_DC)
  127: {
  128: 	MYSQLI_WARNING	*w, *first = NULL, *prev = NULL;
  129: 	MYSQL_RES		*result;
  130: 	zval			*row;
  131: 
  132: 	if (mysql->m->query(mysql, "SHOW WARNINGS", 13 TSRMLS_CC)) {
  133: 		return NULL;
  134: 	}
  135: 
  136: 	result = mysql->m->use_result(mysql TSRMLS_CC);
  137: 
  138: 	for (;;) {
  139: 		zval **entry;
  140: 		int errno;
  141: 
  142: 		MAKE_STD_ZVAL(row);
  143: 		mysqlnd_fetch_into(result, MYSQLND_FETCH_NUM, row, MYSQLND_MYSQLI);
  144: 		if (Z_TYPE_P(row) != IS_ARRAY) {
  145: 			zval_ptr_dtor(&row);
  146: 			break;
  147: 		}
  148: 		zend_hash_internal_pointer_reset(Z_ARRVAL_P(row));
  149: 		/* 0. we don't care about the first */
  150: 		zend_hash_move_forward(Z_ARRVAL_P(row));
  151: 
  152: 		/* 1. Here comes the error no */
  153: 		zend_hash_get_current_data(Z_ARRVAL_P(row), (void **)&entry);
  154: 		convert_to_long_ex(entry);
  155: 		errno = Z_LVAL_PP(entry);
  156: 		zend_hash_move_forward(Z_ARRVAL_P(row));
  157: 
  158: 		/* 2. Here comes the reason */
  159: 		zend_hash_get_current_data(Z_ARRVAL_P(row), (void **)&entry);
  160: 
  161: 		w = php_new_warning(*entry, errno TSRMLS_CC);
  162: 		/*
  163: 		  Don't destroy entry, because the row destroy will decrease
  164: 		  the refcounter. Decreased twice then mysqlnd_free_result()
  165: 		  will crash, because it will try to access already freed memory.
  166: 		*/
  167: 		if (!first) {
  168: 			first = w;
  169: 		}
  170: 		if (prev) {
  171: 			prev->next = (void *)w;
  172: 		}
  173: 		prev = w;
  174: 
  175: 		zval_ptr_dtor(&row);
  176: 	}
  177: 
  178: 	mysql_free_result(result);
  179: 	return first;
  180: }
  181: /* }}} */
  182: #endif
  183: 
  184: 
  185: /* {{{ bool mysqli_warning::next() */
  186: PHP_METHOD(mysqli_warning, next)
  187: {
  188: 	MYSQLI_WARNING 	*w;
  189: 	zval  			*mysqli_warning;
  190: 	mysqli_object *obj = (mysqli_object *)zend_objects_get_address(getThis() TSRMLS_CC);
  191: 
  192: 	if (obj->ptr) {
  193: 		if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O",
  194: 										 &mysqli_warning, mysqli_warning_class_entry) == FAILURE) {
  195: 			return;
  196: 		}
  197: 
  198: 		MYSQLI_FETCH_RESOURCE(w, MYSQLI_WARNING *, &mysqli_warning, "mysqli_warning", MYSQLI_STATUS_VALID);
  199: 
  200: 		if (w && w->next) {
  201: 			w = w->next;
  202: 	        ((MYSQLI_RESOURCE *)(obj->ptr))->ptr = w;
  203: 			RETURN_TRUE;
  204: 		}
  205: 	}
  206: 	RETURN_FALSE;
  207: }
  208: /* }}} */
  209: 
  210: 
  211: /* {{{ property mysqli_warning_message */
  212: static
  213: int mysqli_warning_message(mysqli_object *obj, zval **retval TSRMLS_DC)
  214: {
  215: 	MYSQLI_WARNING *w;
  216: 
  217: 	if (!obj->ptr || !((MYSQLI_RESOURCE *)(obj->ptr))->ptr) {
  218: 		return FAILURE;
  219: 	}
  220: 
  221: 	w = (MYSQLI_WARNING *)((MYSQLI_RESOURCE *)(obj->ptr))->ptr;
  222: 	MAKE_STD_ZVAL(*retval);
  223: 	**retval = w->reason;
  224: 	zval_copy_ctor(*retval);
  225: 	return SUCCESS;
  226: }
  227: /* }}} */
  228: 
  229: 
  230: /* {{{ property mysqli_warning_sqlstate */
  231: static
  232: int mysqli_warning_sqlstate(mysqli_object *obj, zval **retval TSRMLS_DC)
  233: {
  234: 	MYSQLI_WARNING *w;
  235: 
  236: 	if (!obj->ptr || !((MYSQLI_RESOURCE *)(obj->ptr))->ptr) {
  237: 		return FAILURE;
  238: 	}
  239: 
  240: 	w = (MYSQLI_WARNING *)((MYSQLI_RESOURCE *)(obj->ptr))->ptr;
  241: 	MAKE_STD_ZVAL(*retval);
  242: 	**retval = w->sqlstate;
  243: 	zval_copy_ctor(*retval);
  244: 	return SUCCESS;
  245: }
  246: /* }}} */
  247: 
  248: 
  249: /* {{{ property mysqli_warning_error */
  250: static
  251: int mysqli_warning_errno(mysqli_object *obj, zval **retval TSRMLS_DC)
  252: {
  253: 	MYSQLI_WARNING *w;
  254: 
  255: 	if (!obj->ptr || !((MYSQLI_RESOURCE *)(obj->ptr))->ptr) {
  256: 		return FAILURE;
  257: 	}
  258: 	w = (MYSQLI_WARNING *)((MYSQLI_RESOURCE *)(obj->ptr))->ptr;
  259: 	MAKE_STD_ZVAL(*retval);
  260: 	ZVAL_LONG(*retval, w->errorno);
  261: 	return SUCCESS;
  262: }
  263: /* }}} */
  264: 
  265: /* {{{ mysqli_warning_construct(object obj) */
  266: PHP_METHOD(mysqli_warning, __construct)
  267: {
  268: 	zval			*z;
  269: 	mysqli_object	*obj;
  270: #ifndef MYSQLI_USE_MYSQLND
  271: 	MYSQL			*hdl;
  272: #endif
  273: 	MYSQLI_WARNING  *w;
  274: 	MYSQLI_RESOURCE *mysqli_resource;
  275: 
  276: 	if (ZEND_NUM_ARGS() != 1) {
  277: 		WRONG_PARAM_COUNT;
  278: 	}
  279: 	if (zend_parse_parameters(1 TSRMLS_CC, "o", &z)==FAILURE) {
  280: 		return;
  281: 	}
  282: 	obj = (mysqli_object *)zend_object_store_get_object(z TSRMLS_CC);\
  283: 
  284: 	if (obj->zo.ce == mysqli_link_class_entry) {
  285: 		MY_MYSQL *mysql;
  286: 		MYSQLI_FETCH_RESOURCE_CONN(mysql, &z, MYSQLI_STATUS_VALID);
  287: 		if (mysql_warning_count(mysql->mysql)) {
  288: #ifndef MYSQLI_USE_MYSQLND
  289: 			w = php_get_warnings(mysql->mysql TSRMLS_CC);
  290: #else
  291: 			w = php_get_warnings(mysql->mysql->data TSRMLS_CC);
  292: #endif
  293: 		} else {
  294: 			php_error_docref(NULL TSRMLS_CC, E_WARNING, "No warnings found");
  295: 			RETURN_FALSE;
  296: 		}
  297: 	} else if (obj->zo.ce == mysqli_stmt_class_entry) {
  298: 		MY_STMT *stmt;
  299: 		MYSQLI_FETCH_RESOURCE_STMT(stmt, &z, MYSQLI_STATUS_VALID);
  300: #ifndef MYSQLI_USE_MYSQLND
  301: 		hdl = mysqli_stmt_get_connection(stmt->stmt);
  302: 		if (mysql_warning_count(hdl)) {
  303: 			w = php_get_warnings(hdl TSRMLS_CC);
  304: #else
  305: 		if (mysqlnd_stmt_warning_count(stmt->stmt)) {
  306: 			w = php_get_warnings(mysqli_stmt_get_connection(stmt->stmt) TSRMLS_CC);
  307: #endif
  308: 		} else {
  309: 			php_error_docref(NULL TSRMLS_CC, E_WARNING, "No warnings found");
  310: 			RETURN_FALSE;
  311: 		}
  312: 	} else {
  313: 		php_error_docref(NULL TSRMLS_CC, E_WARNING, "invalid class argument");
  314: 		RETURN_FALSE;
  315: 	}
  316: 
  317: 	mysqli_resource = (MYSQLI_RESOURCE *)ecalloc (1, sizeof(MYSQLI_RESOURCE));
  318: 	mysqli_resource->ptr = mysqli_resource->info = (void *)w;
  319: 	mysqli_resource->status = MYSQLI_STATUS_VALID;
  320: 
  321: 	if (!getThis() || !instanceof_function(Z_OBJCE_P(getThis()), mysqli_warning_class_entry TSRMLS_CC)) {
  322: 		MYSQLI_RETURN_RESOURCE(mysqli_resource, mysqli_warning_class_entry);
  323: 	} else {
  324: 		((mysqli_object *) zend_object_store_get_object(getThis() TSRMLS_CC))->ptr = mysqli_resource;
  325: 	}
  326: 
  327: }
  328: /* }}} */
  329: 
  330: /* {{{ mysqli_warning_methods */
  331: const zend_function_entry mysqli_warning_methods[] = {
  332: 	PHP_ME(mysqli_warning, __construct,		NULL, ZEND_ACC_PROTECTED)
  333: 	PHP_ME(mysqli_warning, next, 			NULL, ZEND_ACC_PUBLIC)
  334: 	{NULL, NULL, NULL}
  335: };
  336: /* }}} */
  337: 
  338: /* {{{ mysqli_warning_property_entries */
  339: const mysqli_property_entry mysqli_warning_property_entries[] = {
  340: 	{"message", sizeof("message") - 1, mysqli_warning_message, NULL},
  341: 	{"sqlstate", sizeof("sqlstate") - 1, mysqli_warning_sqlstate, NULL},
  342: 	{"errno", sizeof("errno") - 1, mysqli_warning_errno, NULL},
  343: 	{NULL, 0, NULL, NULL}
  344: };
  345: /* }}} */
  346: 
  347: /* {{{ mysqli_warning_property_info_entries */
  348: const zend_property_info mysqli_warning_property_info_entries[] = {
  349: 	{ZEND_ACC_PUBLIC, "message", 	sizeof("message") - 1,	-1, 0, NULL, 0, NULL},
  350: 	{ZEND_ACC_PUBLIC, "sqlstate",	sizeof("sqlstate") - 1,	-1, 0, NULL, 0, NULL},
  351: 	{ZEND_ACC_PUBLIC, "errno",		sizeof("errno") - 1, 	-1, 0, NULL, 0, NULL},
  352: 	{0,					NULL, 			0,					-1, 0, NULL, 0, NULL}
  353: };
  354: /* }}} */
  355: 
  356: 
  357: /*
  358:  * Local variables:
  359:  * tab-width: 4
  360:  * c-basic-offset: 4
  361:  * indent-tabs-mode: t
  362:  * End:
  363:  * vim600: noet sw=4 ts=4 fdm=marker
  364:  * vim<600: noet sw=4 ts=4
  365:  */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>