List:Commits« Previous MessageNext Message »
From:Ian Greenhoe Date:August 29 2006 9:10pm
Subject:bk commit into 5.0 tree (igreenhoe:1.2255) BUG#16864
View as plain text  
Below is the list of changes that have just been committed into a local
5.0 repository of greenman. When greenman does a push these changes will
be propagated to the main repository and, within 24 hours after the
push, to the public repository.
For information on how to access the public repository
see http://dev.mysql.com/doc/mysql/en/installing-source-tree.html

ChangeSet@stripped, 2006-08-29 14:10:26-07:00, igreenhoe@stripped +29 -0
  Fix for bug #16864, (strxmov in code).
  
  Problem:  strxmov allows for a potential buffer overflow condition
  unless sizes of strings passed in are checked carefully prior to use.
  
  Solution:  Replace uses of strxmov with strxnmov, which checks to
  ensure that a buffer overrun does not occur.
  
  Note:  This is against the 5.0 tree.  The 5.1 tree will require
  some additional changes.

  client/mysql.cc@stripped, 2006-08-29 14:10:18-07:00, igreenhoe@stripped +1 -1
    strxmov cleanup

  client/mysqlcheck.c@stripped, 2006-08-29 14:10:18-07:00, igreenhoe@stripped +19 -11
    strxmov cleanup

  client/mysqldump.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +45 -32
    strxmov cleanup

  client/mysqlimport.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +14 -10
    strxmov cleanup

  client/mysqlshow.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +4 -3
    strxmov cleanup

  client/mysqltest.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +6 -6
    strxmov cleanup

  extra/comp_err.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +5 -4
    strxmov cleanup

  myisammrg/myrg_create.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +3 -2
    strxmov cleanup

  mysys/charset.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +2 -1
    strxmov cleanup

  mysys/default.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +2 -2
    strxmov cleanup

  mysys/mf_loadpath.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +1 -1
    strxmov cleanup

  mysys/my_init.c@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +4 -3
    strxmov cleanup

  mysys/raid.cc@stripped, 2006-08-29 14:10:19-07:00, igreenhoe@stripped +3 -1
    strxmov cleanup

  sql-common/client.c@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +4 -3
    strxmov cleanup

  sql/ha_myisam.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +2 -2
    strxmov cleanup

  sql/item.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +6 -6
    strxmov cleanup

  sql/log.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +3 -3
    strxmov cleanup

  sql/log_event.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +7 -4
    strxmov cleanup

  sql/mysqld.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +11 -10
    strxmov cleanup

  sql/sp.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +2 -2
    strxmov cleanup

  sql/sql_acl.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +9 -9
    strxmov cleanup

  sql/sql_base.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +4 -3
    strxmov cleanup

  sql/sql_db.cc@stripped, 2006-08-29 14:10:20-07:00, igreenhoe@stripped +12 -11
    strxmov cleanup

  sql/sql_parse.cc@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +5 -3
    strxmov cleanup

  sql/sql_show.cc@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +9 -7
    strxmov cleanup

  sql/sql_table.cc@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +12 -9
    strxmov cleanup

  sql/sql_trigger.cc@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +5 -3
    strxmov cleanup

  sql/table.cc@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +6 -6
    strxmov cleanup

  tests/mysql_client_test.c@stripped, 2006-08-29 14:10:21-07:00, igreenhoe@stripped +23 -16
    strxmov cleanup

# This is a BitKeeper patch.  What follows are the unified diffs for the
# set of deltas contained in the patch.  The rest of the patch, the part
# that BitKeeper cares about, is below these diffs.
# User:	igreenhoe
# Host:	anubis.greendragongames.com
# Root:	/home/greenman/workspace-mysql/mysql/bug-5.0-16864

--- 1.215/client/mysql.cc	2006-08-29 14:10:38 -07:00
+++ 1.216/client/mysql.cc	2006-08-29 14:10:38 -07:00
@@ -2812,7 +2812,7 @@
   if (!(editor = (char *)getenv("EDITOR")) &&
       !(editor = (char *)getenv("VISUAL")))
     editor = "vi";
-  strxmov(buff,editor," ",filename,NullS);
+  strxnmov(buff, sizeof(buff), editor, " ", filename, NullS);
   (void) system(buff);
 
   MY_STAT stat_arg;

--- 1.237/client/mysqldump.c	2006-08-29 14:10:38 -07:00
+++ 1.238/client/mysqldump.c	2006-08-29 14:10:38 -07:00
@@ -76,7 +76,7 @@
 #define IGNORE_DATA 0x01 /* don't dump data for this table */
 #define IGNORE_INSERT_DELAYED 0x02 /* table doesn't support INSERT DELAYED */
 
-static char *add_load_option(char *ptr, const char *object,
+static char *add_load_option(char *ptr, uint ptr_size, const char *object,
                              const char *statement);
 static ulong find_set(TYPELIB *lib, const char *x, uint length,
                       char **err_pos, uint *err_len);
@@ -1368,15 +1368,17 @@
                   Allocate memory for new query string: original string
                   from SHOW statement and version-specific comments.
                 */
-                query_str= alloc_query_str(strlen(row[2]) + 23);
+                uint length= strlen(row[2]) + 23;
+                query_str= alloc_query_str(length);
 
                 query_str_tail= strnmov(query_str, row[2],
                                         definer_begin - row[2]);
                 query_str_tail= strmov(query_str_tail, "*/ /*!50020");
                 query_str_tail= strnmov(query_str_tail, definer_begin,
                                         definer_end - definer_begin);
-                query_str_tail= strxmov(query_str_tail, "*/ /*!50003",
-                                        definer_end, NullS);
+                query_str_tail= strxnmov(query_str_tail,
+                                        query_str + length - query_str_tail,
+                                        "*/ /*!50003", definer_end, NullS);
               }
             }
 
@@ -2007,18 +2009,18 @@
   DBUG_VOID_RETURN;
 }
 
-static char *add_load_option(char *ptr,const char *object,
+static char *add_load_option(char *ptr, uint ptr_size, const char *object,
                              const char *statement)
 {
   if (object)
   {
     /* Don't escape hex constants */
     if (object[0] == '0' && (object[1] == 'x' || object[1] == 'X'))
-      ptr= strxmov(ptr," ",statement," ",object,NullS);
+      ptr= strxnmov(ptr, ptr_size, " ", statement, " ", object, NullS);
     else
     {
       /* char constant; escape */
-      ptr= strxmov(ptr," ",statement," '",NullS);
+      ptr= strxnmov(ptr, ptr_size, " ", statement, " '", NullS);
       ptr= field_escape(ptr,object,(uint) strlen(object));
       *ptr++= '\'';
     }
@@ -2162,11 +2164,16 @@
 
     if (fields_terminated || enclosed || opt_enclosed || escaped)
       end= strmov(end, " FIELDS");
-    end= add_load_option(end, fields_terminated, " TERMINATED BY");
-    end= add_load_option(end, enclosed, " ENCLOSED BY");
-    end= add_load_option(end, opt_enclosed, " OPTIONALLY ENCLOSED BY");
-    end= add_load_option(end, escaped, " ESCAPED BY");
-    end= add_load_option(end, lines_terminated, " LINES TERMINATED BY");
+    end= add_load_option(end, query_buf + sizeof(query_buf) - end,
+                         fields_terminated, " TERMINATED BY");
+    end= add_load_option(end, query_buf + sizeof(query_buf) - end,
+                         enclosed, " ENCLOSED BY");
+    end= add_load_option(end, query_buf + sizeof(query_buf) - end,
+                         opt_enclosed, " OPTIONALLY ENCLOSED BY");
+    end= add_load_option(end, query_buf + sizeof(query_buf) - end,
+                         escaped, " ESCAPED BY");
+    end= add_load_option(end, query_buf + sizeof(query_buf) - end,
+                         lines_terminated, " LINES TERMINATED BY");
     *end= '\0';
 
     my_snprintf(buff, sizeof(buff), " FROM %s", result_table);
@@ -2179,9 +2186,11 @@
       end = strmov(query, query_buf);
 
       if (where)
-        end = strxmov(end, " WHERE ", where, NullS);
+        end= strxnmov(end, query_buf + sizeof(query_buf) - end, " WHERE ",
+                     where, NullS);
       if (order_by)
-        end = strxmov(end, " ORDER BY ", order_by, NullS);
+        end= strxnmov(end, query_buf + sizeof(query_buf) - end, " ORDER BY ",
+                     order_by, NullS);
     }
     if (mysql_real_query(mysql, query, (uint) (end - query)))
     {
@@ -2214,7 +2223,8 @@
           fprintf(md_result_file, "-- WHERE:  %s\n", where);
           check_io(md_result_file);
         }
-        end = strxmov(end, " WHERE ", where, NullS);
+        end= strxnmov(end, query_buf + sizeof(query_buf) - end, " WHERE ",
+                      where, NullS);
       }
       if (order_by)
       {
@@ -2223,7 +2233,8 @@
           fprintf(md_result_file, "-- ORDER BY:  %s\n", order_by);
           check_io(md_result_file);
         }
-        end = strxmov(end, " ORDER BY ", order_by, NullS);
+        end= strxnmov(end, query_buf + sizeof(query_buf) - end, " ORDER BY ",
+                      order_by, NullS);
       }
     }
     if (!opt_xml && !opt_compact)
