summaryrefslogtreecommitdiff
path: root/sql
diff options
context:
space:
mode:
authorDmitry Lenev <Dmitry.Lenev@oracle.com>2010-10-07 20:01:17 +0400
committerDmitry Lenev <Dmitry.Lenev@oracle.com>2010-10-07 20:01:17 +0400
commiteaae675279435c06974c166b183cc5bd9232eddc (patch)
tree52fe8883af8edd4beabecb0e989d80f49ea3222d /sql
parent4bc7ff6993128b1389410b5dff5b65723515c1ac (diff)
downloadmariadb-git-eaae675279435c06974c166b183cc5bd9232eddc.tar.gz
Fix for bug#57061 "User without privilege on routine can
discover its existence". The problem was that user without any privileges on routine was able to find out whether it existed or not. DROP FUNCTION and DROP PROCEDURE statements were checking if routine being dropped existed and reported ER_SP_DOES_NOT_EXIST error/warning before checking if user had enough privileges to drop it. This patch solves this problem by changing code not to check if routine exists before checking if user has enough privileges to drop it. Moreover we no longer perform this check using a separate call instead we rely on sp_drop_routine() returning SP_KEY_NOT_FOUND if routine doesn't exist. This change also simplifies one of upcoming patches refactoring global read lock implementation. mysql-test/r/grant.result: Updated test case after fixing bug#57061 "User without privilege on routine can discover its existence". Removed DROP PROCEDURE/FUNCTION statements which have started to fail after this fix (correctly). There is no need in dropping routines in freshly created database anyway. mysql-test/r/sp-security.result: Added new test case for bug#57061 "User without privilege on routine can discover its existence". Updated existing tests according to new behaviour. mysql-test/suite/funcs_1/r/innodb_storedproc_06.result: Updated test case after fixing bug#57061 "User without privilege on routine can discover its existence". Now we drop routines under user which has enough privileges to do so. mysql-test/suite/funcs_1/r/memory_storedproc_06.result: Updated test case after fixing bug#57061 "User without privilege on routine can discover its existence". Now we drop routines under user which has enough privileges to do so. mysql-test/suite/funcs_1/r/myisam_storedproc_06.result: Updated test case after fixing bug#57061 "User without privilege on routine can discover its existence". Now we drop routines under user which has enough privileges to do so. mysql-test/suite/funcs_1/storedproc/storedproc_06.inc: Updated test case after fixing bug#57061 "User without privilege on routine can discover its existence". Now we drop routines under user which has enough privileges to do so. mysql-test/t/grant.test: Updated test case after fixing bug#57061 "User without privilege on routine can discover its existence". Removed DROP PROCEDURE/FUNCTION statements which have started to fail after this fix (correctly). There is no need in dropping routines in freshly created database anyway. mysql-test/t/sp-security.test: Added new test case for bug#57061 "User without privilege on routine can discover its existence". Updated existing tests according to new behaviour. sql/sp.cc: Removed sp_routine_exists_in_table() which is no longer used. sql/sp.h: Removed sp_routine_exists_in_table() which is no longer used. sql/sql_parse.cc: When dropping routine we no longer check if routine exists before checking if user has enough privileges to do so. Moreover we no longer perform this check using a separate call instead we rely on sp_drop_routine() returning SP_KEY_NOT_FOUND if routine doesn't exist.
Diffstat (limited to 'sql')
-rw-r--r--sql/sp.cc32
-rw-r--r--sql/sp.h3
-rw-r--r--sql/sql_parse.cc64
3 files changed, 27 insertions, 72 deletions
diff --git a/sql/sp.cc b/sql/sp.cc
index 8821dc9365d..87eb40c29ac 100644
--- a/sql/sp.cc
+++ b/sql/sp.cc
@@ -1636,38 +1636,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)
{
diff --git a/sql/sp.h b/sql/sp.h
index 10e70261b86..5d0490586a1 100644
--- a/sql/sp.h
+++ b/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);
diff --git a/sql/sql_parse.cc b/sql/sql_parse.cc
index 2f8a72ee25c..0f3338cb6a6 100644
--- a/sql/sql_parse.cc
+++ b/sql/sql_parse.cc
@@ -4023,49 +4023,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: