mirror of
https://github.com/MariaDB/server.git
synced 2025-07-30 16:24:05 +03:00
fixed environment restoring in case of error during SP function execution (BUG#9503)
#define macro improvement mysql-test/r/sp-security.result: BUG#9503: reseting correct parameters of thread after error in SP function mysql-test/t/sp-security.test: BUG#9503: reseting correct parameters of thread after error in SP function sql/item_func.cc: fixed environment restoring in case of error during SP function execution sql/protocol.cc: added debug print sql/sql_class.h: fixed #defines to force them to be alvaise in piar, and variable name made more complex for accident repeating in other code
This commit is contained in:
@ -194,3 +194,20 @@ use test;
|
|||||||
drop database sptest;
|
drop database sptest;
|
||||||
delete from mysql.user where user='usera' or user='userb' or user='userc';
|
delete from mysql.user where user='usera' or user='userb' or user='userc';
|
||||||
delete from mysql.procs_priv where user='usera' or user='userb' or user='userc';
|
delete from mysql.procs_priv where user='usera' or user='userb' or user='userc';
|
||||||
|
drop function if exists bug_9503;
|
||||||
|
create database mysqltest//
|
||||||
|
use mysqltest//
|
||||||
|
create table t1 (s1 int)//
|
||||||
|
grant select on t1 to user1@localhost//
|
||||||
|
create function bug_9503 () returns int sql security invoker begin declare v int;
|
||||||
|
select min(s1) into v from t1; return v; end//
|
||||||
|
use mysqltest;
|
||||||
|
select bug_9503();
|
||||||
|
ERROR 42000: execute command denied to user 'user1'@'localhost' for routine 'mysqltest.bug_9503'
|
||||||
|
grant execute on function bug_9503 to user1@localhost;
|
||||||
|
do 1;
|
||||||
|
use test;
|
||||||
|
REVOKE ALL PRIVILEGES, GRANT OPTION FROM user1@localhost;
|
||||||
|
drop function bug_9503;
|
||||||
|
use test;
|
||||||
|
drop database mysqltest;
|
||||||
|
@ -304,3 +304,39 @@ drop database sptest;
|
|||||||
delete from mysql.user where user='usera' or user='userb' or user='userc';
|
delete from mysql.user where user='usera' or user='userb' or user='userc';
|
||||||
delete from mysql.procs_priv where user='usera' or user='userb' or user='userc';
|
delete from mysql.procs_priv where user='usera' or user='userb' or user='userc';
|
||||||
|
|
||||||
|
#
|
||||||
|
# BUG#9503: reseting correct parameters of thread after error in SP function
|
||||||
|
#
|
||||||
|
connect (root,localhost,root,,test);
|
||||||
|
connection root;
|
||||||
|
|
||||||
|
--disable_warnings
|
||||||
|
drop function if exists bug_9503;
|
||||||
|
--enable_warnings
|
||||||
|
delimiter //;
|
||||||
|
create database mysqltest//
|
||||||
|
use mysqltest//
|
||||||
|
create table t1 (s1 int)//
|
||||||
|
grant select on t1 to user1@localhost//
|
||||||
|
create function bug_9503 () returns int sql security invoker begin declare v int;
|
||||||
|
select min(s1) into v from t1; return v; end//
|
||||||
|
delimiter ;//
|
||||||
|
|
||||||
|
connect (user1,localhost,user1,,test);
|
||||||
|
connection user1;
|
||||||
|
use mysqltest;
|
||||||
|
-- error 1370
|
||||||
|
select bug_9503();
|
||||||
|
|
||||||
|
connection root;
|
||||||
|
grant execute on function bug_9503 to user1@localhost;
|
||||||
|
|
||||||
|
connection user1;
|
||||||
|
do 1;
|
||||||
|
use test;
|
||||||
|
|
||||||
|
connection root;
|
||||||
|
REVOKE ALL PRIVILEGES, GRANT OPTION FROM user1@localhost;
|
||||||
|
drop function bug_9503;
|
||||||
|
use test;
|
||||||
|
drop database mysqltest;
|
||||||
|
@ -4807,42 +4807,37 @@ Item_func_sp::execute(Item **itp)
|
|||||||
DBUG_ENTER("Item_func_sp::execute");
|
DBUG_ENTER("Item_func_sp::execute");
|
||||||
THD *thd= current_thd;
|
THD *thd= current_thd;
|
||||||
ulong old_client_capabilites;
|
ulong old_client_capabilites;
|
||||||
int res;
|
int res= -1;
|
||||||
bool save_in_sub_stmt= thd->transaction.in_sub_stmt;
|
bool save_in_sub_stmt= thd->transaction.in_sub_stmt;
|
||||||
|
my_bool nsok;
|
||||||
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
||||||
st_sp_security_context save_ctx;
|
st_sp_security_context save_ctx;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (! m_sp)
|
if (! m_sp && ! (m_sp= sp_find_function(thd, m_name, TRUE)))
|
||||||
{
|
{
|
||||||
if (!(m_sp= sp_find_function(thd, m_name, TRUE)))
|
my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "FUNCTION", m_name->m_qname.str);
|
||||||
{
|
goto error;
|
||||||
my_error(ER_SP_DOES_NOT_EXIST, MYF(0), "FUNCTION", m_name->m_qname.str);
|
|
||||||
DBUG_RETURN(-1);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
old_client_capabilites= thd->client_capabilities;
|
old_client_capabilites= thd->client_capabilities;
|
||||||
thd->client_capabilities &= ~CLIENT_MULTI_RESULTS;
|
thd->client_capabilities &= ~CLIENT_MULTI_RESULTS;
|
||||||
|
|
||||||
#ifndef EMBEDDED_LIBRARY
|
#ifndef EMBEDDED_LIBRARY
|
||||||
my_bool nsok= thd->net.no_send_ok;
|
nsok= thd->net.no_send_ok;
|
||||||
thd->net.no_send_ok= TRUE;
|
thd->net.no_send_ok= TRUE;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
res= -1;
|
||||||
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
||||||
if (check_routine_access(thd, EXECUTE_ACL,
|
if (check_routine_access(thd, EXECUTE_ACL,
|
||||||
m_sp->m_db.str, m_sp->m_name.str, 0, 0))
|
m_sp->m_db.str, m_sp->m_name.str, 0, 0))
|
||||||
DBUG_RETURN(-1);
|
goto error_check;
|
||||||
sp_change_security_context(thd, m_sp, &save_ctx);
|
sp_change_security_context(thd, m_sp, &save_ctx);
|
||||||
if (save_ctx.changed &&
|
if (save_ctx.changed &&
|
||||||
check_routine_access(thd, EXECUTE_ACL,
|
check_routine_access(thd, EXECUTE_ACL,
|
||||||
m_sp->m_db.str, m_sp->m_name.str, 0, 0))
|
m_sp->m_db.str, m_sp->m_name.str, 0, 0))
|
||||||
{
|
goto error_check;
|
||||||
sp_restore_security_context(thd, m_sp, &save_ctx);
|
|
||||||
thd->client_capabilities|= old_client_capabilites & CLIENT_MULTI_RESULTS;
|
|
||||||
DBUG_RETURN(-1);
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
/*
|
/*
|
||||||
Like for SPs, we don't binlog the substatements. If the statement which
|
Like for SPs, we don't binlog the substatements. If the statement which
|
||||||
@ -4850,6 +4845,7 @@ Item_func_sp::execute(Item **itp)
|
|||||||
it's not (e.g. SELECT myfunc()) it won't be binlogged (documented known
|
it's not (e.g. SELECT myfunc()) it won't be binlogged (documented known
|
||||||
problem).
|
problem).
|
||||||
*/
|
*/
|
||||||
|
|
||||||
tmp_disable_binlog(thd); /* don't binlog the substatements */
|
tmp_disable_binlog(thd); /* don't binlog the substatements */
|
||||||
thd->transaction.in_sub_stmt= TRUE;
|
thd->transaction.in_sub_stmt= TRUE;
|
||||||
|
|
||||||
@ -4864,16 +4860,21 @@ Item_func_sp::execute(Item **itp)
|
|||||||
ER_FAILED_ROUTINE_BREAK_BINLOG,
|
ER_FAILED_ROUTINE_BREAK_BINLOG,
|
||||||
ER(ER_FAILED_ROUTINE_BREAK_BINLOG));
|
ER(ER_FAILED_ROUTINE_BREAK_BINLOG));
|
||||||
|
|
||||||
|
error_check_ctx:
|
||||||
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
#ifndef NO_EMBEDDED_ACCESS_CHECKS
|
||||||
sp_restore_security_context(thd, m_sp, &save_ctx);
|
sp_restore_security_context(thd, m_sp, &save_ctx);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
thd->client_capabilities|= old_client_capabilites & CLIENT_MULTI_RESULTS;
|
||||||
|
|
||||||
|
error_check:
|
||||||
#ifndef EMBEDDED_LIBRARY
|
#ifndef EMBEDDED_LIBRARY
|
||||||
thd->net.no_send_ok= nsok;
|
thd->net.no_send_ok= nsok;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
thd->client_capabilities|= old_client_capabilites & CLIENT_MULTI_RESULTS;
|
thd->client_capabilities|= old_client_capabilites & CLIENT_MULTI_RESULTS;
|
||||||
|
|
||||||
|
error:
|
||||||
DBUG_RETURN(res);
|
DBUG_RETURN(res);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -294,7 +294,12 @@ send_ok(THD *thd, ha_rows affected_rows, ulonglong id, const char *message)
|
|||||||
DBUG_ENTER("send_ok");
|
DBUG_ENTER("send_ok");
|
||||||
|
|
||||||
if (net->no_send_ok || !net->vio) // hack for re-parsing queries
|
if (net->no_send_ok || !net->vio) // hack for re-parsing queries
|
||||||
|
{
|
||||||
|
DBUG_PRINT("info", ("no send ok: %s, vio present: %s",
|
||||||
|
(net->no_send_ok ? "YES" : "NO"),
|
||||||
|
(net->vio ? "YES" : "NO")));
|
||||||
DBUG_VOID_RETURN;
|
DBUG_VOID_RETURN;
|
||||||
|
}
|
||||||
|
|
||||||
buff[0]=0; // No fields
|
buff[0]=0; // No fields
|
||||||
pos=net_store_length(buff+1,(ulonglong) affected_rows);
|
pos=net_store_length(buff+1,(ulonglong) affected_rows);
|
||||||
|
@ -1433,10 +1433,10 @@ public:
|
|||||||
};
|
};
|
||||||
|
|
||||||
#define tmp_disable_binlog(A) \
|
#define tmp_disable_binlog(A) \
|
||||||
ulong save_options= (A)->options; \
|
{ulong tmp_disable_binlog__save_options= (A)->options; \
|
||||||
(A)->options&= ~OPTION_BIN_LOG;
|
(A)->options&= ~OPTION_BIN_LOG
|
||||||
|
|
||||||
#define reenable_binlog(A) (A)->options= save_options;
|
#define reenable_binlog(A) (A)->options= tmp_disable_binlog__save_options;}
|
||||||
|
|
||||||
/* Flags for the THD::system_thread (bitmap) variable */
|
/* Flags for the THD::system_thread (bitmap) variable */
|
||||||
#define SYSTEM_THREAD_DELAYED_INSERT 1
|
#define SYSTEM_THREAD_DELAYED_INSERT 1
|
||||||
|
Reference in New Issue
Block a user