@@ -3297,8 +3308,9 @@
   if (result_length)
   {
     char *end;
+    uint length= result_length + 10;
     /* result (terminating \0 is already in result_length) */
-    result = my_malloc(result_length + 10, MYF(MY_WME));
+    result= my_malloc(length, MYF(MY_WME));
     if (!result)
     {
       fprintf(stderr, "Error: Not enough memory to store ORDER BY clause\n");
@@ -3308,7 +3320,7 @@
     row = mysql_fetch_row(res);
     end = strmov(result, row[4]);
     while ((row = mysql_fetch_row(res)) && atoi(row[3]) > 1)
-      end = strxmov(end, ",", row[4], NullS);
+      end= strxnmov(end, result + length - end, ",", row[4], NullS);
   }
 
 cleanup:
@@ -3481,11 +3493,12 @@
     {
 
       ptr= search_buf;
-      search_len= (ulong)(strxmov(ptr, "WITH ", row[0],
+      search_len= (ulong)(strxnmov(ptr, sizeof(search_buf), "WITH ", row[0],
                                   " CHECK OPTION", NullS) - ptr);
       ptr= replace_buf;
-      replace_len=(ulong)(strxmov(ptr, "*/\n/*!50002 WITH ", row[0],
-                                  " CHECK OPTION", NullS) - ptr);
+      replace_len= (ulong)(strxnmov(ptr, sizeof(replace_buf),
+                                    "*/\n/*!50002 WITH ", row[0],
+                                    " CHECK OPTION", NullS) - ptr);
       replace(&ds_view, search_buf, search_len, replace_buf, replace_len);
     }
 
@@ -3506,19 +3519,19 @@
 
       ptr= search_buf;
       search_len=
-        (ulong)(strxmov(ptr, "DEFINER=",
-                        quote_name(user_name_str, quoted_user_name_str, FALSE),
-                        "@",
-                        quote_name(host_name_str, quoted_host_name_str, FALSE),
-                        " SQL SECURITY ", row[2], NullS) - ptr);
+        (ulong)(strxnmov(ptr, sizeof(search_buf), "DEFINER=",
+                         quote_name(user_name_str, quoted_user_name_str, FALSE),
+                         "@",
+                         quote_name(host_name_str, quoted_host_name_str, FALSE),
+                         " SQL SECURITY ", row[2], NullS) - ptr);
       ptr= replace_buf;
       replace_len=
-        (ulong)(strxmov(ptr, "*/\n/*!50013 DEFINER=",
-                        quote_name(user_name_str, quoted_user_name_str, FALSE),
-                        "@",
-                        quote_name(host_name_str, quoted_host_name_str, FALSE),
-                        " SQL SECURITY ", row[2],
-                        " */\n/*!50001", NullS) - ptr);
+        (ulong)(strxnmov(ptr, sizeof(replace_buf), "*/\n/*!50013 DEFINER=",
+                         quote_name(user_name_str, quoted_user_name_str, FALSE),
+                         "@",
+                         quote_name(host_name_str, quoted_host_name_str, FALSE),
+                         " SQL SECURITY ", row[2],
+                         " */\n/*!50001", NullS) - ptr);
       replace(&ds_view, search_buf, search_len, replace_buf, replace_len);
     }
 

--- 1.60/client/mysqlimport.c	2006-08-29 14:10:38 -07:00
+++ 1.61/client/mysqlimport.c	2006-08-29 14:10:38 -07:00
@@ -33,7 +33,7 @@
 static void db_error_with_table(MYSQL *mysql, char *table);
 static void db_error(MYSQL *mysql);
 static char *field_escape(char *to,const char *from,uint length);
-static char *add_load_option(char *ptr,const char *object,
+static char *add_load_option(char *ptr, uint ptr_size, const char *object,
 			     const char *statement);
 
 static my_bool	verbose=0,lock_tables=0,ignore_errors=0,opt_delete=0,
@@ -316,12 +316,16 @@
 
   if (fields_terminated || enclosed || opt_enclosed || escaped)
       end= strmov(end, " FIELDS");
-  end= add_load_option(end, fields_terminated, " TERMINATED BY");
-  end= add_load_option(end, enclosed, " ENCLOSED BY");
-  end= add_load_option(end, opt_enclosed,
-		       " OPTIONALLY ENCLOSED BY");
-  end= add_load_option(end, escaped, " ESCAPED BY");
-  end= add_load_option(end, lines_terminated, " LINES TERMINATED BY");
+  end= add_load_option(end, sql_statement + sizeof(sql_statement) - end,
+                       fields_terminated, " TERMINATED BY");
+  end= add_load_option(end, sql_statement + sizeof(sql_statement) - end,
+                       enclosed, " ENCLOSED BY");
+  end= add_load_option(end, sql_statement + sizeof(sql_statement) - end,
+                       opt_enclosed, " OPTIONALLY ENCLOSED BY");
+  end= add_load_option(end, sql_statement + sizeof(sql_statement) - end,
+                       escaped, " ESCAPED BY");
+  end= add_load_option(end, sql_statement + sizeof(sql_statement) - end,
+                       lines_terminated, " LINES TERMINATED BY");
   if (opt_ignore_lines >= 0)
     end= strmov(longlong10_to_str(opt_ignore_lines, 
 				  strmov(end, " IGNORE "),10), " LINES");
@@ -449,18 +453,18 @@
 }
 
 
-static char *add_load_option(char *ptr, const char *object,
+static char *add_load_option(char *ptr, uint ptr_size, const char *object,
 			     const char *statement)
 {
   if (object)
   {
     /* Don't escape hex constants */
     if (object[0] == '0' && (object[1] == 'x' || object[1] == 'X'))
-      ptr= strxmov(ptr," ",statement," ",object,NullS);
+      ptr= strxnmov(ptr, ptr_size, " ", statement, " ", object, NullS);
     else
     {
       /* char constant; escape */
-      ptr= strxmov(ptr," ",statement," '",NullS);
+      ptr= strxnmov(ptr, ptr_size, " ", statement, " '", NullS);
       ptr= field_escape(ptr,object,(uint) strlen(object));
       *ptr++= '\'';
     }

--- 1.49/client/mysqlshow.c	2006-08-29 14:10:38 -07:00
+++ 1.50/client/mysqlshow.c	2006-08-29 14:10:38 -07:00
@@ -613,9 +613,10 @@
   MYSQL_RES *result;
   MYSQL_ROW row;
 
-  end=strxmov(query,"show table status from `",db,"`",NullS);
+  end= strxnmov(query, sizeof(query), "show table status from `", db, "`",
+                NullS);
   if (wild && wild[0])
-    strxmov(end," like '",wild,"'",NullS);
+    strxnmov(end, query + sizeof(query) - end, " like '", wild, "'", NullS);
   if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql)))
   {
     fprintf(stderr,"%s: Cannot get status for db: %s, table: %s: %s\n",
@@ -676,7 +677,7 @@
 
   end=strmov(strmov(strmov(query,"show /*!32332 FULL */ columns from `"),table),"`");
   if (wild && wild[0])
-    strxmov(end," like '",wild,"'",NullS);
+    strxnmov(end, query + sizeof(query) - end, " like '", wild, "'", NullS);
   if (mysql_query(mysql,query) || !(result=mysql_store_result(mysql)))
   {
     fprintf(stderr,"%s: Cannot list columns in db: %s, table: %s: %s\n",

--- 1.23/extra/comp_err.c	2006-08-29 14:10:38 -07:00
+++ 1.24/extra/comp_err.c	2006-08-29 14:10:38 -07:00
@@ -282,11 +282,11 @@
       DBUG_RETURN(1);
     }
 
-    outfile_end= strxmov(outfile, DATADIRECTORY, 
+    outfile_end= strxnmov(outfile, sizeof(outfile), DATADIRECTORY, 
                          tmp_lang->lang_long_name, NullS);
-    if (!my_stat(outfile, &stat_info,MYF(0)))
+    if (!my_stat(outfile, &stat_info, MYF(0)))
     {
-      if (my_mkdir(outfile, 0777,MYF(0)) < 0)
+      if (my_mkdir(outfile, 0777, MYF(0)) < 0)
       {
         fprintf(stderr, "Can't create output directory for %s\n", 
                 outfile);
@@ -294,7 +294,8 @@
       }
     }
 
-    strxmov(outfile_end, FN_ROOTDIR, OUTFILE, NullS);
+    strxnmov(outfile_end, outfile + sizeof(outfile) - outfile_end,
+             FN_ROOTDIR, OUTFILE, NullS);
 
     if (!(to= my_fopen(outfile, O_WRONLY | FILE_BINARY, MYF(MY_WME))))
       DBUG_RETURN(1);

--- 1.10/myisammrg/myrg_create.c	2006-08-29 14:10:38 -07:00
+++ 1.11/myisammrg/myrg_create.c	2006-08-29 14:10:38 -07:00
@@ -53,8 +53,9 @@
   }
   if (insert_method != MERGE_INSERT_DISABLED)
   {
-    end=strxmov(buff,"#INSERT_METHOD=",
-		get_type(&merge_insert_method,insert_method-1),"\n",NullS);
+    end= strxnmov(buff, sizeof(buff), "#INSERT_METHOD=",
+                  get_type(&merge_insert_method, insert_method - 1), "\n",
+                  NullS);
     if (my_write(file,buff,(uint) (end-buff),MYF(MY_WME | MY_NABP)))
         goto err;
   }

--- 1.147/mysys/charset.c	2006-08-29 14:10:38 -07:00
+++ 1.148/mysys/charset.c	2006-08-29 14:10:38 -07:00
@@ -484,7 +484,8 @@
   {
     if (!(cs->state & MY_CS_COMPILED) && !(cs->state & MY_CS_LOADED))
     {
-      strxmov(get_charsets_dir(buf), cs->csname, ".xml", NullS);
+      char *end= get_charsets_dir(buf);
+      strxnmov(end, buf + sizeof(buf) - end, cs->csname, ".xml", NullS);
       my_read_charset_file(buf,flags);
     }
     cs= (cs->state & MY_CS_AVAILABLE) ? cs : NULL;

--- 1.82/mysys/default.c	2006-08-29 14:10:38 -07:00
+++ 1.83/mysys/default.c	2006-08-29 14:10:38 -07:00
@@ -594,7 +594,7 @@
     end=convert_dirname(name, dir, NullS);
     if (dir[0] == FN_HOMELIB)		/* Add . to filenames in home */
       *end++='.';
-    strxmov(end,config_file,ext,NullS);
+    strxnmov(end, name + sizeof(name) - end, config_file, ext, NullS);
   }
   else
   {
@@ -874,7 +874,7 @@
 	end= convert_dirname(name, pos, NullS);
 	if (name[0] == FN_HOMELIB)	/* Add . to filenames in home */
 	  *end++='.';
-	strxmov(end, conf_file, *ext, " ", NullS);
+        strxnmov(end, name + sizeof(name) - end, conf_file, *ext, " ", NullS);
 	fputs(name,stdout);
       }
     }

--- 1.9/mysys/mf_loadpath.c	2006-08-29 14:10:38 -07:00
+++ 1.10/mysys/mf_loadpath.c	2006-08-29 14:10:38 -07:00
@@ -48,7 +48,7 @@
       VOID(strmov(buff,path));			/* Return org file name */
   }
   else
-    VOID(strxmov(buff,own_path_prefix,path,NullS));
+    VOID(strxnmov(buff, sizeof(buff), own_path_prefix, path, NullS));
   strmov(to,buff);
   DBUG_PRINT("exit",("to: %s",to));
   DBUG_RETURN(to);

--- 1.46/mysys/my_init.c	2006-08-29 14:10:38 -07:00
+++ 1.47/mysys/my_init.c	2006-08-29 14:10:38 -07:00
@@ -238,10 +238,10 @@
 
 /* Crea la stringa d'ambiente */
 
-void setEnvString(char *ret, const char *name, const char *value)
+void setEnvString(char *ret, uint ret_size, const char *name, const char *value)
 {
   DBUG_ENTER("setEnvString");
-  strxmov(ret, name,"=",value,NullS);
+  strxnmov(ret, ret_size, name, "=", value, NullS);
   DBUG_VOID_RETURN ;
 }
 
@@ -312,7 +312,8 @@
   {
     char *my_env;
     /* Crea la stringa d'ambiente */
-    setEnvString(EnvString, NameValueBuffer, DataValueBuffer) ;
+    setEnvString(EnvString, sizeof(EnvString), NameValueBuffer,
+                 DataValueBuffer) ;
 
     /* Inserisce i dati come variabili d'ambiente */
     my_env=strdup(EnvString);  /* variable for putenv must be allocated ! */

--- 1.36/mysys/raid.cc	2006-08-29 14:10:38 -07:00
+++ 1.37/mysys/raid.cc	2006-08-29 14:10:38 -07:00
@@ -370,7 +370,9 @@
 	  DBUG_RETURN(-1);
 	}
       }
-      strxmov(strend(new_end),"/",new_name+new_length,NullS);
+      strxnmov(strend(new_end),
+               new_name_buff + sizeof(new_name_buff) - new_end, "/",
+               new_name + new_length, NullS);
       sprintf(old_end,"%02x/%s",i, old_name+old_length);
       if (my_redel(old_name_buff, new_name_buff, MyFlags))
 	error=1;

--- 1.166/sql/ha_myisam.cc	2006-08-29 14:10:38 -07:00
+++ 1.167/sql/ha_myisam.cc	2006-08-29 14:10:38 -07:00
@@ -108,8 +108,8 @@
     my_message(ER_NOT_KEYFILE,msgbuf,MYF(MY_WME));
     return;
   }
-  length=(uint) (strxmov(name, param->db_name,".",param->table_name,NullS) -
-		 name);
+  length=(uint) (strxnmov(name, sizeof(name), param->db_name, ".",
+                          param->table_name,NullS) - name);
   protocol->prepare_for_resend();
   protocol->store(name, length, system_charset_info);
   protocol->store(param->op_name, system_charset_info);

--- 1.230/sql/item.cc	2006-08-29 14:10:38 -07:00
+++ 1.231/sql/item.cc	2006-08-29 14:10:38 -07:00
@@ -1601,17 +1601,17 @@
     return field_name ? field_name : name ? name : "tmp_field";
   if (db_name && db_name[0])
   {
-    tmp=(char*) sql_alloc((uint) strlen(db_name)+(uint) strlen(table_name)+
-			  (uint) strlen(field_name)+3);
-    strxmov(tmp,db_name,".",table_name,".",field_name,NullS);
+    uint length= strlen(db_name) + strlen(table_name) + strlen(field_name) + 3;
+    tmp=(char*) sql_alloc(length);
+    strxnmov(tmp, length, db_name, ".", table_name, ".", field_name, NullS);
   }
   else
   {
     if (table_name[0])
     {
-      tmp= (char*) sql_alloc((uint) strlen(table_name) +
-			     (uint) strlen(field_name) + 2);
-      strxmov(tmp, table_name, ".", field_name, NullS);
+      uint length= strlen(table_name) + strlen(field_name) + 2;
+      tmp= (char*) sql_alloc(length);
+      strxnmov(tmp, length, table_name, ".", field_name, NullS);
     }
     else
       tmp= (char*) field_name;

--- 1.191/sql/log.cc	2006-08-29 14:10:38 -07:00
+++ 1.192/sql/log.cc	2006-08-29 14:10:38 -07:00
@@ -2022,8 +2022,8 @@
     }
     if (!query)
     {
-      end=strxmov(buff, "# administrator command: ",
-                  command_name[thd->command], NullS);
+      end= strxnmov(buff, sizeof(buff), "# administrator command: ",
+                    command_name[thd->command], NullS);
       query_length=(ulong) (end-buff);
       query=buff;
     }
@@ -2277,7 +2277,7 @@
      On Windows is necessary a temporary file for to rename
      the current error file.
     */
-    strxmov(err_temp, err_renamed,"-tmp",NullS);
+    strxnmov(err_temp, sizeof(err_temp), err_renamed, "-tmp", NullS);
     (void) my_delete(err_temp, MYF(0)); 
     if (freopen(err_temp,"a+",stdout))
     {

--- 1.208/sql/log_event.cc	2006-08-29 14:10:38 -07:00
+++ 1.209/sql/log_event.cc	2006-08-29 14:10:38 -07:00
@@ -3524,6 +3524,7 @@
   char *buf= 0;
   uint val_offset= 4 + name_len;
   uint event_len= val_offset;
+  uint buf_len= 0;
 
   if (is_null)
   {
@@ -3557,7 +3558,8 @@
     } 
     case STRING_RESULT:
       /* 15 is for 'COLLATE' and other chars */
-      buf= my_malloc(event_len+val_len*2+1+2*MY_CS_NAME_SIZE+15, MYF(MY_WME));
+      buf_len= event_len + val_len * 2 + 1 + 2 * MY_CS_NAME_SIZE + 15;
+      buf= my_malloc(buf_len, MYF(MY_WME));
       CHARSET_INFO *cs;
       if (!(cs= get_charset(charset_number, MYF(0))))
       {
@@ -3566,10 +3568,11 @@
       }
       else
       {
-        char *p= strxmov(buf + val_offset, "_", cs->csname, " ", NullS);
+        char *p= strxnmov(buf + val_offset, buf_len - val_offset, "_",
+                          cs->csname, " ", NullS);
         p= str_to_hex(p, val, val_len);
-        p= strxmov(p, " COLLATE ", cs->name, NullS);
-        event_len= p-buf;
+        p= strxnmov(p, buf + buf_len - p, " COLLATE ", cs->name, NullS);
+        event_len= p - buf;
       }
       break;
     case ROW_RESULT:

--- 1.567/sql/mysqld.cc	2006-08-29 14:10:39 -07:00
+++ 1.568/sql/mysqld.cc	2006-08-29 14:10:39 -07:00
@@ -1918,8 +1918,8 @@
     NSS admin volumes directory.
   */
 
-  strxmov(path, (const char *) ADMIN_VOL_PATH, (const char *) volumeName,
-          NullS);
+  strxnmov(path, sizeof(path), (const char *) ADMIN_VOL_PATH,
+           (const char *) volumeName, NullS);
   if ((status= zOpen(rootKey, zNSS_TASK, zNSPACE_LONG|zMODE_UTF8,
                      (BYTE *) path, zRR_READ_ACCESS, &fileKey)) != zOK)
   {
@@ -4281,7 +4281,7 @@
       shared_memory_base_name is unique value for each server
       unique_part is unique value for each object (events and file-mapping)
   */
-  suffix_pos= strxmov(tmp,shared_memory_base_name,"_",NullS);
+  suffix_pos= strxnmov(tmp, sizeof(tmp), shared_memory_base_name, "_", NullS);
   strmov(suffix_pos, "CONNECT_REQUEST");
   if ((smem_event_connect_request= CreateEvent(sa_event,
                                                FALSE, FALSE, tmp)) == 0)
@@ -4340,8 +4340,8 @@
 	  unique_part is unique value for each object (events and file-mapping)
 	  number_of_connection is connection-number between server and client
     */
-    suffix_pos= strxmov(tmp,shared_memory_base_name,"_",connect_number_char,
-			 "_",NullS);
+    suffix_pos= strxnmov(tmp, sizeof(tmp), shared_memory_base_name, "_",
+                         connect_number_char, "_", NullS);
     strmov(suffix_pos, "DATA");
     if ((handle_client_file_map=
          CreateFileMapping(INVALID_HANDLE_VALUE, sa_mapping,
@@ -4430,8 +4430,8 @@
     if (errmsg)
     {
       char buff[180];
-      strxmov(buff, "Can't create shared memory connection: ", errmsg, ".",
-	      NullS);
+      strxnmov(buff, sizeof(buff), "Can't create shared memory connection: ",
+               errmsg, ".", NullS);
       sql_perror(buff);
     }
     if (handle_client_file_map)
@@ -4456,7 +4456,8 @@
   if (errmsg)
   {
     char buff[180];
-    strxmov(buff, "Can't create shared memory service: ", errmsg, ".", NullS);
+    strxnmov(buff, sizeof(buff), "Can't create shared memory service: ",
+             errmsg, ".", NullS);
     sql_perror(buff);
   }
   my_security_attr_free(sa_event);
@@ -7239,8 +7240,8 @@
 
 static void set_server_version(void)
 {
-  char *end= strxmov(server_version, MYSQL_SERVER_VERSION,
-                     MYSQL_SERVER_SUFFIX_STR, NullS);
+  char *end= strxnmov(server_version, sizeof(server_version),
+                      MYSQL_SERVER_VERSION, MYSQL_SERVER_SUFFIX_STR, NullS);
 #ifdef EMBEDDED_LIBRARY
   end= strmov(end, "-embedded");
 #endif

--- 1.204/sql/sql_acl.cc	2006-08-29 14:10:39 -07:00
+++ 1.205/sql/sql_acl.cc	2006-08-29 14:10:39 -07:00
@@ -2523,7 +2523,7 @@
   byte user_key[MAX_KEY_LENGTH];
   DBUG_ENTER("replace_table_table");
 
-  strxmov(grantor, thd->security_ctx->user, "@",
+  strxnmov(grantor, sizeof(grantor), thd->security_ctx->user, "@",
           thd->security_ctx->host_or_ip, NullS);
 
   /*
@@ -2646,7 +2646,7 @@
     DBUG_RETURN(-1);
   }
 
-  strxmov(grantor, thd->security_ctx->user, "@",
+  strxnmov(grantor, sizeof(grantor), thd->security_ctx->user, "@",
           thd->security_ctx->host_or_ip, NullS);
 
   /*
@@ -3969,7 +3969,7 @@
     char buff[1024];
     const char *command="";
     if (table)
-      strxmov(buff, table->db, ".", table->table_name, NullS);
+      strxnmov(buff, sizeof(buff), table->db, ".", table->table_name, NullS);
     if (want_access & EXECUTE_ACL)
       command= "execute";
     else if (want_access & ALTER_PROC_ACL)
@@ -4188,8 +4188,8 @@
   List<Item> field_list;
   field->name=buff;
   field->max_length=1024;
-  strxmov(buff,"Grants for ",lex_user->user.str,"@",
-	  lex_user->host.str,NullS);
+  strxnmov(buff, sizeof(buff), "Grants for ", lex_user->user.str, "@",
+           lex_user->host.str, NullS);
   field_list.push_back(field);
   if (protocol->send_fields(&field_list,
                             Protocol::SEND_NUM_ROWS | Protocol::SEND_EOF))
@@ -5880,7 +5880,7 @@
     if (!(want_access & GRANT_ACL))
       is_grantable= "NO";
 
-    strxmov(buff,"'",user,"'@'",host,"'",NullS);
+    strxnmov(buff, sizeof(buff), "'", user, "'@'", host, "'", NullS);
     if (!(want_access & ~GRANT_ACL))
       update_schema_privilege(table, buff, 0, 0, 0, 0,
                               STRING_WITH_LEN("USAGE"), is_grantable);
@@ -5943,7 +5943,7 @@
       {
         is_grantable= "NO";
       }
-      strxmov(buff,"'",user,"'@'",host,"'",NullS);
+      strxnmov(buff, sizeof(buff), "'", user, "'@'", host, "'", NullS);
       if (!(want_access & ~GRANT_ACL))
         update_schema_privilege(table, buff, acl_db->db, 0, 0,
                                 0, STRING_WITH_LEN("USAGE"), is_grantable);
@@ -6009,7 +6009,7 @@
       if (!(table_access & GRANT_ACL))
         is_grantable= "NO";
 
-      strxmov(buff, "'", user, "'@'", host, "'", NullS);
+      strxnmov(buff, sizeof(buff), "'", user, "'@'", host, "'", NullS);
       if (!test_access)
         update_schema_privilege(table, buff, grant_table->db, grant_table->tname,
                                 0, 0, STRING_WITH_LEN("USAGE"), is_grantable);
@@ -6071,7 +6071,7 @@
         is_grantable= "NO";
 
       ulong test_access= table_access & ~GRANT_ACL;
-      strxmov(buff, "'", user, "'@'", host, "'", NullS);
+      strxnmov(buff, sizeof(buff), "'", user, "'@'", host, "'", NullS);
       if (!test_access)
         continue;
       else

--- 1.348/sql/sql_base.cc	2006-08-29 14:10:39 -07:00
+++ 1.349/sql/sql_base.cc	2006-08-29 14:10:39 -07:00
@@ -1883,7 +1883,7 @@
   uint discover_retry_count= 0;
   DBUG_ENTER("open_unireg_entry");
 
-  strxmov(path, mysql_data_home, "/", db, "/", name, NullS);
+  strxnmov(path, sizeof(path), mysql_data_home, "/", db, "/", name, NullS);
   while ((error= openfrm(thd, path, alias,
 		         (uint) (HA_OPEN_KEYFILE | HA_OPEN_RNDFILE |
 			         HA_GET_INDEX | HA_TRY_READ_ONLY |
@@ -2006,8 +2006,9 @@
       uint query_buf_size= 20 + 2*NAME_LEN + 1;
       if ((query= (char*)my_malloc(query_buf_size,MYF(MY_WME))))
       {
-        end = strxmov(strmov(query, "DELETE FROM `"),
-                      db,"`.`",name,"`", NullS);
+        end= strmov(query, "DELETE FROM `");
+        end= strxnmov(end, query + query_buf_size - end, db, "`.`", name, "`",
+                      NullS);
         Query_log_event qinfo(thd, query, (ulong)(end-query), 0, FALSE);
         mysql_bin_log.write(&qinfo);
         my_free(query, MYF(0));

--- 1.131/sql/sql_db.cc	2006-08-29 14:10:39 -07:00
+++ 1.132/sql/sql_db.cc	2006-08-29 14:10:39 -07:00
@@ -453,7 +453,7 @@
 bool mysql_create_db(THD *thd, char *db, HA_CREATE_INFO *create_info,
                      bool silent)
 {
-  char	 path[FN_REFLEN+16];
+  char	 path[FN_REFLEN + 16];
   long result= 1;
   int error= 0;
   MY_STAT stat_info;
@@ -489,7 +489,7 @@
   VOID(pthread_mutex_lock(&LOCK_mysql_create_db));
 
   /* Check directory */
-  strxmov(path, mysql_data_home, "/", db, NullS);
+  strxnmov(path, sizeof(path), mysql_data_home, "/", db, NullS);
   path_len= unpack_dirname(path,path);    // Convert if not unix
   path[path_len-1]= 0;                    // Remove last '/' from path
 
@@ -552,8 +552,8 @@
     if (!thd->query)				// Only in replication
     {
       query= 	     path;
-      query_length= (uint) (strxmov(path,"create database `", db, "`", NullS) -
-			    path);
+      query_length= (uint) (strxnmov(path, sizeof(path), "create database `",
+                                     db, "`", NullS) - path);
     }
     else
     {
@@ -625,7 +625,8 @@
   VOID(pthread_mutex_lock(&LOCK_mysql_create_db));
 
   /* Check directory */
-  strxmov(path, mysql_data_home, "/", db, "/", MY_DB_OPT_FILE, NullS);
+  strxnmov(path, sizeof(path), mysql_data_home, "/", db, "/", MY_DB_OPT_FILE,
+           NullS);
   fn_format(path, path, "", "", MYF(MY_UNPACK_FILENAME));
   if ((error=write_db_opt(thd, path, create_info)))
     goto exit;
@@ -758,8 +759,8 @@
     {
       /* The client used the old obsolete mysql_drop_db() call */
       query= path;
-      query_length= (uint) (strxmov(path, "drop database `", db, "`",
-                                     NullS) - path);
+      query_length= (uint) (strxnmov(path, sizeof(path), "drop database `", db,
+                                     "`", NullS) - path);
     }
     else
     {
@@ -882,7 +883,7 @@
       String *dir;
       uint length;
 
-      strxmov(newpath,org_path,"/",file->name,NullS);
+      strxnmov(newpath, sizeof(newpath), org_path, "/", file->name, NullS);
       length= unpack_filename(newpath,newpath);
       if ((new_dirp = my_dir(newpath,MYF(MY_DONT_SORT))))
       {
@@ -905,7 +906,7 @@
       /* .frm archive */
       char newpath[FN_REFLEN];
       MY_DIR *new_dirp;
-      strxmov(newpath, org_path, "/", "arc", NullS);
+      strxnmov(newpath, sizeof(newpath), org_path, "/", "arc", NullS);
       (void) unpack_filename(newpath, newpath);
       if ((new_dirp = my_dir(newpath, MYF(MY_DONT_SORT))))
       {
@@ -944,7 +945,7 @@
     }
     else
     {
-      strxmov(filePath, org_path, "/", file->name, NullS);
+      strxnmov(filePath, sizeof(filePath), org_path, "/", file->name, NullS);
       if (my_delete_with_symlink(filePath,MYF(MY_WME)))
       {
 	goto err;
@@ -1096,7 +1097,7 @@
       found_other_files++;
       continue;
     }
-    strxmov(filePath, org_path, "/", file->name, NullS);
+    strxnmov(filePath, sizeof(filePath), org_path, "/", file->name, NullS);
     if (my_delete_with_symlink(filePath,MYF(MY_WME)))
     {
       goto err;

--- 1.563/sql/sql_parse.cc	2006-08-29 14:10:39 -07:00
+++ 1.564/sql/sql_parse.cc	2006-08-29 14:10:39 -07:00
@@ -5756,7 +5756,7 @@
   */
   if ((var= get_system_var(thd, OPT_SESSION, tmp, null_lex_string)))
   {
-    end= strxmov(buff, "@@session.", var_name, NullS);
+    end= strxnmov(buff, sizeof(buff), "@@session.", var_name, NullS);
     var->set_name(buff, end-buff, system_charset_info);
     add_item_to_list(thd, var);
   }
@@ -6892,6 +6892,7 @@
 			       const char *table_name)
 {
   char buff[FN_REFLEN],*ptr, *end;
+  uint length;
   if (!*filename_ptr)
     return 0;					// nothing to do
 
@@ -6905,10 +6906,11 @@
   /* Fix is using unix filename format on dos */
   strmov(buff,*filename_ptr);
   end=convert_dirname(buff, *filename_ptr, NullS);
-  if (!(ptr=thd->alloc((uint) (end-buff)+(uint) strlen(table_name)+1)))
+  length= end - buff + strlen(table_name) + 1;
+  if (!(ptr=thd->alloc(length)))
     return 1;					// End of memory
   *filename_ptr=ptr;
-  strxmov(ptr,buff,table_name,NullS);
+  strxnmov(ptr, length, buff, table_name, NullS);
   return 0;
 }
 

--- 1.328/sql/sql_show.cc	2006-08-29 14:10:39 -07:00
+++ 1.329/sql/sql_show.cc	2006-08-29 14:10:39 -07:00
@@ -2218,7 +2218,8 @@
       }
       else
       {
-        strxmov(path, mysql_data_home, "/", base_name, NullS);
+        strxnmov(path, sizeof(path), mysql_data_home, "/", base_name,
+                 NullS);
         end= path + (len= unpack_dirname(path,path));
         len= FN_LEN - len;
         find_files_result res= find_files(thd, &files, base_name, 
@@ -2560,9 +2561,9 @@
     if (share->db_create_options & HA_OPTION_DELAY_KEY_WRITE)
       ptr=strmov(ptr," delay_key_write=1");
     if (share->row_type != ROW_TYPE_DEFAULT)
-      ptr=strxmov(ptr, " row_format=", 
-                  ha_row_type[(uint) share->row_type],
-                  NullS);
+      ptr=strxnmov(ptr, option_buff + sizeof(option_buff) - ptr,
+                   " row_format=", ha_row_type[(uint) share->row_type],
+                   NullS);
     if (file->raid_type)
     {
       char buff[100];
@@ -2994,7 +2995,7 @@
   Open_tables_state open_tables_state_backup;
   DBUG_ENTER("fill_schema_proc");
 
-  strxmov(definer, thd->security_ctx->priv_user, "@",
+  strxnmov(definer, sizeof(definer), thd->security_ctx->priv_user, "@",
           thd->security_ctx->priv_host, NullS);
   /* We use this TABLE_LIST instance only for checking of privileges. */
   bzero((char*) &proc_tables,sizeof(proc_tables));
@@ -3175,8 +3176,9 @@
       table->field[5]->store(STRING_WITH_LEN("YES"), cs);
     else
       table->field[5]->store(STRING_WITH_LEN("NO"), cs);
-    definer_len= (strxmov(definer, tables->definer.user.str, "@",
-                          tables->definer.host.str, NullS) - definer);
+    definer_len= (strxnmov(definer, sizeof(definer),
+                           tables->definer.user.str, "@",
+                           tables->definer.host.str, NullS) - definer);
     table->field[6]->store(definer, definer_len, cs);
     if (tables->view_suid)
       table->field[7]->store(STRING_WITH_LEN("DEFINER"), cs);

--- 1.320/sql/sql_table.cc	2006-08-29 14:10:39 -07:00
+++ 1.321/sql/sql_table.cc	2006-08-29 14:10:39 -07:00
@@ -2059,7 +2059,8 @@
   if (!ext[0] || !ext[1])
     goto end;					// No data file
 
-  strxmov(from, table->s->path, ext[1], NullS);	// Name of data file
+  strxnmov(from, sizeof(from), table->s->path, ext[1], NullS);
+     // Name of data file
   if (!my_stat(from, &stat_info, MYF(0)))
     goto end;				// Can't use USE_FRM flag
 
@@ -2176,7 +2177,7 @@
     char* db = table->db;
     bool fatal_error=0;
 
-    strxmov(table_name, db, ".", table->table_name, NullS);
+    strxnmov(table_name, sizeof(table_name), db, ".", table->table_name, NullS);
     thd->open_options|= extra_open_options;
     table->lock_type= lock_type;
     /* open only one table from local list of command */
@@ -2238,7 +2239,7 @@
       if (table->view &&
           view_checksum(thd, table) == HA_ADMIN_WRONG_CHECKSUM)
       {
-        strxmov(buf, err_msg, "; ", ER(ER_VIEW_CHECKSUM), NullS);
+        strxnmov(buf, sizeof(buf), err_msg, "; ", ER(ER_VIEW_CHECKSUM), NullS);
         err_msg= (const char *)buf;
       }
       protocol->store(err_msg, system_charset_info);
@@ -2708,11 +2709,12 @@
     goto err;
 
   if ((tmp_table= find_temporary_table(thd, src_db, src_table)))
-    strxmov(src_path, (*tmp_table)->s->path, reg_ext, NullS);
+    strxnmov(src_path, sizeof(src_path), (*tmp_table)->s->path, reg_ext,
+             NullS);
   else
   {
-    strxmov(src_path, mysql_data_home, "/", src_db, "/", src_table,
-	    reg_ext, NullS);
+    strxnmov(src_path, sizeof(src_path), mysql_data_home, "/", src_db,
+             "/", src_table, reg_ext, NullS);
     /* Resolve symlinks (for windows) */
     fn_format(src_path, src_path, "", "", MYF(MY_UNPACK_FILENAME));
     if (lower_case_table_names)
@@ -2752,8 +2754,8 @@
   }
   else
   {
-    strxmov(dst_path, mysql_data_home, "/", db, "/", table_name,
-	    reg_ext, NullS);
+    strxnmov(dst_path, sizeof(dst_path), mysql_data_home, "/", db, "/",
+             table_name, reg_ext, NullS);
     fn_format(dst_path, dst_path, "", "", MYF(MY_UNPACK_FILENAME));
     if (!access(dst_path, F_OK))
       goto table_exists;
@@ -4189,7 +4191,8 @@
     char table_name[NAME_LEN*2+2];
     TABLE *t;
 
-    strxmov(table_name, table->db ,".", table->table_name, NullS);
+    strxnmov(table_name, sizeof(table_name), table->db, ".", table->table_name,
+             NullS);
 
     t= table->table= open_ltable(thd, table, TL_READ);
     thd->clear_error();			// these errors shouldn't get client

--- 1.231/sql/table.cc	2006-08-29 14:10:39 -07:00
+++ 1.232/sql/table.cc	2006-08-29 14:10:39 -07:00
@@ -1132,10 +1132,10 @@
   if (n_length == 1 )
   {						/* First name */
     length++;
-    VOID(strxmov(buff,"/",newname,"/",NullS));
+    VOID(strxnmov(buff, sizeof(buff), "/", newname, "/", NullS));
   }
   else
-    VOID(strxmov(buff,newname,"/",NullS)); /* purecov: inspected */
+    VOID(strxnmov(buff, sizeof(buff), newname, "/", NullS)); /* purecov: inspected */
   VOID(my_seek(file,63L+(ulong) n_length,MY_SEEK_SET,MYF(0)));
   if (my_write(file,(byte*) buff,(uint) length+1,MYF(MY_NABP+MY_WME)) ||
       (names && my_write(file,(byte*) (*formnames->type_names+n_length-1),
@@ -1506,10 +1506,10 @@
 int
 rename_file_ext(const char * from,const char * to,const char * ext)
 {
-  char from_b[FN_REFLEN],to_b[FN_REFLEN];
-  VOID(strxmov(from_b,from,ext,NullS));
-  VOID(strxmov(to_b,to,ext,NullS));
-  return (my_rename(from_b,to_b,MYF(MY_WME)));
+  char from_b[FN_REFLEN], to_b[FN_REFLEN];
+  VOID(strxnmov(from_b, sizeof(from_b), from, ext, NullS));
+  VOID(strxnmov(to_b, sizeof(to_b), to, ext, NullS));
+  return (my_rename(from_b, to_b, MYF(MY_WME)));
 }
 
 

--- 1.54/sql/sql_trigger.cc	2006-08-29 14:10:39 -07:00
+++ 1.55/sql/sql_trigger.cc	2006-08-29 14:10:39 -07:00
@@ -533,8 +533,9 @@
     *definer_host= lex->definer->host;
 
     trg_definer->str= trg_definer_holder;
-    trg_definer->length= strxmov(trg_definer->str, definer_user->str, "@",
-                                 definer_host->str, NullS) - trg_definer->str;
+    trg_definer->length= strxnmov(trg_definer->str, sizeof(trg_definer_holder),
+                                  definer_user->str, "@", definer_host->str,
+                                  NullS) - trg_definer->str;
   }
   else
   {
@@ -927,7 +928,8 @@
               alloc_root(&table->mem_root, triggers->sroutines_key.length)))
         DBUG_RETURN(1);
       triggers->sroutines_key.str[0]= TYPE_ENUM_TRIGGER;
-      strxmov(triggers->sroutines_key.str+1, db, ".", table_name, NullS);
+      strxnmov(triggers->sroutines_key.str + 1,
+               triggers->sroutines_key.length - 1, db, ".", table_name, NullS);
 
       /*
         TODO: This could be avoided if there is no triggers

--- 1.96/sql-common/client.c	2006-08-29 14:10:39 -07:00
+++ 1.97/sql-common/client.c	2006-08-29 14:10:39 -07:00
@@ -417,7 +417,8 @@
     shared_memory_base_name is unique value for each server
     unique_part is uniquel value for each object (events and file-mapping)
   */
-  suffix_pos = strxmov(tmp,shared_memory_base_name,"_",NullS);
+  suffix_pos= strxnmov(tmp, sizeof(tmp), shared_memory_base_name, "_",
+                       NullS);
   strmov(suffix_pos, "CONNECT_REQUEST");
   if (!(event_connect_request= OpenEvent(event_access_rights, FALSE, tmp)))
   {
@@ -471,8 +472,8 @@
     unique_part is uniquel value for each object (events and file-mapping)
     number_of_connection is number of connection between server and client
   */
-  suffix_pos = strxmov(tmp,shared_memory_base_name,"_",connect_number_char,
-		       "_",NullS);
+  suffix_pos= strxnmov(tmp, sizeof(tmp), shared_memory_base_name, "_",
+                       connect_number_char, "_", NullS);
   strmov(suffix_pos, "DATA");
   if ((handle_file_map = OpenFileMapping(FILE_MAP_WRITE,FALSE,tmp)) == NULL)
   {

--- 1.57/client/mysqlcheck.c	2006-08-29 14:10:39 -07:00
+++ 1.58/client/mysqlcheck.c	2006-08-29 14:10:39 -07:00
@@ -181,7 +181,7 @@
 static void DBerror(MYSQL *mysql, const char *when);
 static void safe_exit(int error);
 static void print_result();
-static char *fix_table_name(char *dest, char *src);
+static char *fix_table_name(char *dest, uint dest_alloc_size, char *src);
 int what_to_do = 0;
 
 #include <help_start.h>
@@ -409,18 +409,21 @@
     */	  
     char *table_names_comma_sep, *end;
     int i, tot_length = 0;
+    uint length;
 
     for (i = 0; i < tables; i++)
       tot_length += strlen(*(table_names + i)) + 4;
 
+    length= sizeof(char) * tot_length + 4;
     if (!(table_names_comma_sep = (char *)
-	  my_malloc((sizeof(char) * tot_length) + 4, MYF(MY_WME))))
+          my_malloc(length, MYF(MY_WME))))
       return 1;
 
     for (end = table_names_comma_sep + 1; tables > 0;
 	 tables--, table_names++)
     {
-      end= fix_table_name(end, *table_names);
+      end= fix_table_name(end, table_names_comma_sep + length - end,
+                          *table_names);
       *end++= ',';
     }
     *--end = 0;
@@ -434,8 +437,9 @@
 } /* process_selected_tables */
 
 
-static char *fix_table_name(char *dest, char *src)
+static char *fix_table_name(char *dest, uint dest_alloc_size, char *src)
 {
+  char *start= dest; 
   char *db_sep;
 
   *dest++= '`';
@@ -445,7 +449,7 @@
     dest= strmov(dest, "`.`");
     src= db_sep + 1;
   }
-  dest= strxmov(dest, src, "`", NullS);
+  dest= strxnmov(dest, start + dest_alloc_size - dest, src, "`", NullS);
   return dest;
 }
 
@@ -471,13 +475,15 @@
      */
 
     char *tables, *end;
-    uint tot_length = 0;
+    uint tot_length= 0;
+    uint length;
 
     while ((row = mysql_fetch_row(res)))
       tot_length += strlen(row[0]) + 4;
     mysql_data_seek(res, 0);
 
-    if (!(tables=(char *) my_malloc(sizeof(char)*tot_length+4, MYF(MY_WME))))
+    length= sizeof(char) * tot_length + 4;
+    if (!(tables=(char *) my_malloc(length, MYF(MY_WME))))
     {
       mysql_free_result(res);
       return 1;
@@ -487,7 +493,7 @@
       /* Skip tables with an engine of NULL (probably a view). */
       if (row[1])
       {
-        end= fix_table_name(end, row[0]);
+        end= fix_table_name(end, tables + length - end, row[0]);
         *end++= ',';
       }
     }
@@ -529,6 +535,7 @@
   char *query, *end, options[100], message[100];
   uint query_length= 0;
   const char *op = 0;
+  uint alloc_length;
 
   options[0] = 0;
   end = options;
@@ -556,7 +563,8 @@
     break;
   }
 
-  if (!(query =(char *) my_malloc((sizeof(char)*(length+110)), MYF(MY_WME))))
+  alloc_length= sizeof(char) * (length + 110);
+  if (!(query= (char *) my_malloc(alloc_length, MYF(MY_WME))))
     return 1;
   if (opt_all_in_1)
   {
@@ -569,8 +577,8 @@
     char *ptr;
 
     ptr= strmov(strmov(query, op), " TABLE ");
-    ptr= fix_table_name(ptr, tables);
-    ptr= strxmov(ptr, " ", options, NullS);
+    ptr= fix_table_name(ptr, query + alloc_length - ptr, tables);
+    ptr= strxnmov(ptr, query + alloc_length - ptr, " ", options, NullS);
     query_length= (uint) (ptr - query);
   }
   if (mysql_real_query(sock, query, query_length))

--- 1.241/client/mysqltest.c	2006-08-29 14:10:39 -07:00
+++ 1.242/client/mysqltest.c	2006-08-29 14:10:39 -07:00
@@ -694,7 +694,7 @@
 
   if (!test_if_hard_path(fname))
   {
-    strxmov(eval_file, opt_basedir, fname, NullS);
+    strxnmov(eval_file, sizeof(eval_file), opt_basedir, fname, NullS);
     fn_format(eval_file, eval_file,"","",4);
   }
   else
@@ -889,7 +889,7 @@
   DBUG_PRINT("enter", ("name: %s", name));
   if (!test_if_hard_path(name))
   {
-    strxmov(buff, opt_basedir, name, NullS);
+    strxnmov(buff, sizeof(buff), opt_basedir, name, NullS);
     name=buff;
   }
   fn_format(buff,name,"","",4);
@@ -3022,7 +3022,7 @@
       char buff[FN_REFLEN];
       if (!test_if_hard_path(argument))
       {
-	strxmov(buff, opt_basedir, argument, NullS);
+        strxnmov(buff, sizeof(buff), opt_basedir, argument, NullS);
 	argument= buff;
       }
       fn_format(buff, argument, "", "", 4);
@@ -3039,7 +3039,7 @@
       static char buff[FN_REFLEN];
       if (!test_if_hard_path(argument))
       {
-	strxmov(buff, opt_basedir, argument, NullS);
+        strxnmov(buff, sizeof(buff), opt_basedir, argument, NullS);
 	argument= buff;
       }
       fn_format(buff, argument, "", "", 4);
@@ -3133,7 +3133,7 @@
   char buff[FN_REFLEN];
   if (!test_if_hard_path(fname))
   {
-    strxmov(buff, opt_basedir, fname, NullS);
+    strxnmov(buff, sizeof(buff), opt_basedir, fname, NullS);
     fname= buff;
   }
   fn_format(buff,fname,"","",4);
@@ -4983,7 +4983,7 @@
 
   if (!test_if_hard_path(name))
   {
-    strxmov(buff, opt_basedir, name, NullS);
+    strxnmov(buff, sizeof(buff), opt_basedir, name, NullS);
     name=buff;
   }
   fn_format(buff,name,"","",4);

--- 1.115/sql/sp.cc	2006-08-29 14:10:39 -07:00
+++ 1.116/sql/sp.cc	2006-08-29 14:10:39 -07:00
@@ -531,7 +531,7 @@
     restore_record(table, s->default_values); // Get default values for fields
 
     /* NOTE: all needed privilege checks have been already done. */
-    strxmov(definer, thd->lex->definer->user.str, "@",
+    strxnmov(definer, sizeof(definer), thd->lex->definer->user.str, "@",
             thd->lex->definer->host.str, NullS);
 
     if (table->s->fields != MYSQL_PROC_FIELD_COUNT)
@@ -1013,7 +1013,7 @@
       DBUG_RETURN(0);
     }
 
-    strxmov(definer, sp->m_definer_user.str, "@",
+    strxnmov(definer, sizeof(definer), sp->m_definer_user.str, "@",
             sp->m_definer_host.str, NullS);
     if (type == TYPE_ENUM_FUNCTION)
     {

--- 1.204/tests/mysql_client_test.c	2006-08-29 14:10:39 -07:00
+++ 1.205/tests/mysql_client_test.c	2006-08-29 14:10:39 -07:00
@@ -309,12 +309,13 @@
             (ulong) mysql_get_server_version(mysql));
     fprintf(stdout, "\n Creating a test database '%s' ...", current_db);
   }
-  strxmov(query, "CREATE DATABASE IF NOT EXISTS ", current_db, NullS);
+  strxnmov(query, sizeof(query), "CREATE DATABASE IF NOT EXISTS ",
+           current_db, NullS);
 
   rc= mysql_query(mysql, query);
   myquery(rc);
 
-  strxmov(query, "USE ", current_db, NullS);
+  strxnmov(query, sizeof(query), "USE ", current_db, NullS);
   rc= mysql_query(mysql, query);
   myquery(rc);
   have_innodb= check_have_innodb(mysql);
@@ -336,7 +337,8 @@
   {
     if (!opt_silent)
       fprintf(stdout, "\n dropping the test database '%s' ...", current_db);
-    strxmov(query, "DROP DATABASE IF EXISTS ", current_db, NullS);
+    strxnmov(query, sizeof(query), "DROP DATABASE IF EXISTS ",
+             current_db, NullS);
 
     mysql_query(mysql, query);
     if (!opt_silent)
@@ -668,7 +670,8 @@
 
   if (table && col)
   {
-    strxmov(query, "SELECT ", col, " FROM ", table, " LIMIT 1", NullS);
+    strxnmov(query, sizeof(query), "SELECT ", col, " FROM ", table,
+             " LIMIT 1", NullS);
     if (!opt_silent)
       fprintf(stdout, "\n %s", query);
     rc= mysql_query(mysql, query);
@@ -1584,7 +1587,8 @@
   myquery(rc);
 
   /* insert by prepare */
-  strxmov(query, "INSERT INTO my_prepare VALUES(?, ?, ?, ?, ?, ?, ?)", NullS);
+  strxnmov(query, sizeof(query),
+           "INSERT INTO my_prepare VALUES(?, ?, ?, ?, ?, ?, ?)", NullS);
   stmt= mysql_simple_prepare(mysql, query);
   check_stmt(stmt);
 
@@ -2692,7 +2696,8 @@
   stmt= mysql_simple_prepare(mysql, "show tables from mysql like ?");
   check_stmt_r(stmt);
 
-  strxmov(query, "show tables from ", current_db, " like \'test_show\'", NullS);
+  strxnmov(query, sizeof(query), "show tables from ", current_db,
+           " like \'test_show\'", NullS);
   stmt= mysql_simple_prepare(mysql, query);
   check_stmt(stmt);
 
@@ -2971,7 +2976,7 @@
   verify_col_data("test_long_data_str", "LENGTH(longstr)", data);
   data[0]= '\0';
   while (i--)
-   strxmov(data, data, "MySQL", NullS);
+   strxnmov(data, sizeof(data), data, "MySQL", NullS);
   verify_col_data("test_long_data_str", "longstr", data);
 
   rc= mysql_query(mysql, "DROP TABLE test_long_data_str");
@@ -7166,9 +7171,9 @@
   rc= mysql_query(mysql, "CREATE TABLE test_grant(a tinyint primary key auto_increment)");
   myquery(rc);
 
-  strxmov(query, "GRANT INSERT, UPDATE, SELECT ON ", current_db,
-                ".test_grant TO 'test_grant'@",
-                opt_host ? opt_host : "'localhost'", NullS);
+  strxnmov(query, sizeof(query), "GRANT INSERT, UPDATE, SELECT ON ",
+           current_db, ".test_grant TO 'test_grant'@",
+           opt_host ? opt_host : "'localhost'", NullS);
 
   if (mysql_query(mysql, query))
   {
@@ -7297,7 +7302,8 @@
   rc= mysql_stmt_fetch(stmt);
   DIE_UNLESS(rc == MYSQL_NO_DATA);
 
-  strxmov(test_frm, data_dir, "/", current_db, "/", "test_frm_bug.frm", NullS);
+  strxnmov(test_frm, sizeof(test_frm), data_dir, "/", current_db, "/",
+           "test_frm_bug.frm", NullS);
 
   if (!opt_silent)
     fprintf(stdout, "\n test_frm: %s", test_frm);
@@ -7612,7 +7618,7 @@
   rc= mysql_query(mysql, "delete from mysql.db where Db='test_drop_temp_db'");
   myquery(rc);
 
-  strxmov(query, "GRANT SELECT, USAGE, DROP ON test_drop_temp_db.* TO test_temp@",
+  strxnmov(query, sizeof(query), "GRANT SELECT, USAGE, DROP ON test_drop_temp_db.* TO test_temp@",
                 opt_host ? opt_host : "localhost", NullS);
 
   if (mysql_query(mysql, query))
@@ -8398,11 +8404,11 @@
   rc= mysql_query(mysql, "drop table if exists t_mem_overun");
   myquery(rc);
 
-  strxmov(buffer, "create table t_mem_overun(", NullS);
+  strxnmov(buffer, sizeof(buffer), "create table t_mem_overun(", NullS);
   for (i= 0; i < 1000; i++)
   {
     sprintf(field, "c%d int", i);
-    strxmov(buffer, buffer, field, ", ", NullS);
+    strxnmov(buffer, sizeof(buffer), buffer, field, ", ", NullS);
   }
   length= strlen(buffer);
   buffer[length-2]= ')';
@@ -8411,10 +8417,11 @@
   rc= mysql_real_query(mysql, buffer, length);
   myquery(rc);
 
-  strxmov(buffer, "insert into t_mem_overun values(", NullS);
+  strxnmov(buffer, sizeof(buffer), "insert into t_mem_overun values(",
+           NullS);
   for (i= 0; i < 1000; i++)
   {
-    strxmov(buffer, buffer, "1, ", NullS);
+    strxnmov(buffer, sizeof(buffer), buffer, "1, ", NullS);
   }
   length= strlen(buffer);
   buffer[length-2]= ')';
Thread
bk commit into 5.0 tree (igreenhoe:1.2255) BUG#16864Ian Greenhoe29 Aug