Pantek Library
Hosting Provided By
CybrHost
High Speed Hosting

PHP mysqlnd svn commit: r735 - in trunk: mysqlnd tests/ext/mysql

From: <ahristov(at)mysql.com>
Date: Thu Jul 12 2007 - 10:42:24 EDT


Author: ahristov
Date: 2007-07-12 16:42:24 +0200 (Thu, 12 Jul 2007) New Revision: 735

Modified:

   trunk/mysqlnd/mysqlnd_result_meta.c
   trunk/mysqlnd/mysqlnd_wireprotocol.c
   trunk/mysqlnd/mysqlnd_wireprotocol.h
   trunk/mysqlnd/portability.h
   trunk/tests/ext/mysql/mysql_query.phpt
Log:
Fix crash and possible crashes in metadata cloning. Added output to mysql_result.phpt which is needed after the new addition to the test.

Modified: trunk/mysqlnd/mysqlnd_result_meta.c


  • trunk/mysqlnd/mysqlnd_result_meta.c 2007-07-12 14:08:44 UTC (rev 734) +++ trunk/mysqlnd/mysqlnd_result_meta.c 2007-07-12 14:42:24 UTC (rev 735) @@ -271,26 +271,26 @@ new_fields[i].root = pemalloc(orig_fields[i].root_len, persistent); memcpy(new_fields[i].root, orig_fields[i].root, new_fields[i].root_len);
    • if (orig_fields[i].name) { + if (orig_fields[i].name && orig_fields[i].name != mysqlnd_empty_string) { new_fields[i].name = new_fields[i].root + (orig_fields[i].name - orig_fields[i].root); }
    • if (orig_fields[i].org_name) { + if (orig_fields[i].org_name && orig_fields[i].org_name != mysqlnd_empty_string) { new_fields[i].org_name = new_fields[i].root + (orig_fields[i].org_name - orig_fields[i].root); }
    • if (orig_fields[i].table) { + if (orig_fields[i].table && orig_fields[i].table != mysqlnd_empty_string) { new_fields[i].table = new_fields[i].root + (orig_fields[i].table - orig_fields[i].root); }
    • if (orig_fields[i].org_table) { + if (orig_fields[i].org_table && orig_fields[i].org_table != mysqlnd_empty_string) { new_fields[i].org_table = new_fields[i].root + (orig_fields[i].org_table - orig_fields[i].root); }
    • if (orig_fields[i].db) { + if (orig_fields[i].db && orig_fields[i].db != mysqlnd_empty_string) { new_fields[i].db = new_fields[i].root + (orig_fields[i].db - orig_fields[i].root); }
    • if (orig_fields[i].catalog) { + if (orig_fields[i].catalog && orig_fields[i].catalog != mysqlnd_empty_string) { new_fields[i].catalog = new_fields[i].root + (orig_fields[i].catalog - orig_fields[i].root); } /* def is not on the root, if allocated at all */

Modified: trunk/mysqlnd/mysqlnd_wireprotocol.c


  • trunk/mysqlnd/mysqlnd_wireprotocol.c 2007-07-12 14:08:44 UTC (rev 734) +++ trunk/mysqlnd/mysqlnd_wireprotocol.c 2007-07-12 14:42:24 UTC (rev 735) @@ -59,9 +59,11 @@

 extern mysqlnd_packet_methods packet_methods[];  

-static const char *unknown_sqlstate= "HY000"; +static const char *unknown_sqlstate= "HY000";  

+char * const mysqlnd_empty_string = "";  

+
 /* {{{ mysqlnd_command_to_text
  */
 const char * const mysqlnd_command_to_text[COM_END] = @@ -950,7 +952,23 @@
 }
 /* }}} */  

+static size_t rset_field_offsets[] =
+{
+	STRUCT_OFFSET(MYSQLND_FIELD, catalog),
+	STRUCT_OFFSET(MYSQLND_FIELD, catalog_length),
+	STRUCT_OFFSET(MYSQLND_FIELD, db),
+	STRUCT_OFFSET(MYSQLND_FIELD, db_length),
+	STRUCT_OFFSET(MYSQLND_FIELD, table),
+	STRUCT_OFFSET(MYSQLND_FIELD, table_length),
+	STRUCT_OFFSET(MYSQLND_FIELD, org_table),
+	STRUCT_OFFSET(MYSQLND_FIELD, org_table_length),
+	STRUCT_OFFSET(MYSQLND_FIELD, name),
+	STRUCT_OFFSET(MYSQLND_FIELD, name_length),
+	STRUCT_OFFSET(MYSQLND_FIELD, org_name),
+	STRUCT_OFFSET(MYSQLND_FIELD, org_name_length)
+};
 
Do you need help?X

+
 /* {{{ php_mysqlnd_rset_field_read */
 static enum_func_status
 php_mysqlnd_rset_field_read(void *_packet, MYSQLND *conn TSRMLS_DC) @@ -963,6 +981,7 @@

 	char *root_ptr;
 	size_t buf_len = conn->net.cmd_buffer.length, len, total_len = 0;
 	MYSQLND_FIELD *meta;
+	unsigned int i, field_count = sizeof(rset_field_offsets)/sizeof(size_t);
 
 	PACKET_READ_HEADER_AND_BODY(packet, conn, buf, buf_len, "field");
 
@@ -971,55 +990,24 @@
 	}
 
 	meta = packet->metadata;
-	if ((len = php_mysqlnd_net_field_length(&p)) && len != MYSQLND_NULL_LENGTH) {

- meta->catalog = (char *)p;
- p += (meta->catalog_length = len);
- total_len += len + 1;
- } else if (len == MYSQLND_NULL_LENGTH) {
- goto faulty_fake;
- } - if ((len = php_mysqlnd_net_field_length(&p)) && len != MYSQLND_NULL_LENGTH) {
- meta->db = (char *)p;
- p += (meta->db_length = len);
- total_len += len + 1;
- } else if (len == MYSQLND_NULL_LENGTH) {
- goto faulty_fake;
+ for (i = 0; i < field_count; i += 2) { + switch ((len = php_mysqlnd_net_field_length(&p))) { + case 0: + *(char **)(((char*)meta) + rset_field_offsets[i]) = mysqlnd_empty_string; + *(unsigned int *)(((char*)meta) + rset_field_offsets[i+1]) = 0; + break; + case MYSQLND_NULL_LENGTH: + goto faulty_fake; + default: + *(char **)(((char *)meta) + rset_field_offsets[i]) = p; + *(unsigned int *)(((char*)meta) + rset_field_offsets[i+1]) = len;
Do you need more help?X
+ p += len; + total_len += len + 1; + break; + } } - if ((len = php_mysqlnd_net_field_length(&p)) && len != MYSQLND_NULL_LENGTH) {
- meta->table = (char *)p;
- p += (meta->table_length = len);
- total_len += len + 1;
- } else if (len == MYSQLND_NULL_LENGTH) {
- goto faulty_fake;
- } - - if ((len = php_mysqlnd_net_field_length(&p)) && len != MYSQLND_NULL_LENGTH) {
- meta->org_table = (char *)p;
- p += (meta->org_table_length = len);
- total_len += len + 1;
- } else if (len == MYSQLND_NULL_LENGTH) {
- goto faulty_fake;
- } - - if ((len = php_mysqlnd_net_field_length(&p)) && len != MYSQLND_NULL_LENGTH) {
- meta->name = (char *)p;
- p += (meta->name_length = len);
- total_len += len + 1;
- } else if (len == MYSQLND_NULL_LENGTH) {
- goto faulty_fake;
- } - - if ((len = php_mysqlnd_net_field_length(&p)) && len != MYSQLND_NULL_LENGTH) {
- meta->org_name = (char *)p;
- p += (meta->org_name_length = len);
- total_len += len + 1;
- } else if (len == MYSQLND_NULL_LENGTH) {
- goto faulty_fake;
- }

-
-
 	/* 1 byte filler */
 	p++;
 
@@ -1068,41 +1056,41 @@
 	root_ptr = meta->root = emalloc(total_len);
 	meta->root_len = total_len;
 	/* Now do allocs */
-	if (meta->catalog) {
+	if (meta->catalog && meta->catalog != mysqlnd_empty_string) {
 		len = meta->catalog_length;
 		meta->catalog = memcpy(root_ptr, meta->catalog, len);
 		*(root_ptr +=len) = '\0';
 		root_ptr++;
 	}
 
-	if (meta->db) {
+	if (meta->db && meta->db != mysqlnd_empty_string) {
 		len = meta->db_length;
 		meta->db = memcpy(root_ptr, meta->db, len);
 		*(root_ptr + len) = '\0';
 	}
 
-	if (meta->table) {
+	if (meta->table && meta->table != mysqlnd_empty_string) {
 		len = meta->table_length;
 		meta->table = memcpy(root_ptr, meta->table, len);
 		*(root_ptr +=len) = '\0';
 		root_ptr++;
 	}
 
-	if (meta->org_table) {
+	if (meta->org_table && meta->org_table != mysqlnd_empty_string) {
 		len = meta->org_table_length;
 		meta->org_table = memcpy(root_ptr, meta->org_table, len);
 		*(root_ptr +=len) = '\0';
 		root_ptr++;
 	}
 
-	if (meta->name) {
+	if (meta->name && meta->name != mysqlnd_empty_string) {
 		len = meta->name_length;
 		meta->name = memcpy(root_ptr, meta->name, len);
 		*(root_ptr +=len) = '\0';
Can we help you?X
root_ptr++; } - if (meta->org_name) { + if (meta->org_name && meta->org_name != mysqlnd_empty_string) { len = meta->org_name_length; meta->org_name = memcpy(root_ptr, meta->org_name, len); *(root_ptr +=len) = '\0';

Modified: trunk/mysqlnd/mysqlnd_wireprotocol.h


  • trunk/mysqlnd/mysqlnd_wireprotocol.h 2007-07-12 14:08:44 UTC (rev 734) +++ trunk/mysqlnd/mysqlnd_wireprotocol.h 2007-07-12 14:42:24 UTC (rev 735) @@ -311,6 +311,8 @@ unsigned long php_mysqlnd_net_field_length(zend_uchar **packet); zend_uchar * php_mysqlnd_net_store_length(zend_uchar *packet, mynd_ulonglong length);

+extern char * const mysqlnd_empty_string; +
 #endif /* MYSQLND_WIREPROTOCOL_H */  

 /*

Modified: trunk/mysqlnd/portability.h


  • trunk/mysqlnd/portability.h 2007-07-12 14:08:44 UTC (rev 734) +++ trunk/mysqlnd/portability.h 2007-07-12 14:42:24 UTC (rev 735) @@ -11,6 +11,9 @@

 #include <main/php_config.h>  

+/* Comes from global.h as OFFSET, renamed to STRUCT_OFFSET */
+#define STRUCT_OFFSET(t, f)   ((size_t)(char *)&((t *)0)->f)
+
 #ifndef __attribute

 #if !defined(__GNUC__)
 #define __attribute(A)

Modified: trunk/tests/ext/mysql/mysql_query.phpt


  • trunk/tests/ext/mysql/mysql_query.phpt 2007-07-12 14:08:44 UTC (rev 734) +++ trunk/tests/ext/mysql/mysql_query.phpt 2007-07-12 14:42:24 UTC (rev 735) @@ -93,6 +93,10 @@ ["valid"]=> string(30) "this is sql but with semicolon" } +array(1) { + [""]=> + string(1) "a" +}

 Warning: mysql_query(): %d is not a valid MySQL-Link resource in %s on line %d  done!
@@ -101,6 +105,10 @@

Can't find what you're looking for?X

   [u"valid"]=>
   unicode(30) "this is sql but with semicolon"  }

+array(1) {
+  [u""]=>
+  unicode(1) "a"
+}
 

 Warning: mysql_query(): %d is not a valid MySQL-Link resource in %s on line %d  done!

-- 
MySQL Code Commits Mailing List
For list archives: 
http://lists.mysql.com/commits
To unsubscribe:    
http://lists.mysql.com/commits?unsub=lists@pantek.com
Received on Thu Jul 12 10:42:29 2007

This archive was generated by hypermail 2.1.8 : Thu Aug 02 2007 - 01:54:59 EDT


Contact Us  Legal Notices  Order Services Online 
Pantek Home  Privacy Policy  IT news  Site Map  Pantek Library