#At file:///home/anders/Work/bzrwork/wt1/mysql-trunk/ based on revid:anders.song@stripped
3516 Libing Song 2011-01-28
BUG#33048 Post patch
To disable mysql client commands in binary mode, except
'delimiter' and '\C'.
modified:
client/mysql.cc
=== modified file 'client/mysql.cc'
--- a/client/mysql.cc 2011-01-26 07:13:45 +0000
+++ b/client/mysql.cc 2011-01-28 03:32:51 +0000
@@ -1045,7 +1045,8 @@ static void initialize_readline (char *n
static void fix_history(String *final_command);
#endif
-static COMMANDS *find_command(char *name,char cmd_name);
+static COMMANDS *find_command(char *name);
+static COMMANDS *find_command(char cmd_name);
static bool add_line(String &buffer, char *line, ulong line_length,
char *in_string, bool *ml_comment, bool truncated);
static void remove_cntrl(String &buffer);
@@ -1065,6 +1066,31 @@ extern "C" sig_handler handle_sigint(int
static sig_handler window_resize(int sig);
#endif
+const char DELIMITER_NAME[]= "delimiter";
+const uint DELIMITER_NAME_LEN= sizeof(DELIMITER_NAME) - 1;
+inline bool is_delimiter_command(char *name, ulong len)
+{
+ DBUG_PRINT("slb-", ("len: %d", DELIMITER_NAME_LEN));
+ return (len == DELIMITER_NAME_LEN &&
+ !my_strnncoll(charset_info, (uchar*)name, DELIMITER_NAME_LEN,
+ (uchar *)DELIMITER_NAME, DELIMITER_NAME_LEN));
+}
+
+inline int get_command_index(char cmd_char)
+{
+ /*
+ All commands are in the first part of commands array and have a function
+ to implemente it.
+ */
+ for (uint i=0; *commands[i].func; i++)
+ if (commands[i].cmd_char == cmd_char)
+ return i;
+ return -1;
+}
+
+static int delimiter_index= -1;
+static int charset_index= -1;
+static bool real_binary_mode= FALSE;
int main(int argc,char *argv[])
{
@@ -1073,7 +1099,9 @@ int main(int argc,char *argv[])
MY_INIT(argv[0]);
DBUG_ENTER("main");
DBUG_PROCESS(argv[0]);
-
+
+ charset_index= get_command_index('C');
+ delimiter_index= get_command_index('d');
delimiter_str= delimiter;
default_prompt = my_strdup(getenv("MYSQL_PS1") ?
getenv("MYSQL_PS1") :
@@ -1852,18 +1880,18 @@ static int read_and_execute(bool interac
bool truncated= 0;
ulong line_length= 0;
status.exit_status=1;
-
+ real_binary_mode= (!interactive && opt_binary_mode);
for (;;)
{
if (!interactive)
{
- line=batch_readline(status.line_buff, &truncated, opt_binary_mode);
+ line=batch_readline(status.line_buff, &truncated, real_binary_mode);
line_length= status.line_buff->read_length;
/*
ASCII 0x00 is not allowed appearing in queries if it is not in binary
mode.
*/
- if (!opt_binary_mode && line && strlen(line) != line_length)
+ if (!real_binary_mode && line && strlen(line) != line_length)
{
status.exit_status= 1;
String msg;
@@ -1952,7 +1980,7 @@ static int read_and_execute(bool interac
(We want to allow help, print and clear anywhere at line start
*/
if ((named_cmds || glob_buffer.is_empty())
- && !ml_comment && !in_string && (com=find_command(line,0)))
+ && !ml_comment && !in_string && (com=find_command(line)))
{
if ((*com->func)(&glob_buffer,line) > 0)
break;
@@ -1985,65 +2013,96 @@ static int read_and_execute(bool interac
buffer.free();
tmpbuf.free();
#endif
-
+ real_binary_mode= FALSE;
return status.exit_status;
}
+static COMMANDS *find_command(char cmd_char)
+{
+ DBUG_ENTER("find_command");
+ DBUG_PRINT("enter", ("cmd_char: %d", cmd_char));
+
+ int index= -1;
+ if (real_binary_mode)
+ {
+ if (cmd_char == 'C')
+ index= charset_index;
+ }
+ else
+ index= get_command_index(cmd_char);
+
+ if (index >= 0)
+ {
+ DBUG_PRINT("exit",("found command: %s", commands[index].name));
+ DBUG_RETURN(&commands[index]);
+ }
+ else
+ DBUG_RETURN((COMMANDS *) 0);
+}
-static COMMANDS *find_command(char *name,char cmd_char)
+static COMMANDS *find_command(char *name)
{
uint len;
char *end;
DBUG_ENTER("find_command");
- DBUG_PRINT("enter",("name: '%s' char: %d", name ? name : "NULL", cmd_char));
- if (!name)
+ DBUG_ASSERT(name != NULL);
+ DBUG_PRINT("enter", ("name: '%s'", name));
+
+ while (my_isspace(charset_info,*name))
+ name++;
+ /*
+ If there is an \\g in the row or if the row has a delimiter but
+ this is not a delimiter command, let add_line() take care of
+ parsing the row and calling find_command()
+ */
+ if ((!real_binary_mode && strstr(name, "\\g")) ||
+ (strstr(name, delimiter) &&
+ !is_delimiter_command(name, DELIMITER_NAME_LEN)))
+ DBUG_RETURN((COMMANDS *) 0);
+
+ if ((end=strcont(name," \t")))
+ {
+ len=(uint) (end - name);
+ while (my_isspace(charset_info,*end))
+ end++;
+ if (!*end)
+ end=0; // no arguments to function
+ }
+ else
+ len=(uint) strlen(name);
+
+ int index= -1;
+ if (real_binary_mode)
{
- len=0;
- end=0;
+ if (is_delimiter_command(name, len))
+ index= delimiter_index;
}
else
{
- while (my_isspace(charset_info,*name))
- name++;
/*
- If there is an \\g in the row or if the row has a delimiter but
- this is not a delimiter command, let add_line() take care of
- parsing the row and calling find_command()
+ All commands are in the first part of commands array and have a function
+ to implemente it.
*/
- if (strstr(name, "\\g") || (strstr(name, delimiter) &&
- !(strlen(name) >= 9 &&
- !my_strnncoll(&my_charset_latin1,
- (uchar*) name, 9,
- (const uchar*) "delimiter",
- 9))))
- DBUG_RETURN((COMMANDS *) 0);
- if ((end=strcont(name," \t")))
+ for (uint i= 0; commands[i].func; i++)
{
- len=(uint) (end - name);
- while (my_isspace(charset_info,*end))
- end++;
- if (!*end)
- end=0; // no arguments to function
+ if (commands[i].name[len] == '\0' &&
+ !my_strnncoll(&my_charset_latin1, (uchar*)name, len,
+ (uchar*)commands[i].name,len) &&
+ (!end || commands[i].takes_params))
+ {
+ index= i;
+ break;
+ }
}
- else
- len=(uint) strlen(name);
}
- for (uint i= 0; commands[i].name; i++)
+ if (index >= 0)
{
- if (commands[i].func &&
- ((name &&
- !my_strnncoll(&my_charset_latin1, (uchar*)name, len,
- (uchar*)commands[i].name,len) &&
- !commands[i].name[len] &&
- (!end || (end && commands[i].takes_params))) ||
- (!name && commands[i].cmd_char == cmd_char)))
- {
- DBUG_PRINT("exit",("found command: %s", commands[i].name));
- DBUG_RETURN(&commands[i]);
- }
+ DBUG_PRINT("exit",("found command: %s", commands[index].name));
+ DBUG_RETURN(&commands[index]);
}
+
DBUG_RETURN((COMMANDS *) 0);
}
@@ -2108,7 +2167,7 @@ static bool add_line(String &buffer, cha
*out++= (char) inchar;
continue;
}
- if ((com=find_command(NullS,(char) inchar)))
+ if ((com=find_command((char) inchar)))
{
// Flush previously accepted characters
if (out != line)
@@ -2184,7 +2243,7 @@ static bool add_line(String &buffer, cha
pos--;
- if ((com= find_command(buffer.c_ptr(), 0)))
+ if ((com= find_command(buffer.c_ptr())))
{
if ((*com->func)(&buffer, buffer.c_ptr()) > 0)
@@ -2299,9 +2358,7 @@ static bool add_line(String &buffer, cha
uint length=(uint) (out-line);
if (!truncated &&
- (length < 9 ||
- my_strnncoll (charset_info,
- (uchar *)line, 9, (const uchar *) "delimiter", 9)))
+ (length < 9 || !is_delimiter_command(line, DELIMITER_NAME_LEN)))
{
/*
Don't add a new line in case there's a DELIMITER command to be
Attachment: [text/bzr-bundle] bzr/anders.song@greatopensource.com-20110128033251-eg3xq9h669veta8m.bundle
| Thread |
|---|
| • bzr commit into mysql-trunk branch (anders.song:3516) Bug#33048 | Libing Song | 28 Jan |