Commit a7ba7109 authored by msvensson@pilot.(none)'s avatar msvensson@pilot.(none)

Merge pilot.(none):/data/msvensson/mysql/mysql-5.0-maint

into  pilot.(none):/data/msvensson/mysql/mysql-5.1-new-maint
parents 66b74f6a 7c034137
......@@ -219,7 +219,7 @@ struct st_connection
#endif /*EMBEDDED_LIBRARY*/
};
struct st_connection connections[128];
struct st_connection* cur_con, *next_con, *connections_end;
struct st_connection* cur_con= NULL, *next_con, *connections_end;
/*
List of commands in mysqltest
......@@ -483,11 +483,11 @@ void handle_no_error(struct st_command*);
pthread_attr_t cn_thd_attrib;
/*
send_one_query executes query in separate thread what is
send_one_query executes query in separate thread, which is
necessary in embedded library to run 'send' in proper way.
This implementation doesn't handle errors returned
by mysql_send_query. It's technically possible, though
i don't see where it is needed.
I don't see where it is needed.
*/
pthread_handler_t send_one_query(void *arg)
{
......@@ -588,6 +588,77 @@ void do_eval(DYNAMIC_STRING *query_eval, const char *query,
}
/*
Show any warnings just before the error. Since the last error
is added to the warning stack, only print @@warning_count-1 warnings.
NOTE! This function should be safe to call when an error
has occured and this any further errors will be ignored(although logged)
SYNOPSIS
show_warnings_before_error
mysql - connection to use
*/
static void show_warnings_before_error(MYSQL* mysql)
{
MYSQL_RES* res;
const char* query= "SHOW WARNINGS";
DBUG_ENTER("show_warnings_before_error");
if (!mysql)
DBUG_VOID_RETURN;
if (mysql_query(mysql, query))
{
log_msg("Error running query '%s': %d %s",
query, mysql_errno(mysql), mysql_error(mysql));
DBUG_VOID_RETURN;
}
if ((res= mysql_store_result(mysql)) == NULL)
{
/* No result set returned */
DBUG_VOID_RETURN;
}
if (mysql_num_rows(res) <= 1)
{
/* Don't display the last row, it's "last error" */
}
else
{
MYSQL_ROW row;
unsigned int row_num= 0;
unsigned int num_fields= mysql_num_fields(res);
fprintf(stderr, "\nWarnings from just before the error:\n");
while ((row= mysql_fetch_row(res)))
{
unsigned int i;
unsigned long *lengths= mysql_fetch_lengths(res);
if (++row_num >= mysql_num_rows(res))
{
/* Don't display the last row, it's "last error" */
break;
}
for(i= 0; i < num_fields; i++)
{
fprintf(stderr, "%.*s ", lengths[i],
row[i] ? row[i] : "NULL");
}
fprintf(stderr, "\n");
}
}
mysql_free_result(res);
DBUG_VOID_RETURN;
}
enum arg_type
{
ARG_STRING,
......@@ -887,6 +958,13 @@ void die(const char *fmt, ...)
if (result_file_name && ds_warning_messages.length)
dump_warning_messages();
/*
Help debugging by displaying any warnings that might have
been produced prior to the error
*/
if (cur_con)
show_warnings_before_error(&cur_con->mysql);
cleanup_and_exit(1);
}
......@@ -990,11 +1068,10 @@ void warning_msg(const char *fmt, ...)
void log_msg(const char *fmt, ...)
{
va_list args;
char buff[512];
char buff[1024];
size_t len;
DBUG_ENTER("log_msg");
memset(buff, 0, sizeof(buff));
va_start(args, fmt);
len= my_vsnprintf(buff, sizeof(buff)-1, fmt, args);
va_end(args);
......@@ -1762,40 +1839,22 @@ void var_query_set(VAR *var, const char *query, const char** query_end)
die("Query '%s' didn't return a result set", ds_query.str);
dynstr_free(&ds_query);
if ((row = mysql_fetch_row(res)) && row[0])
if ((row= mysql_fetch_row(res)) && row[0])
{
/*
Concatenate all row results with tab in between to allow us to work
with results from many columns (for example from SHOW VARIABLES)
Concatenate all fields in the first row with tab in between
and assign that string to the $variable
*/
DYNAMIC_STRING result;
uint i;
ulong *lengths;
#ifdef NOT_YET
MYSQL_FIELD *fields= mysql_fetch_fields(res);
#endif
init_dynamic_string(&result, "", 2048, 2048);
init_dynamic_string(&result, "", 512, 512);
lengths= mysql_fetch_lengths(res);
for (i=0; i < mysql_num_fields(res); i++)
{
if (row[0])
for (i= 0; i < mysql_num_fields(res); i++)
{
#ifdef NOT_YET
/* Add to <var_name>_<col_name> */
uint j;
char var_col_name[MAX_VAR_NAME_LENGTH];
uint length= snprintf(var_col_name, MAX_VAR_NAME_LENGTH,
"$%s_%s", var->name, fields[i].name);
/* Convert characters not allowed in variable names to '_' */
for (j= 1; j < length; j++)
if (row[i])
{
if (!my_isvar(charset_info,var_col_name[j]))
var_col_name[j]= '_';
}
var_set(var_col_name, var_col_name + length,
row[i], row[i] + lengths[i]);
#endif
/* Add column to tab separated string */
dynstr_append_mem(&result, row[i], lengths[i]);
}
......@@ -2273,7 +2332,7 @@ void do_exec(struct st_command *command)
if (command->abort_on_error)
{
log_msg("exec of '%s failed, error: %d, status: %d, errno: %d",
log_msg("exec of '%s' failed, error: %d, status: %d, errno: %d",
ds_cmd.str, error, status, errno);
die("command \"%s\" failed", command->first_argument);
}
......@@ -4054,7 +4113,7 @@ void do_connect(struct st_command *command)
mysql_options(&con_slot->mysql, MYSQL_SET_CHARSET_NAME,
charset_info->csname);
if (opt_charsets_dir)
mysql_options(&cur_con->mysql, MYSQL_SET_CHARSET_DIR,
mysql_options(&con_slot->mysql, MYSQL_SET_CHARSET_DIR,
opt_charsets_dir);
#ifdef HAVE_OPENSSL
......@@ -6481,7 +6540,6 @@ int main(int argc, char **argv)
connections_end= connections +
(sizeof(connections)/sizeof(struct st_connection)) - 1;
next_con= connections + 1;
cur_con= connections;
#ifdef EMBEDDED_LIBRARY
/* set appropriate stack for the 'query' threads */
......@@ -6557,6 +6615,7 @@ int main(int argc, char **argv)
if (cursor_protocol_enabled)
ps_protocol_enabled= 1;
cur_con= connections;
if (!( mysql_init(&cur_con->mysql)))
die("Failed in mysql_init()");
if (opt_compress)
......
......@@ -280,6 +280,18 @@ let $B = changed value of B;
var2: content of variable 1
var3: content of variable 1 content of variable 1
length of var3 is longer than 0
var1
hi 1 hi there
var2
2
var2 again
2
var3 two columns with same name
1 2 3
var4 from query that returns NULL
var5 from query that returns no row
failing query in let
mysqltest: At line 1: Error running query 'failing query': 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'failing query' at line 1
mysqltest: At line 1: Missing required argument 'filename' to command 'source'
mysqltest: At line 1: Could not open file ./non_existingFile
mysqltest: In included file "MYSQLTEST_VARDIR/tmp/recursive.sql": At line 1: Source directives are nesting too deep
......
......@@ -741,38 +741,40 @@ if (`select length("$var3") > 0`)
# Test to assign let from query
# let $<var_name>=`<query>`;
# ----------------------------------------------------------------------------
--disable_parsing
echo var1;
let $var1= `select "hi" as "Col", 1 as "Column1", "hi there" as Col3`;
echo $var1;
echo $var1_Col;
echo $var1_Column1;
echo $var1_Col3;
echo var2;
let $var2= `select 2 as "Column num 2"`;
echo $var2;
echo $var2_Column num 2;
echo $var2_Column;
echo var2 again;
let $var2= `select 2 as "Column num 2"`;
echo $var2;
echo $var2_Column num 2;
echo $var2_Column_num_2;
echo $var2_Column;
echo var3 two columns with same name;
let $var3= `select 1 as "Col", 2 as "Col", 3 as "var3"`;
echo $var3;
echo $var3_Col;
echo $var3_Col;
echo $var3_var3;
#echo failing query in let;
#--error 1
#--exec echo "let $var2= `failing query;`" | $MYSQL_TEST 2>&1
--enable_parsing
echo var4 from query that returns NULL;
let $var4= `select NULL`;
echo var5 from query that returns no row;
let $var5= `SHOW VARIABLES LIKE "nonexisting_variable"`;
echo failing query in let;
--write_file $MYSQLTEST_VARDIR/tmp/let.sql
let $var2= `failing query`;
echo $var2;
EOF
--error 1
--exec $MYSQL_TEST < $MYSQLTEST_VARDIR/tmp/let.sql 2>&1
remove_file $MYSQLTEST_VARDIR/tmp/let.sql;
# ----------------------------------------------------------------------------
# Test source command
# ----------------------------------------------------------------------------
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment