Merge from mysql-5.5-runtime to mysql-5.5-bugteam
No conflicts
This commit is contained in:
commit
d293c4258e
@ -35,10 +35,23 @@ connection master1;
|
||||
send CALL test.p1();
|
||||
|
||||
connection master;
|
||||
# To make sure tha the call on master1 arrived at the get_lock
|
||||
sleep 1;
|
||||
# Make sure that the call on master1 arrived at the get_lock.
|
||||
let $wait_condition=
|
||||
select count(*) = 1 from information_schema.processlist
|
||||
where state = 'User lock' and
|
||||
info = 'SELECT get_lock("test", 100)';
|
||||
--source include/wait_condition.inc
|
||||
CALL test.p2();
|
||||
SELECT release_lock("test");
|
||||
|
||||
connection master1;
|
||||
# Reap CALL test.p1() to ensure that it has fully completed
|
||||
# before doing any selects on test.t1.
|
||||
--reap
|
||||
# Release lock acquired by it.
|
||||
SELECT release_lock("test");
|
||||
|
||||
connection master;
|
||||
SELECT * FROM test.t1;
|
||||
#show binlog events;
|
||||
--source include/wait_for_ndb_to_binlog.inc
|
||||
@ -51,6 +64,7 @@ DROP TABLE IF EXISTS test.t1;
|
||||
eval CREATE TABLE test.t1(a INT,PRIMARY KEY(a))ENGINE=$engine_type;
|
||||
CALL test.p2();
|
||||
CALL test.p1();
|
||||
SELECT release_lock("test");
|
||||
SELECT * FROM test.t1;
|
||||
|
||||
sync_slave_with_master;
|
||||
|
@ -1448,8 +1448,6 @@ CREATE USER 'userbug33464'@'localhost';
|
||||
GRANT CREATE ROUTINE ON dbbug33464.* TO 'userbug33464'@'localhost';
|
||||
|
||||
userbug33464@localhost dbbug33464
|
||||
DROP PROCEDURE IF EXISTS sp3;
|
||||
DROP FUNCTION IF EXISTS fn1;
|
||||
CREATE PROCEDURE sp3(v1 char(20))
|
||||
BEGIN
|
||||
SELECT * from dbbug33464.t6 where t6.f2= 'xyz';
|
||||
|
@ -1807,3 +1807,47 @@ USING (TABLE_SCHEMA, TABLE_NAME, COLUMN_NAME)
|
||||
WHERE COLUMNS.TABLE_SCHEMA = 'test'
|
||||
AND COLUMNS.TABLE_NAME = 't1';
|
||||
TABLE_SCHEMA TABLE_NAME COLUMN_NAME CONSTRAINT_CATALOG CONSTRAINT_SCHEMA CONSTRAINT_NAME TABLE_CATALOG ORDINAL_POSITION POSITION_IN_UNIQUE_CONSTRAINT REFERENCED_TABLE_SCHEMA REFERENCED_TABLE_NAME REFERENCED_COLUMN_NAME TABLE_CATALOG ORDINAL_POSITION COLUMN_DEFAULT IS_NULLABLE DATA_TYPE CHARACTER_MAXIMUM_LENGTH CHARACTER_OCTET_LENGTH NUMERIC_PRECISION NUMERIC_SCALE CHARACTER_SET_NAME COLLATION_NAME COLUMN_TYPE COLUMN_KEY EXTRA PRIVILEGES COLUMN_COMMENT
|
||||
#
|
||||
# A test case for Bug#56540 "Exception (crash) in sql_show.cc
|
||||
# during rqg_info_schema test on Windows"
|
||||
# Ensure that we never access memory of a closed table,
|
||||
# in particular, never access table->field[] array.
|
||||
# Before the fix, the below test case, produced
|
||||
# valgrind errors.
|
||||
#
|
||||
drop table if exists t1;
|
||||
drop view if exists v1;
|
||||
create table t1 (a int, b int);
|
||||
create view v1 as select t1.a, t1.b from t1;
|
||||
alter table t1 change b c int;
|
||||
lock table t1 read;
|
||||
# --> connection con1
|
||||
flush tables;
|
||||
# --> connection default
|
||||
select * from information_schema.views;
|
||||
TABLE_CATALOG def
|
||||
TABLE_SCHEMA test
|
||||
TABLE_NAME v1
|
||||
VIEW_DEFINITION select `test`.`t1`.`a` AS `a`,`test`.`t1`.`b` AS `b` from `test`.`t1`
|
||||
CHECK_OPTION NONE
|
||||
IS_UPDATABLE
|
||||
DEFINER root@localhost
|
||||
SECURITY_TYPE DEFINER
|
||||
CHARACTER_SET_CLIENT latin1
|
||||
COLLATION_CONNECTION latin1_swedish_ci
|
||||
Warnings:
|
||||
Level Warning
|
||||
Code 1356
|
||||
Message View 'test.v1' references invalid table(s) or column(s) or function(s) or definer/invoker of view lack rights to use them
|
||||
unlock tables;
|
||||
#
|
||||
# Cleanup.
|
||||
#
|
||||
# --> connection con1
|
||||
# Reaping 'flush tables'
|
||||
# --> connection default
|
||||
drop table t1;
|
||||
drop view v1;
|
||||
#
|
||||
# End of 5.5 tests
|
||||
#
|
||||
|
@ -704,3 +704,37 @@ SET DEBUG_SYNC="now SIGNAL query";
|
||||
# Connection default
|
||||
DROP EVENT e2;
|
||||
SET DEBUG_SYNC="RESET";
|
||||
#
|
||||
# Bug#55930 Assertion `thd->transaction.stmt.is_empty() ||
|
||||
# thd->in_sub_stmt || (thd->state..
|
||||
#
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(a INT) engine=InnoDB;
|
||||
INSERT INTO t1 VALUES (1), (2);
|
||||
# Connection con1
|
||||
SET SESSION lock_wait_timeout= 1;
|
||||
SET DEBUG_SYNC= 'ha_admin_open_ltable SIGNAL opti_recreate WAIT_FOR opti_analyze';
|
||||
# Sending:
|
||||
OPTIMIZE TABLE t1;
|
||||
# Connection con2
|
||||
SET DEBUG_SYNC= 'now WAIT_FOR opti_recreate';
|
||||
SET DEBUG_SYNC= 'after_lock_tables_takes_lock SIGNAL thrlock WAIT_FOR release_thrlock';
|
||||
# Sending:
|
||||
INSERT INTO t1 VALUES (3);
|
||||
# Connection default
|
||||
SET DEBUG_SYNC= 'now WAIT_FOR thrlock';
|
||||
SET DEBUG_SYNC= 'now SIGNAL opti_analyze';
|
||||
# Connection con1
|
||||
# Reaping: OPTIMIZE TABLE t1
|
||||
Table Op Msg_type Msg_text
|
||||
test.t1 optimize note Table does not support optimize, doing recreate + analyze instead
|
||||
test.t1 optimize error Lock wait timeout exceeded; try restarting transaction
|
||||
test.t1 optimize status Operation failed
|
||||
Warnings:
|
||||
Error 1205 Lock wait timeout exceeded; try restarting transaction
|
||||
SET DEBUG_SYNC= 'now SIGNAL release_thrlock';
|
||||
# Connection con2
|
||||
# Reaping: INSERT INTO t1 VALUES (3)
|
||||
# Connection default
|
||||
DROP TABLE t1;
|
||||
SET DEBUG_SYNC= 'RESET';
|
||||
|
@ -44,7 +44,7 @@ ERROR 42000: SELECT command denied to user 'user1'@'localhost' for table 't1'
|
||||
create procedure db1_secret.dummy() begin end;
|
||||
ERROR 42000: Access denied for user 'user1'@'localhost' to database 'db1_secret'
|
||||
drop procedure db1_secret.dummy;
|
||||
ERROR 42000: PROCEDURE db1_secret.dummy does not exist
|
||||
ERROR 42000: alter routine command denied to user 'user1'@'localhost' for routine 'db1_secret.dummy'
|
||||
drop procedure db1_secret.stamp;
|
||||
ERROR 42000: alter routine command denied to user 'user1'@'localhost' for routine 'db1_secret.stamp'
|
||||
drop function db1_secret.db;
|
||||
@ -58,7 +58,7 @@ ERROR 42000: SELECT command denied to user ''@'localhost' for table 't1'
|
||||
create procedure db1_secret.dummy() begin end;
|
||||
ERROR 42000: Access denied for user ''@'%' to database 'db1_secret'
|
||||
drop procedure db1_secret.dummy;
|
||||
ERROR 42000: PROCEDURE db1_secret.dummy does not exist
|
||||
ERROR 42000: alter routine command denied to user ''@'%' for routine 'db1_secret.dummy'
|
||||
drop procedure db1_secret.stamp;
|
||||
ERROR 42000: alter routine command denied to user ''@'%' for routine 'db1_secret.stamp'
|
||||
drop function db1_secret.db;
|
||||
@ -567,3 +567,28 @@ DROP USER 'tester';
|
||||
DROP USER 'Tester';
|
||||
DROP DATABASE B48872;
|
||||
End of 5.0 tests.
|
||||
#
|
||||
# Test for bug#57061 "User without privilege on routine can discover
|
||||
# its existence."
|
||||
#
|
||||
drop database if exists mysqltest_db;
|
||||
create database mysqltest_db;
|
||||
# Create user with no privileges on mysqltest_db database.
|
||||
create user bug57061_user@localhost;
|
||||
create function mysqltest_db.f1() returns int return 0;
|
||||
create procedure mysqltest_db.p1() begin end;
|
||||
# Connect as user 'bug57061_user@localhost'
|
||||
# Attempt to drop routine on which user doesn't have privileges
|
||||
# should result in the same 'access denied' type of error whether
|
||||
# routine exists or not.
|
||||
drop function if exists mysqltest_db.f_does_not_exist;
|
||||
ERROR 42000: alter routine command denied to user 'bug57061_user'@'localhost' for routine 'mysqltest_db.f_does_not_exist'
|
||||
drop procedure if exists mysqltest_db.p_does_not_exist;
|
||||
ERROR 42000: alter routine command denied to user 'bug57061_user'@'localhost' for routine 'mysqltest_db.p_does_not_exist'
|
||||
drop function if exists mysqltest_db.f1;
|
||||
ERROR 42000: alter routine command denied to user 'bug57061_user'@'localhost' for routine 'mysqltest_db.f1'
|
||||
drop procedure if exists mysqltest_db.p1;
|
||||
ERROR 42000: alter routine command denied to user 'bug57061_user'@'localhost' for routine 'mysqltest_db.p1'
|
||||
# Connection 'default'.
|
||||
drop user bug57061_user@localhost;
|
||||
drop database mysqltest_db;
|
||||
|
@ -110,10 +110,10 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege.
|
||||
--------------------------------------------------------------------------------
|
||||
grant create routine on db_storedproc_1.* to 'user_1'@'localhost';
|
||||
flush privileges;
|
||||
DROP PROCEDURE IF EXISTS db_storedproc_1.sp3;
|
||||
DROP FUNCTION IF EXISTS db_storedproc_1.fn1;
|
||||
|
||||
user_1@localhost db_storedproc_1
|
||||
DROP PROCEDURE IF EXISTS sp3;
|
||||
DROP FUNCTION IF EXISTS fn1;
|
||||
CREATE PROCEDURE sp3(v1 char(20))
|
||||
BEGIN
|
||||
SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz';
|
||||
|
@ -111,10 +111,10 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege.
|
||||
--------------------------------------------------------------------------------
|
||||
grant create routine on db_storedproc_1.* to 'user_1'@'localhost';
|
||||
flush privileges;
|
||||
DROP PROCEDURE IF EXISTS db_storedproc_1.sp3;
|
||||
DROP FUNCTION IF EXISTS db_storedproc_1.fn1;
|
||||
|
||||
user_1@localhost db_storedproc_1
|
||||
DROP PROCEDURE IF EXISTS sp3;
|
||||
DROP FUNCTION IF EXISTS fn1;
|
||||
CREATE PROCEDURE sp3(v1 char(20))
|
||||
BEGIN
|
||||
SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz';
|
||||
|
@ -111,10 +111,10 @@ Ensure that root always has the GRANT CREATE ROUTINE privilege.
|
||||
--------------------------------------------------------------------------------
|
||||
grant create routine on db_storedproc_1.* to 'user_1'@'localhost';
|
||||
flush privileges;
|
||||
DROP PROCEDURE IF EXISTS db_storedproc_1.sp3;
|
||||
DROP FUNCTION IF EXISTS db_storedproc_1.fn1;
|
||||
|
||||
user_1@localhost db_storedproc_1
|
||||
DROP PROCEDURE IF EXISTS sp3;
|
||||
DROP FUNCTION IF EXISTS fn1;
|
||||
CREATE PROCEDURE sp3(v1 char(20))
|
||||
BEGIN
|
||||
SELECT * from db_storedproc_1.t6 where t6.f2= 'xyz';
|
||||
|
@ -117,15 +117,15 @@ create user 'user_1'@'localhost';
|
||||
grant create routine on db_storedproc_1.* to 'user_1'@'localhost';
|
||||
flush privileges;
|
||||
|
||||
--disable_warnings
|
||||
DROP PROCEDURE IF EXISTS db_storedproc_1.sp3;
|
||||
DROP FUNCTION IF EXISTS db_storedproc_1.fn1;
|
||||
--enable_warnings
|
||||
|
||||
# disconnect default;
|
||||
connect (user2, localhost, user_1, , db_storedproc_1);
|
||||
--source suite/funcs_1/include/show_connection.inc
|
||||
|
||||
--disable_warnings
|
||||
DROP PROCEDURE IF EXISTS sp3;
|
||||
DROP FUNCTION IF EXISTS fn1;
|
||||
--enable_warnings
|
||||
|
||||
delimiter //;
|
||||
CREATE PROCEDURE sp3(v1 char(20))
|
||||
BEGIN
|
||||
|
@ -26,6 +26,11 @@ CALL test.p2();
|
||||
SELECT release_lock("test");
|
||||
release_lock("test")
|
||||
1
|
||||
get_lock("test", 100)
|
||||
1
|
||||
SELECT release_lock("test");
|
||||
release_lock("test")
|
||||
1
|
||||
SELECT * FROM test.t1;
|
||||
a
|
||||
5
|
||||
@ -37,7 +42,10 @@ CREATE TABLE test.t1(a INT,PRIMARY KEY(a))ENGINE=INNODB;
|
||||
CALL test.p2();
|
||||
CALL test.p1();
|
||||
get_lock("test", 100)
|
||||
0
|
||||
1
|
||||
SELECT release_lock("test");
|
||||
release_lock("test")
|
||||
1
|
||||
SELECT * FROM test.t1;
|
||||
a
|
||||
8
|
||||
|
@ -1419,11 +1419,6 @@ GRANT CREATE ROUTINE ON dbbug33464.* TO 'userbug33464'@'localhost';
|
||||
connect (connbug33464, localhost, userbug33464, , dbbug33464);
|
||||
--source suite/funcs_1/include/show_connection.inc
|
||||
|
||||
--disable_warnings
|
||||
DROP PROCEDURE IF EXISTS sp3;
|
||||
DROP FUNCTION IF EXISTS fn1;
|
||||
--enable_warnings
|
||||
|
||||
delimiter //;
|
||||
CREATE PROCEDURE sp3(v1 char(20))
|
||||
BEGIN
|
||||
|
@ -1555,3 +1555,56 @@ WHERE COLUMNS.TABLE_SCHEMA = 'test'
|
||||
AND COLUMNS.TABLE_NAME = 't1';
|
||||
|
||||
|
||||
--echo #
|
||||
--echo # A test case for Bug#56540 "Exception (crash) in sql_show.cc
|
||||
--echo # during rqg_info_schema test on Windows"
|
||||
--echo # Ensure that we never access memory of a closed table,
|
||||
--echo # in particular, never access table->field[] array.
|
||||
--echo # Before the fix, the below test case, produced
|
||||
--echo # valgrind errors.
|
||||
--echo #
|
||||
|
||||
--disable_warnings
|
||||
drop table if exists t1;
|
||||
drop view if exists v1;
|
||||
--enable_warnings
|
||||
|
||||
create table t1 (a int, b int);
|
||||
create view v1 as select t1.a, t1.b from t1;
|
||||
alter table t1 change b c int;
|
||||
lock table t1 read;
|
||||
connect(con1, localhost, root,,);
|
||||
--echo # --> connection con1
|
||||
connection con1;
|
||||
send flush tables;
|
||||
--echo # --> connection default
|
||||
connection default;
|
||||
let $wait_condition=
|
||||
select count(*) = 1 from information_schema.processlist
|
||||
where state = "Waiting for table flush" and
|
||||
info = "flush tables";
|
||||
--source include/wait_condition.inc
|
||||
--vertical_results
|
||||
select * from information_schema.views;
|
||||
--horizontal_results
|
||||
unlock tables;
|
||||
|
||||
--echo #
|
||||
--echo # Cleanup.
|
||||
--echo #
|
||||
|
||||
--echo # --> connection con1
|
||||
connection con1;
|
||||
--echo # Reaping 'flush tables'
|
||||
reap;
|
||||
disconnect con1;
|
||||
--source include/wait_until_disconnected.inc
|
||||
--echo # --> connection default
|
||||
connection default;
|
||||
drop table t1;
|
||||
drop view v1;
|
||||
|
||||
|
||||
--echo #
|
||||
--echo # End of 5.5 tests
|
||||
--echo #
|
||||
|
@ -1023,6 +1023,61 @@ DROP EVENT e2;
|
||||
SET DEBUG_SYNC="RESET";
|
||||
|
||||
|
||||
--echo #
|
||||
--echo # Bug#55930 Assertion `thd->transaction.stmt.is_empty() ||
|
||||
--echo # thd->in_sub_stmt || (thd->state..
|
||||
--echo #
|
||||
|
||||
--disable_warnings
|
||||
DROP TABLE IF EXISTS t1;
|
||||
--enable_warnings
|
||||
|
||||
CREATE TABLE t1(a INT) engine=InnoDB;
|
||||
INSERT INTO t1 VALUES (1), (2);
|
||||
|
||||
connect (con1, localhost, root);
|
||||
connect (con2, localhost, root);
|
||||
|
||||
--echo # Connection con1
|
||||
connection con1;
|
||||
SET SESSION lock_wait_timeout= 1;
|
||||
SET DEBUG_SYNC= 'ha_admin_open_ltable SIGNAL opti_recreate WAIT_FOR opti_analyze';
|
||||
--echo # Sending:
|
||||
--send OPTIMIZE TABLE t1
|
||||
|
||||
--echo # Connection con2
|
||||
connection con2;
|
||||
SET DEBUG_SYNC= 'now WAIT_FOR opti_recreate';
|
||||
SET DEBUG_SYNC= 'after_lock_tables_takes_lock SIGNAL thrlock WAIT_FOR release_thrlock';
|
||||
--echo # Sending:
|
||||
--send INSERT INTO t1 VALUES (3)
|
||||
|
||||
--echo # Connection default
|
||||
connection default;
|
||||
SET DEBUG_SYNC= 'now WAIT_FOR thrlock';
|
||||
SET DEBUG_SYNC= 'now SIGNAL opti_analyze';
|
||||
|
||||
--echo # Connection con1
|
||||
connection con1;
|
||||
--echo # Reaping: OPTIMIZE TABLE t1
|
||||
--reap
|
||||
SET DEBUG_SYNC= 'now SIGNAL release_thrlock';
|
||||
disconnect con1;
|
||||
--source include/wait_until_disconnected.inc
|
||||
|
||||
--echo # Connection con2
|
||||
connection con2;
|
||||
--echo # Reaping: INSERT INTO t1 VALUES (3)
|
||||
--reap
|
||||
disconnect con2;
|
||||
--source include/wait_until_disconnected.inc
|
||||
|
||||
--echo # Connection default
|
||||
connection default;
|
||||
DROP TABLE t1;
|
||||
SET DEBUG_SYNC= 'RESET';
|
||||
|
||||
|
||||
# Check that all connections opened by test cases in this file are really
|
||||
# gone so execution of other tests won't be affected by their presence.
|
||||
--source include/wait_until_count_sessions.inc
|
||||
|
@ -82,7 +82,7 @@ select * from db1_secret.t1;
|
||||
# ...and not this
|
||||
--error ER_DBACCESS_DENIED_ERROR
|
||||
create procedure db1_secret.dummy() begin end;
|
||||
--error ER_SP_DOES_NOT_EXIST
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop procedure db1_secret.dummy;
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop procedure db1_secret.stamp;
|
||||
@ -106,7 +106,7 @@ select * from db1_secret.t1;
|
||||
# ...and not this
|
||||
--error ER_DBACCESS_DENIED_ERROR
|
||||
create procedure db1_secret.dummy() begin end;
|
||||
--error ER_SP_DOES_NOT_EXIST
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop procedure db1_secret.dummy;
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop procedure db1_secret.stamp;
|
||||
@ -926,6 +926,39 @@ DROP DATABASE B48872;
|
||||
|
||||
--echo End of 5.0 tests.
|
||||
|
||||
|
||||
--echo #
|
||||
--echo # Test for bug#57061 "User without privilege on routine can discover
|
||||
--echo # its existence."
|
||||
--echo #
|
||||
--disable_warnings
|
||||
drop database if exists mysqltest_db;
|
||||
--enable_warnings
|
||||
create database mysqltest_db;
|
||||
--echo # Create user with no privileges on mysqltest_db database.
|
||||
create user bug57061_user@localhost;
|
||||
create function mysqltest_db.f1() returns int return 0;
|
||||
create procedure mysqltest_db.p1() begin end;
|
||||
--echo # Connect as user 'bug57061_user@localhost'
|
||||
connect (conn1, localhost, bug57061_user,,);
|
||||
--echo # Attempt to drop routine on which user doesn't have privileges
|
||||
--echo # should result in the same 'access denied' type of error whether
|
||||
--echo # routine exists or not.
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop function if exists mysqltest_db.f_does_not_exist;
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop procedure if exists mysqltest_db.p_does_not_exist;
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop function if exists mysqltest_db.f1;
|
||||
--error ER_PROCACCESS_DENIED_ERROR
|
||||
drop procedure if exists mysqltest_db.p1;
|
||||
--echo # Connection 'default'.
|
||||
connection default;
|
||||
disconnect conn1;
|
||||
drop user bug57061_user@localhost;
|
||||
drop database mysqltest_db;
|
||||
|
||||
|
||||
# Wait till all disconnects are completed
|
||||
--source include/wait_until_count_sessions.inc
|
||||
|
||||
|
38
sql/sp.cc
38
sql/sp.cc
@ -779,6 +779,9 @@ db_load_routine(THD *thd, int type, sp_name *name, sp_head **sphp,
|
||||
|
||||
int ret= 0;
|
||||
|
||||
if (check_stack_overrun(thd, STACK_MIN_SIZE, (uchar*)&ret))
|
||||
return TRUE;
|
||||
|
||||
thd->lex= &newlex;
|
||||
newlex.current_select= NULL;
|
||||
|
||||
@ -1505,6 +1508,9 @@ sp_find_routine(THD *thd, int type, sp_name *name, sp_cache **cp,
|
||||
(int) name->m_name.length, name->m_name.str,
|
||||
type, cache_only));
|
||||
|
||||
if (check_stack_overrun(thd, STACK_MIN_SIZE, (uchar*)&depth))
|
||||
return NULL;
|
||||
|
||||
if ((sp= sp_cache_lookup(cp, name)))
|
||||
{
|
||||
ulong level;
|
||||
@ -1636,38 +1642,6 @@ sp_exist_routines(THD *thd, TABLE_LIST *routines, bool any)
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
Check if a routine exists in the mysql.proc table, without actually
|
||||
parsing the definition. (Used for dropping).
|
||||
|
||||
@param thd thread context
|
||||
@param name name of procedure
|
||||
|
||||
@retval
|
||||
0 Success
|
||||
@retval
|
||||
non-0 Error; SP_OPEN_TABLE_FAILED or SP_KEY_NOT_FOUND
|
||||
*/
|
||||
|
||||
int
|
||||
sp_routine_exists_in_table(THD *thd, int type, sp_name *name)
|
||||
{
|
||||
TABLE *table;
|
||||
int ret;
|
||||
Open_tables_backup open_tables_state_backup;
|
||||
|
||||
if (!(table= open_proc_table_for_read(thd, &open_tables_state_backup)))
|
||||
ret= SP_OPEN_TABLE_FAILED;
|
||||
else
|
||||
{
|
||||
if ((ret= db_find_routine_aux(thd, type, name, table)) != SP_OK)
|
||||
ret= SP_KEY_NOT_FOUND;
|
||||
close_system_tables(thd, &open_tables_state_backup);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
extern "C" uchar* sp_sroutine_key(const uchar *ptr, size_t *plen,
|
||||
my_bool first)
|
||||
{
|
||||
|
3
sql/sp.h
3
sql/sp.h
@ -100,9 +100,6 @@ sp_cache_routine(THD *thd, int type, sp_name *name,
|
||||
bool
|
||||
sp_exist_routines(THD *thd, TABLE_LIST *procs, bool any);
|
||||
|
||||
int
|
||||
sp_routine_exists_in_table(THD *thd, int type, sp_name *name);
|
||||
|
||||
bool
|
||||
sp_show_create_routine(THD *thd, int type, sp_name *name);
|
||||
|
||||
|
@ -1233,11 +1233,8 @@ sp_head::execute(THD *thd)
|
||||
The same with db_load_routine() required circa 7k bytes and
|
||||
14k bytes accordingly. Hence, here we book the stack with some
|
||||
reasonable margin.
|
||||
|
||||
Reverting back to 8 * STACK_MIN_SIZE until further fix.
|
||||
8 * STACK_MIN_SIZE is required on some exotic platforms.
|
||||
*/
|
||||
if (check_stack_overrun(thd, 8 * STACK_MIN_SIZE, (uchar*)&old_packet))
|
||||
if (check_stack_overrun(thd, STACK_MIN_SIZE, (uchar*)&old_packet))
|
||||
DBUG_RETURN(TRUE);
|
||||
|
||||
/* init per-instruction memroot */
|
||||
@ -2902,6 +2899,9 @@ sp_lex_keeper::reset_lex_and_exec_core(THD *thd, uint *nextp,
|
||||
It's merged with the saved parent's value at the exit of this func.
|
||||
*/
|
||||
bool parent_modified_non_trans_table= thd->transaction.stmt.modified_non_trans_table;
|
||||
if (check_stack_overrun(thd, STACK_MIN_SIZE, (uchar*)&parent_modified_non_trans_table))
|
||||
DBUG_RETURN(TRUE);
|
||||
|
||||
thd->transaction.stmt.modified_non_trans_table= FALSE;
|
||||
DBUG_ASSERT(!thd->derived_tables);
|
||||
DBUG_ASSERT(thd->change_list.is_empty());
|
||||
@ -3057,6 +3057,9 @@ sp_instr_stmt::execute(THD *thd, uint *nextp)
|
||||
DBUG_ENTER("sp_instr_stmt::execute");
|
||||
DBUG_PRINT("info", ("command: %d", m_lex_keeper.sql_command()));
|
||||
|
||||
if (check_stack_overrun(thd, STACK_MIN_SIZE, (uchar*)&res))
|
||||
DBUG_RETURN(TRUE);
|
||||
|
||||
query= thd->query();
|
||||
query_length= thd->query_length();
|
||||
#if defined(ENABLED_PROFILING)
|
||||
|
@ -2902,8 +2902,12 @@ retry_share:
|
||||
*/
|
||||
if (check_and_update_table_version(thd, table_list, share))
|
||||
goto err_unlock;
|
||||
if (table_list->i_s_requested_object & OPEN_TABLE_ONLY)
|
||||
if (table_list->i_s_requested_object & OPEN_TABLE_ONLY)
|
||||
{
|
||||
my_error(ER_NO_SUCH_TABLE, MYF(0), table_list->db,
|
||||
table_list->table_name);
|
||||
goto err_unlock;
|
||||
}
|
||||
|
||||
/* Open view */
|
||||
if (open_new_frm(thd, share, alias,
|
||||
@ -2931,7 +2935,11 @@ retry_share:
|
||||
*/
|
||||
|
||||
if (table_list->i_s_requested_object & OPEN_VIEW_ONLY)
|
||||
{
|
||||
my_error(ER_NO_SUCH_TABLE, MYF(0), table_list->db,
|
||||
table_list->table_name);
|
||||
goto err_unlock;
|
||||
}
|
||||
|
||||
if (!(flags & MYSQL_OPEN_IGNORE_FLUSH))
|
||||
{
|
||||
@ -5319,7 +5327,11 @@ TABLE *open_ltable(THD *thd, TABLE_LIST *table_list, thr_lock_type lock_type,
|
||||
|
||||
end:
|
||||
if (table == NULL)
|
||||
{
|
||||
if (!thd->in_sub_stmt)
|
||||
trans_rollback_stmt(thd);
|
||||
close_thread_tables(thd);
|
||||
}
|
||||
thd_proc_info(thd, 0);
|
||||
DBUG_RETURN(table);
|
||||
}
|
||||
|
@ -4032,49 +4032,39 @@ create_sp_error:
|
||||
int sp_result;
|
||||
int type= (lex->sql_command == SQLCOM_DROP_PROCEDURE ?
|
||||
TYPE_ENUM_PROCEDURE : TYPE_ENUM_FUNCTION);
|
||||
char *db= lex->spname->m_db.str;
|
||||
char *name= lex->spname->m_name.str;
|
||||
|
||||
/*
|
||||
@todo: here we break the metadata locking protocol by
|
||||
looking up the information about the routine without
|
||||
a metadata lock. Rewrite this piece to make sp_drop_routine
|
||||
return whether the routine existed or not.
|
||||
*/
|
||||
sp_result= sp_routine_exists_in_table(thd, type, lex->spname);
|
||||
thd->warning_info->opt_clear_warning_info(thd->query_id);
|
||||
if (sp_result == SP_OK)
|
||||
{
|
||||
char *db= lex->spname->m_db.str;
|
||||
char *name= lex->spname->m_name.str;
|
||||
if (check_routine_access(thd, ALTER_PROC_ACL, db, name,
|
||||
lex->sql_command == SQLCOM_DROP_PROCEDURE, 0))
|
||||
goto error;
|
||||
|
||||
if (check_routine_access(thd, ALTER_PROC_ACL, db, name,
|
||||
lex->sql_command == SQLCOM_DROP_PROCEDURE, 0))
|
||||
goto error;
|
||||
|
||||
/* Conditionally writes to binlog */
|
||||
sp_result= sp_drop_routine(thd, type, lex->spname);
|
||||
/* Conditionally writes to binlog */
|
||||
sp_result= sp_drop_routine(thd, type, lex->spname);
|
||||
|
||||
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
||||
/*
|
||||
We're going to issue an implicit REVOKE statement.
|
||||
It takes metadata locks and updates system tables.
|
||||
Make sure that sp_create_routine() did not leave any
|
||||
locks in the MDL context, so there is no risk to
|
||||
deadlock.
|
||||
*/
|
||||
close_mysql_tables(thd);
|
||||
/*
|
||||
We're going to issue an implicit REVOKE statement.
|
||||
It takes metadata locks and updates system tables.
|
||||
Make sure that sp_create_routine() did not leave any
|
||||
locks in the MDL context, so there is no risk to
|
||||
deadlock.
|
||||
*/
|
||||
close_mysql_tables(thd);
|
||||
|
||||
if (sp_automatic_privileges && !opt_noacl &&
|
||||
sp_revoke_privileges(thd, db, name,
|
||||
lex->sql_command == SQLCOM_DROP_PROCEDURE))
|
||||
{
|
||||
push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
|
||||
ER_PROC_AUTO_REVOKE_FAIL,
|
||||
ER(ER_PROC_AUTO_REVOKE_FAIL));
|
||||
/* If this happens, an error should have been reported. */
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
if (sp_result != SP_KEY_NOT_FOUND &&
|
||||
sp_automatic_privileges && !opt_noacl &&
|
||||
sp_revoke_privileges(thd, db, name,
|
||||
lex->sql_command == SQLCOM_DROP_PROCEDURE))
|
||||
{
|
||||
push_warning(thd, MYSQL_ERROR::WARN_LEVEL_WARN,
|
||||
ER_PROC_AUTO_REVOKE_FAIL,
|
||||
ER(ER_PROC_AUTO_REVOKE_FAIL));
|
||||
/* If this happens, an error should have been reported. */
|
||||
goto error;
|
||||
}
|
||||
#endif
|
||||
|
||||
res= sp_result;
|
||||
switch (sp_result) {
|
||||
case SP_OK:
|
||||
@ -5128,10 +5118,17 @@ bool check_stack_overrun(THD *thd, long margin,
|
||||
if ((stack_used=used_stack(thd->thread_stack,(char*) &stack_used)) >=
|
||||
(long) (my_thread_stack_size - margin))
|
||||
{
|
||||
char ebuff[MYSQL_ERRMSG_SIZE];
|
||||
my_snprintf(ebuff, sizeof(ebuff), ER(ER_STACK_OVERRUN_NEED_MORE),
|
||||
stack_used, my_thread_stack_size, margin);
|
||||
my_message(ER_STACK_OVERRUN_NEED_MORE, ebuff, MYF(ME_FATALERROR));
|
||||
/*
|
||||
Do not use stack for the message buffer to ensure correct
|
||||
behaviour in cases we have close to no stack left.
|
||||
*/
|
||||
char* ebuff= new char[MYSQL_ERRMSG_SIZE];
|
||||
if (ebuff) {
|
||||
my_snprintf(ebuff, MYSQL_ERRMSG_SIZE, ER(ER_STACK_OVERRUN_NEED_MORE),
|
||||
stack_used, my_thread_stack_size, margin);
|
||||
my_message(ER_STACK_OVERRUN_NEED_MORE, ebuff, MYF(ME_FATALERROR));
|
||||
delete [] ebuff;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
#ifndef DBUG_OFF
|
||||
@ -7220,6 +7217,9 @@ bool parse_sql(THD *thd,
|
||||
|
||||
Object_creation_ctx *backup_ctx= NULL;
|
||||
|
||||
if (check_stack_overrun(thd, 2 * STACK_MIN_SIZE, (uchar*)&backup_ctx))
|
||||
return TRUE;
|
||||
|
||||
if (creation_ctx)
|
||||
backup_ctx= creation_ctx->set_n_backup(thd);
|
||||
|
||||
|
@ -4934,18 +4934,29 @@ static int get_schema_views_record(THD *thd, TABLE_LIST *tables,
|
||||
else
|
||||
table->field[4]->store(STRING_WITH_LEN("NONE"), cs);
|
||||
|
||||
if (table->pos_in_table_list->table_open_method &
|
||||
OPEN_FULL_TABLE)
|
||||
/*
|
||||
Only try to fill in the information about view updatability
|
||||
if it is requested as part of the top-level query (i.e.
|
||||
it's select * from i_s.views, as opposed to, say, select
|
||||
security_type from i_s.views). Do not try to access the
|
||||
underlying tables if there was an error when opening the
|
||||
view: all underlying tables are released back to the table
|
||||
definition cache on error inside open_normal_and_derived_tables().
|
||||
If a field is not assigned explicitly, it defaults to NULL.
|
||||
*/
|
||||
if (res == FALSE &&
|
||||
table->pos_in_table_list->table_open_method & OPEN_FULL_TABLE)
|
||||
{
|
||||
updatable_view= 0;
|
||||
if (tables->algorithm != VIEW_ALGORITHM_TMPTABLE)
|
||||
{
|
||||
/*
|
||||
We should use tables->view->select_lex.item_list here and
|
||||
can not use Field_iterator_view because the view always uses
|
||||
temporary algorithm during opening for I_S and
|
||||
TABLE_LIST fields 'field_translation' & 'field_translation_end'
|
||||
are uninitialized is this case.
|
||||
We should use tables->view->select_lex.item_list here
|
||||
and can not use Field_iterator_view because the view
|
||||
always uses temporary algorithm during opening for I_S
|
||||
and TABLE_LIST fields 'field_translation'
|
||||
& 'field_translation_end' are uninitialized is this
|
||||
case.
|
||||
*/
|
||||
List<Item> *fields= &tables->view->select_lex.item_list;
|
||||
List_iterator<Item> it(*fields);
|
||||
|
@ -104,7 +104,6 @@ bool mysqld_show_storage_engines(THD *thd);
|
||||
bool mysqld_show_authors(THD *thd);
|
||||
bool mysqld_show_contributors(THD *thd);
|
||||
bool mysqld_show_privileges(THD *thd);
|
||||
bool mysqld_show_column_types(THD *thd);
|
||||
char *make_backup_log_name(char *buff, const char *name, const char* log_ext);
|
||||
void calc_sum_of_all_status(STATUS_VAR *to);
|
||||
void append_definer(THD *thd, String *buffer, const LEX_STRING *definer_user,
|
||||
|
Loading…
x
Reference in New Issue
Block a user