@@ -49,7 +49,7 @@ const char *VER= "14.14";
4949#define MAX_COLUMN_LENGTH 1024
5050
5151/* Buffer to hold 'version' and 'version_comment' */
52- # define MAX_SERVER_VERSION_LENGTH 128
52+ static char *server_version= NULL ;
5353
5454/* Array of options to pass to libemysqld */
5555#define MAX_SERVER_ARGS 64
@@ -115,6 +115,8 @@ extern "C" {
115115#define PROMPT_CHAR ' \\ '
116116#define DEFAULT_DELIMITER " ;"
117117
118+ #define MAX_BATCH_BUFFER_SIZE (1024L * 1024L )
119+
118120typedef struct st_status
119121{
120122 int exit_status;
@@ -246,11 +248,11 @@ typedef struct {
246248
247249static COMMANDS commands[] = {
248250 { " ?" , ' ?' , com_help, 1 , " Synonym for `help'." },
249- { " clear" , ' c' , com_clear, 0 , " Clear command ." },
251+ { " clear" , ' c' , com_clear, 0 , " Clear the current input statement ." },
250252 { " connect" ,' r' , com_connect,1 ,
251253 " Reconnect to the server. Optional arguments are db and host." },
252254 { " delimiter" , ' d' , com_delimiter, 1 ,
253- " Set statement delimiter. NOTE: Takes the rest of the line as new delimiter. " },
255+ " Set statement delimiter." },
254256#ifdef USE_POPEN
255257 { " edit" , ' e' , com_edit, 0 , " Edit command with $EDITOR." },
256258#endif
@@ -1045,7 +1047,7 @@ static void fix_history(String *final_command);
10451047
10461048static COMMANDS *find_command (char *name,char cmd_name);
10471049static bool add_line (String &buffer,char *line,char *in_string,
1048- bool *ml_comment);
1050+ bool *ml_comment, bool truncated );
10491051static void remove_cntrl (String &buffer);
10501052static void print_table_data (MYSQL_RES *result);
10511053static void print_table_data_html (MYSQL_RES *result);
@@ -1117,7 +1119,7 @@ int main(int argc,char *argv[])
11171119 exit (1 );
11181120 }
11191121 if (status.batch && !status.line_buff &&
1120- !(status.line_buff =batch_readline_init (opt_max_allowed_packet+ 512 , stdin)))
1122+ !(status.line_buff = batch_readline_init (MAX_BATCH_BUFFER_SIZE, stdin)))
11211123 {
11221124 free_defaults (defaults_argv);
11231125 my_end (0 );
@@ -1198,7 +1200,7 @@ int main(int argc,char *argv[])
11981200#endif
11991201 sprintf (buff, " %s" ,
12001202#ifndef NOT_YET
1201- " Type 'help;' or '\\ h' for help. Type '\\ c' to clear the buffer .\n " );
1203+ " Type 'help;' or '\\ h' for help. Type '\\ c' to clear the current input statement .\n " );
12021204#else
12031205 " Type 'help [[%]function name[%]]' to get help on usage of function.\n " );
12041206#endif
@@ -1234,6 +1236,7 @@ sig_handler mysql_end(int sig)
12341236 glob_buffer.free ();
12351237 old_buffer.free ();
12361238 processed_prompt.free ();
1239+ my_free (server_version,MYF (MY_ALLOW_ZERO_PTR));
12371240 my_free (opt_password,MYF (MY_ALLOW_ZERO_PTR));
12381241 my_free (opt_mysql_unix_port,MYF (MY_ALLOW_ZERO_PTR));
12391242 my_free (histfile,MYF (MY_ALLOW_ZERO_PTR));
@@ -1810,13 +1813,14 @@ static int read_and_execute(bool interactive)
18101813 ulong line_number=0 ;
18111814 bool ml_comment= 0 ;
18121815 COMMANDS *com;
1816+ bool truncated= 0 ;
18131817 status.exit_status =1 ;
18141818
18151819 for (;;)
18161820 {
18171821 if (!interactive)
18181822 {
1819- line=batch_readline (status.line_buff );
1823+ line=batch_readline (status.line_buff , &truncated );
18201824 /*
18211825 Skip UTF8 Byte Order Marker (BOM) 0xEFBBBF.
18221826 Editors like "notepad" put this marker in
@@ -1913,7 +1917,7 @@ static int read_and_execute(bool interactive)
19131917#endif
19141918 continue ;
19151919 }
1916- if (add_line (glob_buffer,line,&in_string,&ml_comment))
1920+ if (add_line (glob_buffer,line,&in_string,&ml_comment, truncated ))
19171921 break ;
19181922 }
19191923 /* if in batch mode, send last query even if it doesn't end with \g or go */
@@ -1999,7 +2003,7 @@ static COMMANDS *find_command(char *name,char cmd_char)
19992003
20002004
20012005static bool add_line (String &buffer,char *line,char *in_string,
2002- bool *ml_comment)
2006+ bool *ml_comment, bool truncated )
20032007{
20042008 uchar inchar;
20052009 char buff[80 ], *pos, *out;
@@ -2245,8 +2249,23 @@ static bool add_line(String &buffer,char *line,char *in_string,
22452249 }
22462250 if (out != line || !buffer.is_empty ())
22472251 {
2248- *out++=' \n ' ;
22492252 uint length=(uint) (out-line);
2253+
2254+ if (!truncated &&
2255+ (length < 9 ||
2256+ my_strnncoll (charset_info,
2257+ (uchar *)line, 9 , (const uchar *) " delimiter" , 9 )))
2258+ {
2259+ /*
2260+ Don't add a new line in case there's a DELIMITER command to be
2261+ added to the glob buffer (e.g. on processing a line like
2262+ "<command>;DELIMITER <non-eof>") : similar to how a new line is
2263+ not added in the case when the DELIMITER is the first command
2264+ entered with an empty glob buffer.
2265+ */
2266+ *out++=' \n ' ;
2267+ length++;
2268+ }
22502269 if (buffer.length () + length >= buffer.alloced_length ())
22512270 buffer.realloc (buffer.length ()+length+IO_SIZE);
22522271 if ((!*ml_comment || preserve_comments) && buffer.append (line, length))
@@ -2648,7 +2667,7 @@ static void get_current_db()
26482667 (res= mysql_use_result (&mysql)))
26492668 {
26502669 MYSQL_ROW row= mysql_fetch_row (res);
2651- if (row[0 ])
2670+ if (row && row [0 ])
26522671 current_db= my_strdup (row[0 ], MYF (MY_WME));
26532672 mysql_free_result (res);
26542673 }
@@ -2855,7 +2874,7 @@ com_charset(String *buffer __attribute__((unused)), char *line)
28552874 param= get_arg (buff, 0 );
28562875 if (!param || !*param)
28572876 {
2858- return put_info (" Usage: \\ C char_setname | charset charset_name" ,
2877+ return put_info (" Usage: \\ C charset_name | charset charset_name" ,
28592878 INFO_ERROR, 0 );
28602879 }
28612880 new_cs= get_charset_by_csname (param, MY_CS_PRIMARY, MYF (MY_WME));
@@ -3907,7 +3926,7 @@ static int com_source(String *buffer, char *line)
39073926 return put_info (buff, INFO_ERROR, 0 );
39083927 }
39093928
3910- if (!(line_buff=batch_readline_init (opt_max_allowed_packet+ 512 , sql_file)))
3929+ if (!(line_buff= batch_readline_init (MAX_BATCH_BUFFER_SIZE, sql_file)))
39113930 {
39123931 my_fclose (sql_file,MYF (0 ));
39133932 return put_info (" Can't initialize batch_readline" , INFO_ERROR, 0 );
@@ -4347,34 +4366,44 @@ select_limit, max_join_size);
43474366static const char *
43484367server_version_string (MYSQL *con)
43494368{
4350- static char buf[MAX_SERVER_VERSION_LENGTH] = " " ;
4351-
43524369 /* Only one thread calls this, so no synchronization is needed */
4353- if (buf[ 0 ] == ' \0 ' )
4370+ if (server_version == NULL )
43544371 {
4355- char *bufp = buf;
43564372 MYSQL_RES *result;
43574373
4358- bufp= strnmov (buf, mysql_get_server_info (con), sizeof buf);
4359-
43604374 /* "limit 1" is protection against SQL_SELECT_LIMIT=0 */
43614375 if (!mysql_query (con, " select @@version_comment limit 1" ) &&
43624376 (result = mysql_use_result (con)))
43634377 {
43644378 MYSQL_ROW cur = mysql_fetch_row (result);
43654379 if (cur && cur[0 ])
43664380 {
4367- bufp = strxnmov (bufp, sizeof buf - (bufp - buf), " " , cur[0 ], NullS);
4381+ /* version, space, comment, \0 */
4382+ size_t len= strlen (mysql_get_server_info (con)) + strlen (cur[0 ]) + 2 ;
4383+
4384+ if ((server_version= (char *) my_malloc (len, MYF (MY_WME))))
4385+ {
4386+ char *bufp;
4387+ bufp = strmov (server_version, mysql_get_server_info (con));
4388+ bufp = strmov (bufp, " " );
4389+ (void ) strmov (bufp, cur[0 ]);
4390+ }
43684391 }
43694392 mysql_free_result (result);
43704393 }
43714394
4372- /* str*nmov doesn't guarantee NUL-termination */
4373- if (bufp == buf + sizeof buf)
4374- buf[sizeof buf - 1 ] = ' \0 ' ;
4395+ /*
4396+ If for some reason we didn't get a version_comment, we'll
4397+ keep things simple.
4398+ */
4399+
4400+ if (server_version == NULL )
4401+ {
4402+ server_version= strdup (mysql_get_server_info (con));
4403+ }
43754404 }
43764405
4377- return buf ;
4406+ return server_version ? server_version : " " ;
43784407}
43794408
43804409static int
0 commit comments