diff options
24 files changed, 497 insertions, 91 deletions
diff --git a/mysql-test/include/sp-vars.inc b/mysql-test/include/sp-vars.inc index 3e02c9d1709..4bac883ee0e 100644 --- a/mysql-test/include/sp-vars.inc +++ b/mysql-test/include/sp-vars.inc @@ -119,4 +119,13 @@ END| --------------------------------------------------------------------------- +CREATE FUNCTION sp_vars_div_zero() RETURNS INTEGER +BEGIN + DECLARE div_zero INTEGER; + SELECT 1/0 INTO div_zero; + RETURN div_zero; +END| + +--------------------------------------------------------------------------- + delimiter ;| diff --git a/mysql-test/mysql-test-run.pl b/mysql-test/mysql-test-run.pl index e5ed8a99304..c2dc0961a4a 100755 --- a/mysql-test/mysql-test-run.pl +++ b/mysql-test/mysql-test-run.pl @@ -1425,6 +1425,7 @@ sub environment_setup () { # $ENV{'MYSQL_TCP_PORT'}= '@MYSQL_TCP_PORT@'; # FIXME $ENV{'MYSQL_TCP_PORT'}= 3306; + $ENV{'EXE_MYSQL'}= $exe_mysql; $ENV{MTR_BUILD_THREAD}= 0 unless $ENV{MTR_BUILD_THREAD}; # Set if not set # ---------------------------------------------------- @@ -1456,6 +1457,9 @@ sub environment_setup () { $ENV{'IM_PORT'}= $instance_manager->{port}; $ENV{'IM_DEFAULTS_PATH'}= $instance_manager->{defaults_file}; $ENV{'IM_PASSWORD_PATH'}= $instance_manager->{password_file}; + $ENV{'IM_PATH_SOCK'}= $instance_manager->{path_sock}; + $ENV{'IM_USERNAME'}= $instance_manager->{admin_login}; + $ENV{'IM_PASSWORD'}= $instance_manager->{admin_password}; $ENV{'IM_MYSQLD1_SOCK'}= $instance_manager->{instances}->[0]->{path_sock}; $ENV{'IM_MYSQLD1_PORT'}= $instance_manager->{instances}->[0]->{port}; @@ -1464,9 +1468,9 @@ sub environment_setup () { $ENV{'IM_MYSQLD2_PORT'}= $instance_manager->{instances}->[1]->{port}; $ENV{'IM_MYSQLD2_PATH_PID'}=$instance_manager->{instances}->[1]->{path_pid}; - # ---------------------------------------------------- - # Setup env so childs can execute mysqlcheck - # ---------------------------------------------------- +# ---------------------------------------------------- +# Setup env so childs can execute mysqlcheck +# ---------------------------------------------------- my $cmdline_mysqlcheck= "$exe_mysqlcheck --no-defaults -uroot " . "--port=$master->[0]->{'port'} " . @@ -1630,9 +1634,9 @@ sub environment_setup () { ($ENV{'LD_LIBRARY_PATH'} ? ":$ENV{'LD_LIBRARY_PATH'}" : ""); - # ---------------------------------------------------- - # We are nice and report a bit about our settings - # ---------------------------------------------------- +# ---------------------------------------------------- +# We are nice and report a bit about our settings +# ---------------------------------------------------- if (!$opt_extern) { print "Using MTR_BUILD_THREAD = $ENV{MTR_BUILD_THREAD}\n"; diff --git a/mysql-test/r/im_daemon_life_cycle.result b/mysql-test/r/im_daemon_life_cycle.result index eee8479888a..23990240acd 100644 --- a/mysql-test/r/im_daemon_life_cycle.result +++ b/mysql-test/r/im_daemon_life_cycle.result @@ -8,6 +8,7 @@ mysqld2 offline Killing the process... Sleeping... Success: the process was restarted. +Success: server is ready to accept connection on socket. -------------------------------------------------------------------- -- Test for BUG#12751 diff --git a/mysql-test/r/sp-vars.result b/mysql-test/r/sp-vars.result index d41d98113a1..8b59fa371cc 100644 --- a/mysql-test/r/sp-vars.result +++ b/mysql-test/r/sp-vars.result @@ -4,6 +4,7 @@ DROP FUNCTION IF EXISTS sp_vars_check_ret1; DROP FUNCTION IF EXISTS sp_vars_check_ret2; DROP FUNCTION IF EXISTS sp_vars_check_ret3; DROP FUNCTION IF EXISTS sp_vars_check_ret4; +DROP FUNCTION IF EXISTS sp_vars_div_zero; SET @@sql_mode = 'ansi'; CREATE PROCEDURE sp_vars_check_dflt() BEGIN @@ -88,6 +89,12 @@ CREATE FUNCTION sp_vars_check_ret4() RETURNS DECIMAL(64, 2) BEGIN RETURN 12 * 10 + 34 + 0.1234; END| +CREATE FUNCTION sp_vars_div_zero() RETURNS INTEGER +BEGIN +DECLARE div_zero INTEGER; +SELECT 1/0 INTO div_zero; +RETURN div_zero; +END| --------------------------------------------------------------- Calling the routines, created in ANSI mode. @@ -172,6 +179,9 @@ sp_vars_check_ret4() 154.12 Warnings: Note 1265 Data truncated for column 'sp_vars_check_ret4()' at row 1 +SELECT sp_vars_div_zero(); +sp_vars_div_zero() +NULL SET @@sql_mode = 'traditional'; --------------------------------------------------------------- @@ -257,12 +267,16 @@ sp_vars_check_ret4() 154.12 Warnings: Note 1265 Data truncated for column 'sp_vars_check_ret4()' at row 1 +SELECT sp_vars_div_zero(); +sp_vars_div_zero() +NULL DROP PROCEDURE sp_vars_check_dflt; DROP PROCEDURE sp_vars_check_assignment; DROP FUNCTION sp_vars_check_ret1; DROP FUNCTION sp_vars_check_ret2; DROP FUNCTION sp_vars_check_ret3; DROP FUNCTION sp_vars_check_ret4; +DROP FUNCTION sp_vars_div_zero; CREATE PROCEDURE sp_vars_check_dflt() BEGIN DECLARE v1 TINYINT DEFAULT 1e200; @@ -346,6 +360,12 @@ CREATE FUNCTION sp_vars_check_ret4() RETURNS DECIMAL(64, 2) BEGIN RETURN 12 * 10 + 34 + 0.1234; END| +CREATE FUNCTION sp_vars_div_zero() RETURNS INTEGER +BEGIN +DECLARE div_zero INTEGER; +SELECT 1/0 INTO div_zero; +RETURN div_zero; +END| --------------------------------------------------------------- Calling the routines, created in TRADITIONAL mode. @@ -366,6 +386,8 @@ sp_vars_check_ret4() 154.12 Warnings: Note 1265 Data truncated for column 'sp_vars_check_ret4()' at row 1 +SELECT sp_vars_div_zero(); +ERROR 22012: Division by 0 SET @@sql_mode = 'ansi'; DROP PROCEDURE sp_vars_check_dflt; DROP PROCEDURE sp_vars_check_assignment; @@ -373,6 +395,7 @@ DROP FUNCTION sp_vars_check_ret1; DROP FUNCTION sp_vars_check_ret2; DROP FUNCTION sp_vars_check_ret3; DROP FUNCTION sp_vars_check_ret4; +DROP FUNCTION sp_vars_div_zero; --------------------------------------------------------------- BIT data type tests diff --git a/mysql-test/r/trigger.result b/mysql-test/r/trigger.result index 5f027195e2e..52123885772 100644 --- a/mysql-test/r/trigger.result +++ b/mysql-test/r/trigger.result @@ -1073,10 +1073,11 @@ SELECT @x; NULL SET @x=2; UPDATE t1 SET i1 = @x; -ERROR 22012: Division by 0 +Warnings: +Error 1365 Division by 0 SELECT @x; @x -2 +NULL SET SQL_MODE=''; SET @x=3; INSERT INTO t1 VALUES (@x); @@ -1085,10 +1086,12 @@ SELECT @x; NULL SET @x=4; UPDATE t1 SET i1 = @x; -ERROR 22012: Division by 0 +Warnings: +Error 1365 Division by 0 +Error 1365 Division by 0 SELECT @x; @x -4 +NULL SET @@sql_mode=@save_sql_mode; DROP TRIGGER t1_ai; DROP TRIGGER t1_au; @@ -1174,6 +1177,59 @@ ERROR HY000: String '1234567890abcdefghij1234567890abcdefghij1234567890abcdefghi DROP TABLE t1; DROP TABLE t2; drop table if exists t1; +drop table if exists t2; +drop table if exists t3; +drop table if exists t4; +SET @save_sql_mode=@@sql_mode; +SET sql_mode='TRADITIONAL'| +create table t1 (id int(10) not null primary key, v int(10) )| +create table t2 (id int(10) not null primary key, v int(10) )| +create table t3 (id int(10) not null primary key, v int(10) )| +create table t4 (c int)| +create trigger t4_bi before insert on t4 for each row set @t4_bi_called:=1| +create trigger t4_bu before update on t4 for each row set @t4_bu_called:=1| +insert into t1 values(10, 10)| +set @a:=1/0| +Warnings: +Error 1365 Division by 0 +select 1/0 from t1| +1/0 +NULL +Warnings: +Error 1365 Division by 0 +create trigger t1_bi before insert on t1 for each row set @a:=1/0| +insert into t1 values(20, 20)| +Warnings: +Error 1365 Division by 0 +drop trigger t1_bi| +create trigger t1_bi before insert on t1 for each row +begin +insert into t2 values (new.id, new.v); +update t2 set v=v+1 where id= new.id; +replace t3 values (new.id, 0); +update t2, t3 set t2.v=new.v, t3.v=new.v where t2.id=t3.id; +create temporary table t5 select * from t1; +delete from t5; +insert into t5 select * from t1; +insert into t4 values (0); +set @check= (select count(*) from t5); +update t4 set c= @check; +drop temporary table t5; +set @a:=1/0; +end| +set @check=0, @t4_bi_called=0, @t4_bu_called=0| +insert into t1 values(30, 30)| +Warnings: +Error 1365 Division by 0 +select @check, @t4_bi_called, @t4_bu_called| +@check @t4_bi_called @t4_bu_called +2 1 1 +SET @@sql_mode=@save_sql_mode; +drop table t1; +drop table t2; +drop table t3; +drop table t4; +drop table if exists t1; create table t1 (i int, j int key); insert into t1 values (1,1), (2,2), (3,3); create trigger t1_bu before update on t1 for each row diff --git a/mysql-test/t/im_daemon_life_cycle.imtest b/mysql-test/t/im_daemon_life_cycle.imtest index 55e52f4e464..f1d1bd786ff 100644 --- a/mysql-test/t/im_daemon_life_cycle.imtest +++ b/mysql-test/t/im_daemon_life_cycle.imtest @@ -17,6 +17,12 @@ ########################################################################### +# Wait for IM to start accepting connections. + +--exec $MYSQL_TEST_DIR/t/wait_for_socket.sh $EXE_MYSQL $IM_PATH_SOCK $IM_USERNAME $IM_PASSWORD '' 30 + +########################################################################### + # # BUG#12751: Instance Manager: client hangs # diff --git a/mysql-test/t/ps.test b/mysql-test/t/ps.test index 0239be9b6d9..7e269eab050 100644 --- a/mysql-test/t/ps.test +++ b/mysql-test/t/ps.test @@ -988,6 +988,7 @@ execute stmt; drop temporary table t1; deallocate prepare stmt; + # # BUG#22085: Crash on the execution of a prepared statement that # uses an IN subquery with aggregate functions in HAVING @@ -1114,6 +1115,7 @@ DROP TABLE t1; --echo End of 4.1 tests. + ############################# 5.0 tests start ################################ # # diff --git a/mysql-test/t/sp-error.test b/mysql-test/t/sp-error.test index 8754d9ca82d..ef3da60578f 100644 --- a/mysql-test/t/sp-error.test +++ b/mysql-test/t/sp-error.test @@ -1748,6 +1748,8 @@ drop function if exists bug16896; --error ER_SP_NO_AGGREGATE create aggregate function bug16896() returns int return 1; +# +# # BUG#14702: misleading error message when syntax error in CREATE # PROCEDURE # diff --git a/mysql-test/t/sp-vars.test b/mysql-test/t/sp-vars.test index 48dbd4de7aa..7cf92dc5d0d 100644 --- a/mysql-test/t/sp-vars.test +++ b/mysql-test/t/sp-vars.test @@ -15,6 +15,7 @@ DROP FUNCTION IF EXISTS sp_vars_check_ret1; DROP FUNCTION IF EXISTS sp_vars_check_ret2; DROP FUNCTION IF EXISTS sp_vars_check_ret3; DROP FUNCTION IF EXISTS sp_vars_check_ret4; +DROP FUNCTION IF EXISTS sp_vars_div_zero; --enable_warnings @@ -49,6 +50,8 @@ SELECT sp_vars_check_ret3(); SELECT sp_vars_check_ret4(); +SELECT sp_vars_div_zero(); + # Check that changing sql_mode after creating a store procedure does not # matter. @@ -72,6 +75,8 @@ SELECT sp_vars_check_ret3(); SELECT sp_vars_check_ret4(); +SELECT sp_vars_div_zero(); + # Create the procedure in TRADITIONAL mode. Check that error will be thrown on # execution. @@ -81,6 +86,7 @@ DROP FUNCTION sp_vars_check_ret1; DROP FUNCTION sp_vars_check_ret2; DROP FUNCTION sp_vars_check_ret3; DROP FUNCTION sp_vars_check_ret4; +DROP FUNCTION sp_vars_div_zero; --source include/sp-vars.inc @@ -110,6 +116,9 @@ SELECT sp_vars_check_ret3(); SELECT sp_vars_check_ret4(); +--error ER_DIVISION_BY_ZERO +SELECT sp_vars_div_zero(); + SET @@sql_mode = 'ansi'; # @@ -122,6 +131,7 @@ DROP FUNCTION sp_vars_check_ret1; DROP FUNCTION sp_vars_check_ret2; DROP FUNCTION sp_vars_check_ret3; DROP FUNCTION sp_vars_check_ret4; +DROP FUNCTION sp_vars_div_zero; ########################################################################### # diff --git a/mysql-test/t/sp.test b/mysql-test/t/sp.test index b3563e21bdd..7c1fd59c50b 100644 --- a/mysql-test/t/sp.test +++ b/mysql-test/t/sp.test @@ -6419,6 +6419,170 @@ SELECT bug21493(Member_ID) FROM t3| DROP FUNCTION bug21493| DROP TABLE t3,t4| +# +# Bug#20028 Function with select return no data +# + +--disable_warnings +drop function if exists func_20028_a| +drop function if exists func_20028_b| +drop function if exists func_20028_c| +drop procedure if exists proc_20028_a| +drop procedure if exists proc_20028_b| +drop procedure if exists proc_20028_c| +drop table if exists table_20028| +--enable_warnings + +create table table_20028 (i int)| + +SET @save_sql_mode=@@sql_mode| + +SET sql_mode=''| + +create function func_20028_a() returns integer +begin + declare temp integer; + select i into temp from table_20028 limit 1; + return ifnull(temp, 0); +end| + +create function func_20028_b() returns integer +begin + return func_20028_a(); +end| + +create function func_20028_c() returns integer +begin + declare div_zero integer; + set SQL_MODE='TRADITIONAL'; + select 1/0 into div_zero; + return div_zero; +end| + +create procedure proc_20028_a() +begin + declare temp integer; + select i into temp from table_20028 limit 1; +end| + +create procedure proc_20028_b() +begin + call proc_20028_a(); +end| + +create procedure proc_20028_c() +begin + declare div_zero integer; + set SQL_MODE='TRADITIONAL'; + select 1/0 into div_zero; +end| + +select func_20028_a()| +select func_20028_b()| +--error ER_DIVISION_BY_ZERO +select func_20028_c()| +call proc_20028_a()| +call proc_20028_b()| +--error ER_DIVISION_BY_ZERO +call proc_20028_c()| + +SET sql_mode='TRADITIONAL'| + +drop function func_20028_a| +drop function func_20028_b| +drop function func_20028_c| +drop procedure proc_20028_a| +drop procedure proc_20028_b| +drop procedure proc_20028_c| + +create function func_20028_a() returns integer +begin + declare temp integer; + select i into temp from table_20028 limit 1; + return ifnull(temp, 0); +end| + +create function func_20028_b() returns integer +begin + return func_20028_a(); +end| + +create function func_20028_c() returns integer +begin + declare div_zero integer; + set SQL_MODE=''; + select 1/0 into div_zero; + return div_zero; +end| + +create procedure proc_20028_a() +begin + declare temp integer; + select i into temp from table_20028 limit 1; +end| + +create procedure proc_20028_b() +begin + call proc_20028_a(); +end| + +create procedure proc_20028_c() +begin + declare div_zero integer; + set SQL_MODE=''; + select 1/0 into div_zero; +end| + +select func_20028_a()| +select func_20028_b()| +select func_20028_c()| +call proc_20028_a()| +call proc_20028_b()| +call proc_20028_c()| + +SET @@sql_mode=@save_sql_mode| + +drop function func_20028_a| +drop function func_20028_b| +drop function func_20028_c| +drop procedure proc_20028_a| +drop procedure proc_20028_b| +drop procedure proc_20028_c| +drop table table_20028| + +# +# Bug#21462 Stored procedures with no arguments require parenthesis +# + +--disable_warnings +drop procedure if exists proc_21462_a| +drop procedure if exists proc_21462_b| +--enable_warnings + +create procedure proc_21462_a() +begin + select "Called A"; +end| + +create procedure proc_21462_b(x int) +begin + select "Called B"; +end| + +call proc_21462_a| +call proc_21462_a()| +-- error ER_SP_WRONG_NO_OF_ARGS +call proc_21462_a(1)| + +-- error ER_SP_WRONG_NO_OF_ARGS +call proc_21462_b| +-- error ER_SP_WRONG_NO_OF_ARGS +call proc_21462_b()| +call proc_21462_b(1)| + +drop procedure proc_21462_a| +drop procedure proc_21462_b| + --echo End of 5.0 tests diff --git a/mysql-test/t/trigger.test b/mysql-test/t/trigger.test index ccc17e55dc8..8242c614d0a 100644 --- a/mysql-test/t/trigger.test +++ b/mysql-test/t/trigger.test @@ -1274,7 +1274,6 @@ INSERT INTO t1 VALUES (@x); SELECT @x; SET @x=2; ---error ER_DIVISION_BY_ZERO UPDATE t1 SET i1 = @x; SELECT @x; @@ -1285,7 +1284,6 @@ INSERT INTO t1 VALUES (@x); SELECT @x; SET @x=4; ---error ER_DIVISION_BY_ZERO UPDATE t1 SET i1 = @x; SELECT @x; @@ -1420,6 +1418,67 @@ CREATE DEFINER=some_user_name@1234567890abcdefghij1234567890abcdefghij1234567890 DROP TABLE t1; DROP TABLE t2; +# +# Bug#20028 Function with select return no data +# + +--disable_warnings +drop table if exists t1; +drop table if exists t2; +drop table if exists t3; +drop table if exists t4; +--enable_warnings + +SET @save_sql_mode=@@sql_mode; + +delimiter |; +SET sql_mode='TRADITIONAL'| +create table t1 (id int(10) not null primary key, v int(10) )| +create table t2 (id int(10) not null primary key, v int(10) )| +create table t3 (id int(10) not null primary key, v int(10) )| +create table t4 (c int)| + +create trigger t4_bi before insert on t4 for each row set @t4_bi_called:=1| +create trigger t4_bu before update on t4 for each row set @t4_bu_called:=1| + +insert into t1 values(10, 10)| +set @a:=1/0| +select 1/0 from t1| + +create trigger t1_bi before insert on t1 for each row set @a:=1/0| + +insert into t1 values(20, 20)| + +drop trigger t1_bi| +create trigger t1_bi before insert on t1 for each row +begin + insert into t2 values (new.id, new.v); + update t2 set v=v+1 where id= new.id; + replace t3 values (new.id, 0); + update t2, t3 set t2.v=new.v, t3.v=new.v where t2.id=t3.id; + create temporary table t5 select * from t1; + delete from t5; + insert into t5 select * from t1; + insert into t4 values (0); + set @check= (select count(*) from t5); + update t4 set c= @check; + drop temporary table t5; + + set @a:=1/0; +end| + +set @check=0, @t4_bi_called=0, @t4_bu_called=0| +insert into t1 values(30, 30)| +select @check, @t4_bi_called, @t4_bu_called| + +delimiter ;| + +SET @@sql_mode=@save_sql_mode; + +drop table t1; +drop table t2; +drop table t3; +drop table t4; # # Bug#20670 "UPDATE using key and invoking trigger that modifies diff --git a/mysql-test/t/wait_for_socket.sh b/mysql-test/t/wait_for_socket.sh new file mode 100755 index 00000000000..3b900fa2208 --- /dev/null +++ b/mysql-test/t/wait_for_socket.sh @@ -0,0 +1,62 @@ +#!/bin/sh + +########################################################################### + +if [ $# -ne 6 ]; then + echo "Usage: wait_for_socket.sh <executable path> <socket path> <username> <password> <db> <timeout>" + exit 0 +fi + +client_exe="$1" +socket_path="$2" +username="$3" +password="$4" +db="$5" +total_timeout="$6" + +########################################################################### + +if [ -z "$client_exe" ]; then + echo "Error: invalid path to client executable ($client_exe)." + exit 0; +fi + +if [ ! -x "$client_exe" ]; then + echo "Error: client by path '$client_exe' is not available." + exit 0; +fi + +if [ -z "$socket_path" ]; then + echo "Error: invalid socket patch." + exit 0 +fi + +########################################################################### + +client_args="--silent --socket=$socket_path " + +[ -n "$username" ] && client_args="$client_args --user=$username " +[ -n "$password" ] && client_args="$client_args --password=$password " +[ -n "$db" ] && client_args="$client_args $db" + +########################################################################### + +cur_attempt=1 + +while true; do + + if ( echo 'quit' | "$client_exe" $client_args >/dev/null 2>&1 ); then + echo "Success: server is ready to accept connection on socket." + exit 0 + fi + + [ $cur_attempt -ge $total_timeout ] && break + + sleep 1 + + cur_attempt=`expr $cur_attempt + 1` + +done + +echo "Error: server does not accept connections after $total_timeout seconds." +exit 0 diff --git a/server-tools/instance-manager/guardian.cc b/server-tools/instance-manager/guardian.cc index 68d89a4b375..9fc3a6583ef 100644 --- a/server-tools/instance-manager/guardian.cc +++ b/server-tools/instance-manager/guardian.cc @@ -95,11 +95,11 @@ Guardian_thread::~Guardian_thread() } -void Guardian_thread::request_shutdown(bool stop_instances_arg) +void Guardian_thread::request_shutdown() { pthread_mutex_lock(&LOCK_guardian); /* stop instances or just clean up Guardian repository */ - stop_instances(stop_instances_arg); + stop_instances(); shutdown_requested= TRUE; pthread_mutex_unlock(&LOCK_guardian); } @@ -154,11 +154,11 @@ void Guardian_thread::process_instance(Instance *instance, { /* Pid file not created yet, don't go to STARTED state yet */ } - else + else if (current_node->state != STARTED) { /* clear status fields */ - log_info("guardian: instance %s is running, set state to STARTED", - instance->options.instance_name); + log_info("guardian: instance '%s' is running, set state to STARTED.", + (const char *) instance->options.instance_name); current_node->restart_counter= 0; current_node->crash_moment= 0; current_node->state= STARTED; @@ -168,8 +168,8 @@ void Guardian_thread::process_instance(Instance *instance, { switch (current_node->state) { case NOT_STARTED: - log_info("guardian: starting instance %s", - instance->options.instance_name); + log_info("guardian: starting instance '%s'...", + (const char *) instance->options.instance_name); /* NOTE, set state to STARTING _before_ start() is called */ current_node->state= STARTING; @@ -193,8 +193,8 @@ void Guardian_thread::process_instance(Instance *instance, if (instance->is_crashed()) { instance->start(); - log_info("guardian: starting instance %s", - instance->options.instance_name); + log_info("guardian: starting instance '%s'...", + (const char *) instance->options.instance_name); } } else @@ -211,8 +211,8 @@ void Guardian_thread::process_instance(Instance *instance, instance->start(); current_node->last_checked= current_time; current_node->restart_counter++; - log_info("guardian: restarting instance %s", - instance->options.instance_name); + log_info("guardian: restarting instance '%s'...", + (const char *) instance->options.instance_name); } } else @@ -414,12 +414,11 @@ int Guardian_thread::stop_guard(Instance *instance) SYNOPSYS stop_instances() - stop_instances_arg whether we should stop instances at shutdown DESCRIPTION Loops through the guarded_instances list and prepares them for shutdown. - If stop_instances was requested, we need to issue a stop command and change - the state accordingly. Otherwise we simply delete an entry. + For each instance we issue a stop command and change the state + accordingly. NOTE Guardian object should be locked by the calling function. @@ -429,42 +428,29 @@ int Guardian_thread::stop_guard(Instance *instance) 1 - error occured */ -int Guardian_thread::stop_instances(bool stop_instances_arg) +int Guardian_thread::stop_instances() { LIST *node; node= guarded_instances; while (node != NULL) { - if (!stop_instances_arg) + GUARD_NODE *current_node= (GUARD_NODE *) node->data; + /* + If instance is running or was running (and now probably hanging), + request stop. + */ + if (current_node->instance->is_running() || + (current_node->state == STARTED)) { - /* just forget about an instance */ - guarded_instances= list_delete(guarded_instances, node); - /* - This should still work fine, as we have only removed the - node from the list. The pointer to the next one is still valid - */ - node= node->next; + current_node->state= STOPPING; + current_node->last_checked= time(NULL); } else - { - GUARD_NODE *current_node= (GUARD_NODE *) node->data; - /* - If instance is running or was running (and now probably hanging), - request stop. - */ - if (current_node->instance->is_running() || - (current_node->state == STARTED)) - { - current_node->state= STOPPING; - current_node->last_checked= time(NULL); - } - else - /* otherwise remove it from the list */ - guarded_instances= list_delete(guarded_instances, node); - /* But try to kill it anyway. Just in case */ - current_node->instance->kill_instance(SIGTERM); - node= node->next; - } + /* otherwise remove it from the list */ + guarded_instances= list_delete(guarded_instances, node); + /* But try to kill it anyway. Just in case */ + current_node->instance->kill_instance(SIGTERM); + node= node->next; } return 0; } diff --git a/server-tools/instance-manager/guardian.h b/server-tools/instance-manager/guardian.h index 6d3a2b222d7..27ca155fd67 100644 --- a/server-tools/instance-manager/guardian.h +++ b/server-tools/instance-manager/guardian.h @@ -91,7 +91,7 @@ public: /* Initialize or refresh the list of guarded instances */ int init(); /* Request guardian shutdown. Stop instances if needed */ - void request_shutdown(bool stop_instances); + void request_shutdown(); /* Start instance protection */ int guard(Instance *instance, bool nolock= FALSE); /* Stop instance protection */ @@ -123,7 +123,7 @@ public: private: /* Prepares Guardian shutdown. Stops instances is needed */ - int stop_instances(bool stop_instances_arg); + int stop_instances(); /* check instance state and act accordingly */ void process_instance(Instance *instance, GUARD_NODE *current_node, LIST **guarded_instances, LIST *elem); diff --git a/server-tools/instance-manager/instance.cc b/server-tools/instance-manager/instance.cc index dfe26397414..c4bd1e211e1 100644 --- a/server-tools/instance-manager/instance.cc +++ b/server-tools/instance-manager/instance.cc @@ -165,8 +165,8 @@ static int start_process(Instance_options *instance_options, /* exec never returns */ exit(1); case -1: - log_info("cannot create a new process to start instance %s", - instance_options->instance_name); + log_info("cannot create a new process to start instance '%s'.", + (const char *) instance_options->instance_name); return 1; } return 0; @@ -256,7 +256,8 @@ static void start_and_monitor_instance(Instance_options *old_instance_options, are using is destroyed. (E.g. by "FLUSH INSTANCES") */ - log_info("starting instance %s", (const char *) instance_name.get_c_str()); + log_info("starting instance %s...", + (const char *) instance_name.get_c_str()); if (start_process(old_instance_options, &process_info)) { @@ -311,9 +312,9 @@ void Instance::remove_pid() int pid; if ((pid= options.get_pid()) != 0) /* check the pidfile */ if (options.unlink_pidfile()) /* remove stalled pidfile */ - log_error("cannot remove pidfile for instance %i, this might be \ + log_error("cannot remove pidfile for instance '%s', this might be \ since IM lacks permmissions or hasn't found the pidifle", - options.instance_name); + (const char *) options.instance_name); } @@ -467,9 +468,9 @@ bool Instance::is_running() We have successfully connected to the server using fake username/password. Write a warning to the logfile. */ - log_info("The Instance Manager was able to log into you server \ - with faked compiled-in password while checking server status. \ - Looks like something is wrong."); + log_info("The Instance Manager was able to log into you server " + "with faked compiled-in password while checking server status. " + "Looks like something is wrong."); pthread_mutex_unlock(&LOCK_instance); return_val= TRUE; /* server is alive */ } @@ -616,10 +617,10 @@ void Instance::kill_instance(int signum) /* Kill suceeded */ if (signum == SIGKILL) /* really killed instance with SIGKILL */ { - log_error("The instance %s is being stopped forcibly. Normally" \ - "it should not happen. Probably the instance has been" \ + log_error("The instance '%s' is being stopped forcibly. Normally" + "it should not happen. Probably the instance has been" "hanging. You should also check your IM setup", - options.instance_name); + (const char *) options.instance_name); /* After sucessful hard kill the pidfile need to be removed */ options.unlink_pidfile(); } diff --git a/server-tools/instance-manager/instance_map.cc b/server-tools/instance-manager/instance_map.cc index ec73fb7d73a..b7704c027f1 100644 --- a/server-tools/instance-manager/instance_map.cc +++ b/server-tools/instance-manager/instance_map.cc @@ -293,7 +293,9 @@ int Instance_map::flush_instances() get_instance_key, delete_instance, 0); rc= load(); - guardian->init(); // TODO: check error status. + /* don't init guardian if we failed to load instances */ + if (!rc) + guardian->init(); // TODO: check error status. return rc; } diff --git a/server-tools/instance-manager/listener.cc b/server-tools/instance-manager/listener.cc index 197c315dee8..0ab85c0e7aa 100644 --- a/server-tools/instance-manager/listener.cc +++ b/server-tools/instance-manager/listener.cc @@ -283,7 +283,7 @@ int Listener_thread::create_tcp_socket() FD_SET(ip_socket, &read_fds); sockets[num_sockets++]= ip_socket; - log_info("accepting connections on ip socket"); + log_info("accepting connections on ip socket (port: %d)", (int) im_port); return 0; } @@ -337,7 +337,7 @@ create_unix_socket(struct sockaddr_un &unix_socket_address) /* make sure that instances won't be listening our sockets */ set_no_inherit(unix_socket); - log_info("accepting connections on unix socket %s", + log_info("accepting connections on unix socket '%s'", unix_socket_address.sun_path); sockets[num_sockets++]= unix_socket; FD_SET(unix_socket, &read_fds); diff --git a/server-tools/instance-manager/manager.cc b/server-tools/instance-manager/manager.cc index d2d498eebf1..3fb967fc352 100644 --- a/server-tools/instance-manager/manager.cc +++ b/server-tools/instance-manager/manager.cc @@ -120,6 +120,19 @@ int my_sigwait(const sigset_t *set, int *sig) #endif +void stop_all(Guardian_thread *guardian, Thread_registry *registry) +{ + /* + Let guardian thread know that it should break it's processing cycle, + once it wakes up. + */ + guardian->request_shutdown(); + /* wake guardian */ + pthread_cond_signal(&guardian->COND_guardian); + /* stop all threads */ + registry->deliver_shutdown(); +} + /* manager - entry point to the main instance manager process: start listener thread, write pid file and enter into signal handling. @@ -251,7 +264,6 @@ void manager() /* Load instances. */ - { instance_map.guardian->lock(); instance_map.lock(); @@ -266,7 +278,8 @@ void manager() log_error("Cannot init instances repository. This might be caused by " "the wrong config file options. For instance, missing mysqld " "binary. Aborting."); - return; + stop_all(&guardian_thread, &thread_registry); + goto err; } } @@ -284,6 +297,7 @@ void manager() if (rc) { log_error("manager(): set_stacksize_n_create_thread(listener) failed"); + stop_all(&guardian_thread, &thread_registry); goto err; } } @@ -302,6 +316,7 @@ void manager() if ((status= my_sigwait(&mask, &signo)) != 0) { log_error("sigwait() failed"); + stop_all(&guardian_thread, &thread_registry); goto err; } @@ -323,8 +338,7 @@ void manager() { if (!guardian_thread.is_stopped()) { - bool stop_instances= TRUE; - guardian_thread.request_shutdown(stop_instances); + guardian_thread.request_shutdown(); pthread_cond_signal(&guardian_thread.COND_guardian); } else diff --git a/server-tools/instance-manager/options.cc b/server-tools/instance-manager/options.cc index 07a1fd3e932..0fff68fbd4f 100644 --- a/server-tools/instance-manager/options.cc +++ b/server-tools/instance-manager/options.cc @@ -41,7 +41,6 @@ static char win_dflt_config_file_name[FN_REFLEN]; static char win_dflt_password_file_name[FN_REFLEN]; static char win_dflt_pid_file_name[FN_REFLEN]; -static char win_dflt_socket_file_name[FN_REFLEN]; static char win_dflt_mysqld_path[FN_REFLEN]; @@ -54,7 +53,6 @@ my_bool Options::Service::stand_alone; const char *Options::Main::config_file= win_dflt_config_file_name; const char *Options::Main::password_file_name= win_dflt_password_file_name; const char *Options::Main::pid_file_name= win_dflt_pid_file_name; -const char *Options::Main::socket_file_name= win_dflt_socket_file_name; const char *Options::Main::default_mysqld_path= win_dflt_mysqld_path; @@ -262,10 +260,12 @@ static struct my_option my_long_options[] = 0, 0, GET_BOOL, NO_ARG, 0, 0, 1, 0, 0, 0 }, #endif +#ifndef __WIN__ { "socket", OPT_SOCKET, "Socket file to use for connection.", (gptr *) &Options::Main::socket_file_name, (gptr *) &Options::Main::socket_file_name, 0, GET_STR, REQUIRED_ARG, 0, 0, 0, 0, 0, 0 }, +#endif #ifdef __WIN__ { "standalone", OPT_STAND_ALONE, "Run the application in stand alone mode.", @@ -550,8 +550,6 @@ static int setup_windows_defaults() strxmov(win_dflt_password_file_name, dir_name, im_name, DFLT_PASSWD_FILE_EXT, NullS); strxmov(win_dflt_pid_file_name, dir_name, im_name, DFLT_PID_FILE_EXT, NullS); - strxmov(win_dflt_socket_file_name, dir_name, im_name, DFLT_SOCKET_FILE_EXT, - NullS); return 0; } diff --git a/server-tools/instance-manager/options.h b/server-tools/instance-manager/options.h index 5c54ff201b2..ac4f6507892 100644 --- a/server-tools/instance-manager/options.h +++ b/server-tools/instance-manager/options.h @@ -50,7 +50,9 @@ struct Options static bool is_forced_default_file; static const char *pid_file_name; +#ifndef __WIN__ static const char *socket_file_name; +#endif static const char *password_file_name; static const char *default_mysqld_path; static uint monitoring_interval; diff --git a/sql/item_sum.cc b/sql/item_sum.cc index 1c574cc872f..1dde6970823 100644 --- a/sql/item_sum.cc +++ b/sql/item_sum.cc @@ -1065,7 +1065,7 @@ longlong Item_sum_count::val_int() void Item_sum_count::cleanup() { DBUG_ENTER("Item_sum_count::cleanup"); - clear(); + count= 0; Item_sum_int::cleanup(); used_table_cache= ~(table_map) 0; DBUG_VOID_RETURN; diff --git a/sql/item_sum.h b/sql/item_sum.h index 0204e88a9e1..eb4c21bbe06 100644 --- a/sql/item_sum.h +++ b/sql/item_sum.h @@ -643,8 +643,8 @@ public: Field *create_tmp_field(bool group, TABLE *table, uint convert_blob_length); void cleanup() { - clear(); - Item_sum_num::cleanup(); + count= 0; + Item_sum_sum::cleanup(); } }; @@ -727,7 +727,8 @@ public: enum Item_result result_type () const { return REAL_RESULT; } void cleanup() { - clear(); + cur_dec= 0; + count= 0; Item_sum_num::cleanup(); } }; @@ -862,7 +863,7 @@ public: { decimals= 0; max_length=21; unsigned_flag= 1; maybe_null= null_value= 0; } void cleanup() { - clear(); + bits= reset_bits; Item_sum_int::cleanup(); } }; diff --git a/sql/sp_head.cc b/sql/sp_head.cc index a061ae12dd1..b31cf8b73bc 100644 --- a/sql/sp_head.cc +++ b/sql/sp_head.cc @@ -1029,8 +1029,7 @@ sp_head::execute(THD *thd) save_sql_mode= thd->variables.sql_mode; thd->variables.sql_mode= m_sql_mode; save_abort_on_warning= thd->abort_on_warning; - thd->abort_on_warning= - (m_sql_mode & (MODE_STRICT_TRANS_TABLES | MODE_STRICT_ALL_TABLES)); + thd->abort_on_warning= 0; /* It is also more efficient to save/restore current thd->lex once when diff --git a/sql/sql_yacc.yy b/sql/sql_yacc.yy index 05c57479c42..a6ae102fa0c 100644 --- a/sql/sql_yacc.yy +++ b/sql/sql_yacc.yy @@ -1724,15 +1724,20 @@ call: lex->value_list.empty(); sp_add_used_routine(lex, YYTHD, $2, TYPE_ENUM_PROCEDURE); } - '(' sp_cparam_list ')' {} + opt_sp_cparam_list {} ; /* CALL parameters */ -sp_cparam_list: +opt_sp_cparam_list: /* Empty */ - | sp_cparams + | '(' opt_sp_cparams ')' ; +opt_sp_cparams: + /* Empty */ + | sp_cparams + ; + sp_cparams: sp_cparams ',' expr { @@ -6822,7 +6827,7 @@ when_list2: /* Warning - may return NULL in case of incomplete SELECT */ table_ref: table_factor { $$=$1; } - | join_table { $$=$1; } + | join_table { LEX *lex= Lex; if (!($$= lex->current_select->nest_last_join(lex->thd))) @@ -6864,7 +6869,7 @@ join_table: | table_ref normal_join table_ref ON { - YYERROR_UNLESS($1 && ($$=$3)); + YYERROR_UNLESS($1 && $3); /* Change the current name resolution context to a local context. */ if (push_new_name_resolution_context(YYTHD, $1, $3)) YYABORT; @@ -6879,7 +6884,7 @@ join_table: | table_ref STRAIGHT_JOIN table_factor ON { - YYERROR_UNLESS($1 && ($$=$3)); + YYERROR_UNLESS($1 && $3); /* Change the current name resolution context to a local context. */ if (push_new_name_resolution_context(YYTHD, $1, $3)) YYABORT; |