Commit 2f2699f9 authored by Sergei Golubchik's avatar Sergei Golubchik

cleanup.

mainly to avoid the pattern of
* get username/hostname/rolename
* optionally find the corresponding ACL_USER and ACL_ROLE
* allocate memory, concatenate username/hostname/rolename
* call a function passing only this memory as an argument
** use concatenated username/etc to find ACL_USER and ACL_ROLE again
** do something
* free the object

Also to undo push_dynamic we use pop_dynamic now,
not a linear search/scan through the dynamic array.

as a bonus, role@ is now an invalid way to refer to a role.
parent f1a71b68
...@@ -2,7 +2,7 @@ create user test_user@localhost; ...@@ -2,7 +2,7 @@ create user test_user@localhost;
create role test_role1; create role test_role1;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
create role test_role2; create role test_role2;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
user host user host
test_role1 test_role1
......
...@@ -2,7 +2,7 @@ create user test_user@localhost; ...@@ -2,7 +2,7 @@ create user test_user@localhost;
create role test_role1; create role test_role1;
create role test_role2; create role test_role2;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
user host user host
test_role1 test_role1
......
...@@ -2,7 +2,7 @@ create user test_user@localhost; ...@@ -2,7 +2,7 @@ create user test_user@localhost;
create role test_role1; create role test_role1;
create role test_role2; create role test_role2;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
user host user host
test_role1 test_role1
......
...@@ -3,7 +3,7 @@ create role test_role1; ...@@ -3,7 +3,7 @@ create role test_role1;
create role test_role2; create role test_role2;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
grant test_role2 to test_user@localhost; grant test_role2 to test_user@localhost;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
user host user host
test_role1 test_role1
......
...@@ -4,7 +4,7 @@ create user test_user@localhost; ...@@ -4,7 +4,7 @@ create user test_user@localhost;
create role test_role1; create role test_role1;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
create role test_role2; create role test_role2;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
--sorted_result --sorted_result
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
......
...@@ -3,7 +3,7 @@ create role test_role1; ...@@ -3,7 +3,7 @@ create role test_role1;
create role test_role2; create role test_role2;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
--sorted_result --sorted_result
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
--sorted_result --sorted_result
......
...@@ -3,7 +3,7 @@ create role test_role1; ...@@ -3,7 +3,7 @@ create role test_role1;
create role test_role2; create role test_role2;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
--sorted_result --sorted_result
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
--sorted_result --sorted_result
......
...@@ -5,7 +5,7 @@ create role test_role2; ...@@ -5,7 +5,7 @@ create role test_role2;
grant test_role1 to test_user@localhost; grant test_role1 to test_user@localhost;
grant test_role2 to test_user@localhost; grant test_role2 to test_user@localhost;
grant test_role2 to test_role1@; grant test_role2 to test_role1;
--sorted_result --sorted_result
select user, host from mysql.user where user not like 'root'; select user, host from mysql.user where user not like 'root';
--sorted_result --sorted_result
......
...@@ -328,6 +328,12 @@ static bool show_table_and_column_privileges(THD *, const char *, const char *, ...@@ -328,6 +328,12 @@ static bool show_table_and_column_privileges(THD *, const char *, const char *,
static int show_routine_grants(THD *, const char *, const char *, HASH *, static int show_routine_grants(THD *, const char *, const char *, HASH *,
const char *, int, char *, int); const char *, int, char *, int);
static char *safe_str(char *str)
{ return str ? str : const_cast<char*>(""); }
static const char *safe_str(const char *str)
{ return str ? str : ""; }
class ACL_PROXY_USER :public ACL_ACCESS class ACL_PROXY_USER :public ACL_ACCESS
{ {
acl_host_and_ip host; acl_host_and_ip host;
...@@ -406,10 +412,10 @@ public: ...@@ -406,10 +412,10 @@ public:
{ {
sql_print_warning("'proxies_priv' entry '%s@%s %s@%s' " sql_print_warning("'proxies_priv' entry '%s@%s %s@%s' "
"ignored in --skip-name-resolve mode.", "ignored in --skip-name-resolve mode.",
proxied_user ? proxied_user : "", safe_str(proxied_user),
proxied_host.hostname ? proxied_host.hostname : "", safe_str(proxied_host.hostname),
user ? user : "", safe_str(user),
host.hostname ? host.hostname : ""); safe_str(host.hostname));
return TRUE; return TRUE;
} }
return FALSE; return FALSE;
...@@ -719,6 +725,8 @@ static void free_acl_role(ACL_ROLE *acl_role); ...@@ -719,6 +725,8 @@ static void free_acl_role(ACL_ROLE *acl_role);
static ACL_USER *find_user_no_anon(const char *host, const char *user, bool exact); static ACL_USER *find_user_no_anon(const char *host, const char *user, bool exact);
static ACL_USER *find_user(const char *host, const char *user, const char *ip); static ACL_USER *find_user(const char *host, const char *user, const char *ip);
static ACL_ROLE *find_acl_role(const char *user); static ACL_ROLE *find_acl_role(const char *user);
static ROLE_GRANT_PAIR *find_role_grant_pair(const LEX_STRING *u, const LEX_STRING *h, const LEX_STRING *r);
static ACL_USER_BASE *find_acl_user_base(const char *user, const char *host);
static bool update_user_table(THD *thd, TABLE *table, const char *host, static bool update_user_table(THD *thd, TABLE *table, const char *host,
const char *user, const char *new_password, const char *user, const char *new_password,
uint new_password_len); uint new_password_len);
...@@ -728,7 +736,9 @@ static inline void get_grantor(THD *thd, char* grantor); ...@@ -728,7 +736,9 @@ static inline void get_grantor(THD *thd, char* grantor);
static my_bool acl_user_reset_grant(ACL_USER *, void *); static my_bool acl_user_reset_grant(ACL_USER *, void *);
static my_bool acl_role_reset_grant(ACL_ROLE *, void *); static my_bool acl_role_reset_grant(ACL_ROLE *, void *);
static my_bool acl_role_propagate_grants(ACL_ROLE *, void *); static my_bool acl_role_propagate_grants(ACL_ROLE *, void *);
static int add_role_user_mapping(ROLE_GRANT_PAIR *mapping); static bool add_role_user_mapping(ROLE_GRANT_PAIR *mapping);
static bool add_role_user_mapping(ACL_USER_BASE *grantee, ACL_ROLE *role);
static bool add_role_user_mapping(const char *uname, const char *hname, const char *rname);
static void reset_role_db_privileges(ACL_ROLE *role); static void reset_role_db_privileges(ACL_ROLE *role);
static void reset_role_table_and_column_privileges(ACL_ROLE *role); static void reset_role_table_and_column_privileges(ACL_ROLE *role);
...@@ -959,8 +969,8 @@ set_user_plugin (ACL_USER *user, int password_len) ...@@ -959,8 +969,8 @@ set_user_plugin (ACL_USER *user, int password_len)
return FALSE; return FALSE;
default: default:
sql_print_warning("Found invalid password for user: '%s@%s'; " sql_print_warning("Found invalid password for user: '%s@%s'; "
"Ignoring user", user->user.str ? user->user.str : "", "Ignoring user", safe_str(user->user.str),
user->host.hostname ? user->host.hostname : ""); safe_str(user->host.hostname));
return TRUE; return TRUE;
} }
} }
...@@ -1029,8 +1039,8 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1029,8 +1039,8 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
"case that has been forced to lowercase because " "case that has been forced to lowercase because "
"lower_case_table_names is set. It will not be " "lower_case_table_names is set. It will not be "
"possible to remove this privilege using REVOKE.", "possible to remove this privilege using REVOKE.",
host.host.hostname ? host.host.hostname : "", safe_str(host.host.hostname),
host.db ? host.db : ""); safe_str(host.db));
} }
host.access= get_access(table,2); host.access= get_access(table,2);
host.access= fix_rights_for_db(host.access); host.access= fix_rights_for_db(host.access);
...@@ -1039,8 +1049,8 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1039,8 +1049,8 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
{ {
sql_print_warning("'host' entry '%s|%s' " sql_print_warning("'host' entry '%s|%s' "
"ignored in --skip-name-resolve mode.", "ignored in --skip-name-resolve mode.",
host.host.hostname ? host.host.hostname : "", safe_str(host.host.hostname),
host.db ? host.db : ""); safe_str(host.db));
continue; continue;
} }
#ifndef TO_BE_REMOVED #ifndef TO_BE_REMOVED
...@@ -1131,14 +1141,14 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1131,14 +1141,14 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
{ {
sql_print_warning("'user' entry '%s@%s' " sql_print_warning("'user' entry '%s@%s' "
"ignored in --skip-name-resolve mode.", "ignored in --skip-name-resolve mode.",
user.user.str ? user.user.str : "", safe_str(user.user.str),
user.host.hostname ? user.host.hostname : ""); safe_str(user.host.hostname));
continue; continue;
} }
char *password= get_field(&mem, table->field[2]); char *password= get_field(&mem, table->field[2]);
uint password_len= password ? strlen(password) : 0; uint password_len= password ? strlen(password) : 0;
user.auth_string.str= password ? password : const_cast<char*>(""); user.auth_string.str= safe_str(password);
user.auth_string.length= password_len; user.auth_string.length= password_len;
set_user_salt(&user, password, password_len); set_user_salt(&user, password, password_len);
...@@ -1235,12 +1245,11 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1235,12 +1245,11 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
sql_print_warning("'user' entry '%s@%s' has both a password " sql_print_warning("'user' entry '%s@%s' has both a password "
"and an authentication plugin specified. The " "and an authentication plugin specified. The "
"password will be ignored.", "password will be ignored.",
user.user.str ? user.user.str : "", safe_str(user.user.str),
user.host.hostname ? user.host.hostname : ""); safe_str(user.host.hostname));
} }
user.auth_string.str= get_field(&mem, table->field[next_field++]); user.auth_string.str=
if (!user.auth_string.str) safe_str(get_field(&mem, table->field[next_field++]));
user.auth_string.str= const_cast<char*>("");
user.auth_string.length= strlen(user.auth_string.str); user.auth_string.length= strlen(user.auth_string.str);
fix_user_plugin_ptr(&user); fix_user_plugin_ptr(&user);
...@@ -1317,9 +1326,7 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1317,9 +1326,7 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
{ {
sql_print_warning("'db' entry '%s %s@%s' " sql_print_warning("'db' entry '%s %s@%s' "
"ignored in --skip-name-resolve mode.", "ignored in --skip-name-resolve mode.",
db.db, db.db, safe_str(db.user), safe_str(db.host.hostname));
db.user ? db.user : "",
db.host.hostname ? db.host.hostname : "");
continue; continue;
} }
db.access=get_access(table,3); db.access=get_access(table,3);
...@@ -1344,9 +1351,7 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1344,9 +1351,7 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
"case that has been forced to lowercase because " "case that has been forced to lowercase because "
"lower_case_table_names is set. It will not be " "lower_case_table_names is set. It will not be "
"possible to remove this privilege using REVOKE.", "possible to remove this privilege using REVOKE.",
db.db, db.db, safe_str(db.user), safe_str(db.host.hostname));
db.user ? db.user : "",
db.host.hostname ? db.host.hostname : "");
} }
} }
db.sort=get_sort(3,db.host.hostname,db.db,db.user); db.sort=get_sort(3,db.host.hostname,db.db,db.user);
...@@ -1413,23 +1418,22 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables) ...@@ -1413,23 +1418,22 @@ static my_bool acl_load(THD *thd, TABLE_LIST *tables)
init_alloc_root(&temp_root, ACL_ALLOC_BLOCK_SIZE, 0, MYF(0)); init_alloc_root(&temp_root, ACL_ALLOC_BLOCK_SIZE, 0, MYF(0));
while (!(read_record_info.read_record(&read_record_info))) while (!(read_record_info.read_record(&read_record_info)))
{ {
ROLE_GRANT_PAIR *mapping= new (&mem) ROLE_GRANT_PAIR; char *hostname= safe_str(get_field(&temp_root, table->field[0]));
char *hostname= get_field(&temp_root, table->field[0]); char *username= safe_str(get_field(&temp_root, table->field[1]));
char *username= get_field(&temp_root, table->field[1]); char *rolename= safe_str(get_field(&temp_root, table->field[2]));
char *rolename= get_field(&temp_root, table->field[2]);
bool with_grant_option= get_YN_as_bool(table->field[3]); bool with_grant_option= get_YN_as_bool(table->field[3]);
if (mapping->init(&mem, username, hostname, rolename, with_grant_option)) if (add_role_user_mapping(username, hostname, rolename)) {
continue;
if (add_role_user_mapping(mapping) == -1) {
sql_print_error("Invalid roles_mapping table entry user:'%s@%s', rolename:'%s'", sql_print_error("Invalid roles_mapping table entry user:'%s@%s', rolename:'%s'",
mapping->u_uname ? mapping->u_uname : "", username, hostname, rolename);
mapping->u_hname ? mapping->u_hname : "",
mapping->r_uname ? mapping->r_uname : "");
continue; continue;
} }
ROLE_GRANT_PAIR *mapping= new (&mem) ROLE_GRANT_PAIR;
if (mapping->init(&mem, username, hostname, rolename, with_grant_option))
continue;
my_hash_insert(&acl_roles_mappings, (uchar*) mapping); my_hash_insert(&acl_roles_mappings, (uchar*) mapping);
} }
...@@ -1744,7 +1748,7 @@ bool acl_getroot(Security_context *sctx, char *user, char *host, ...@@ -1744,7 +1748,7 @@ bool acl_getroot(Security_context *sctx, char *user, char *host,
sctx->user= user; sctx->user= user;
sctx->host= host; sctx->host= host;
sctx->ip= ip; sctx->ip= ip;
sctx->host_or_ip= host ? host : (ip ? ip : ""); sctx->host_or_ip= host ? host : (safe_str(ip));
if (!initialized) if (!initialized)
{ {
...@@ -2264,7 +2268,7 @@ ulong acl_get(const char *host, const char *ip, ...@@ -2264,7 +2268,7 @@ ulong acl_get(const char *host, const char *ip,
acl_entry *entry; acl_entry *entry;
DBUG_ENTER("acl_get"); DBUG_ENTER("acl_get");
tmp_db= strmov(strmov(key, ip ? ip : "") + 1, user) + 1; tmp_db= strmov(strmov(key, safe_str(ip)) + 1, user) + 1;
end= strnmov(tmp_db, db, key + sizeof(key) - tmp_db); end= strnmov(tmp_db, db, key + sizeof(key) - tmp_db);
if (end >= key + sizeof(key)) // db name was truncated if (end >= key + sizeof(key)) // db name was truncated
...@@ -2709,107 +2713,72 @@ end: ...@@ -2709,107 +2713,72 @@ end:
/* /*
Add a the coresponding pointers present in the mapping to the entries in Add a the coresponding pointers present in the mapping to the entries in
acl_users and acl_roles acl_users and acl_roles
Return values:
0: The entry is valid and was added.
-1: The entry is invalid and was not added.
1: The entry represents a mapping between two roles.
*/ */
int add_role_user_mapping(ROLE_GRANT_PAIR *mapping) static bool add_role_user_mapping(ACL_USER_BASE *grantee, ACL_ROLE *role)
{ {
return push_dynamic(&grantee->role_grants, (uchar*) &role)
|| push_dynamic(&role->parent_grantee, (uchar*) &grantee);
ACL_USER_BASE *user= find_user_no_anon((mapping->u_hname) ? mapping->u_hname: "", }
(mapping->u_uname) ? mapping->u_uname: "",
TRUE);
ACL_ROLE *role= find_acl_role(mapping->r_uname ? mapping->r_uname: "");
static void undo_add_role_user_mapping(ACL_USER_BASE *grantee, ACL_ROLE *role)
{
void *pop __attribute__((unused));
int result= 0; pop= pop_dynamic(&grantee->role_grants);
DBUG_ASSERT(role == *(ACL_ROLE**)pop);
if (user == NULL || role == NULL) pop= pop_dynamic(&role->parent_grantee);
{ DBUG_ASSERT(grantee == *(ACL_USER_BASE**)pop);
/* There still exists the possibility that the user is actually a role */ }
if (user == NULL && role && (!mapping->u_hname || !mapping->u_hname[0])
&& /* in this case the grantee is a role */
((user= find_acl_role(mapping->u_uname ? mapping->u_uname: ""))))
{
result= 1;
}
else
{
DBUG_PRINT("warning", ("Invalid add_role_user_mapping '%s'@'%s' %s %p %p",
mapping->u_uname, mapping->u_hname,
mapping->r_uname, user, role));
return -1; static bool add_role_user_mapping(const char *uname, const char *hname,
} const char *rname)
} {
ACL_USER_BASE *grantee= find_acl_user_base(uname, hname);
ACL_ROLE *role= find_acl_role(rname);
push_dynamic(&user->role_grants, (uchar*) &role); if (grantee == NULL || role == NULL)
push_dynamic(&role->parent_grantee, (uchar*) &user); return 1;
DBUG_PRINT("info", ("Found %s %s@%s having role granted %s\n", return add_role_user_mapping(grantee, role);
(result) ? "role" : "user",
user->user.str,
(result) ? "" : ((ACL_USER *)user)->host.hostname,
role->user.str));
return result;
} }
int remove_role_user_mapping(ROLE_GRANT_PAIR *mapping) static bool add_role_user_mapping(ROLE_GRANT_PAIR *mapping)
{ {
ACL_USER_BASE *user= find_user_no_anon((mapping->u_hname) ? mapping->u_hname: "", return add_role_user_mapping(mapping->u_uname, mapping->u_hname, mapping->r_uname);
(mapping->u_uname) ? mapping->u_uname: "", }
TRUE);
ACL_ROLE *role= find_acl_role(mapping->r_uname ? mapping->r_uname: "");
int result= 0; static void remove_role_user_mapping(ACL_USER_BASE *grantee, ACL_ROLE *role)
{
uint idx_user, idx_role; uint idx_user, idx_role;
bool deleted_role= FALSE, deleted_user= FALSE; bool deleted_role __attribute__((unused))= false,
deleted_user __attribute__((unused))= false;
if (user == NULL || role == NULL)
{
/* There still exists the possibility that the user is actually a role */
if (user == NULL && role && (!mapping->u_hname || !mapping->u_hname[0])
&& /* in this case the grantee is a role */
((user= find_acl_role(mapping->u_uname ? mapping->u_uname: ""))))
{
result= 1;
}
else
{
DBUG_PRINT("warning", ("Invalid remove_role_user_mapping '%s'@'%s' %s %p %p",
mapping->u_uname, mapping->u_hname,
mapping->r_uname, user, role));
return -1;
}
}
/* scan both arrays to find and delete both links */ /* scan both arrays to find and delete both links */
for (idx_user=0; idx_user < user->role_grants.elements; idx_user++) for (idx_user=0; idx_user < grantee->role_grants.elements; idx_user++)
{ {
if (role == *dynamic_element(&user->role_grants, idx_user, ACL_ROLE**)) if (role == *dynamic_element(&grantee->role_grants, idx_user, ACL_ROLE**))
{ {
delete_dynamic_element(&user->role_grants, idx_user); delete_dynamic_element(&grantee->role_grants, idx_user);
deleted_user= TRUE; deleted_user= true;
break;
} }
} }
for (idx_role=0; idx_role < role->parent_grantee.elements; idx_role++) for (idx_role=0; idx_role < role->parent_grantee.elements; idx_role++)
{ {
if (user == *dynamic_element(&role->parent_grantee, idx_role, if (grantee == *dynamic_element(&role->parent_grantee, idx_role,
ACL_USER_BASE**)) ACL_USER_BASE**))
{ {
delete_dynamic_element(&role->parent_grantee, idx_role); delete_dynamic_element(&role->parent_grantee, idx_role);
deleted_role= TRUE; deleted_role= true;
break;
} }
} }
/* we should always get to delete from both arrays */ /* we should always get to delete from both arrays */
DBUG_ASSERT(deleted_role && deleted_user); DBUG_ASSERT(deleted_role && deleted_user);
return result;
} }
...@@ -3027,8 +2996,8 @@ bool change_password(THD *thd, const char *host, const char *user, ...@@ -3027,8 +2996,8 @@ bool change_password(THD *thd, const char *host, const char *user,
ER_SET_PASSWORD_AUTH_PLUGIN, ER(ER_SET_PASSWORD_AUTH_PLUGIN)); ER_SET_PASSWORD_AUTH_PLUGIN, ER(ER_SET_PASSWORD_AUTH_PLUGIN));
if (update_user_table(thd, table, if (update_user_table(thd, table,
acl_user->host.hostname ? acl_user->host.hostname : "", safe_str(acl_user->host.hostname),
acl_user->user.str ? acl_user->user.str : "", safe_str(acl_user->user.str),
new_password, new_password_len)) new_password, new_password_len))
{ {
mysql_mutex_unlock(&acl_cache->lock); /* purecov: deadcode */ mysql_mutex_unlock(&acl_cache->lock); /* purecov: deadcode */
...@@ -3042,8 +3011,8 @@ bool change_password(THD *thd, const char *host, const char *user, ...@@ -3042,8 +3011,8 @@ bool change_password(THD *thd, const char *host, const char *user,
{ {
query_length= query_length=
sprintf(buff,"SET PASSWORD FOR '%-.120s'@'%-.120s'='%-.120s'", sprintf(buff,"SET PASSWORD FOR '%-.120s'@'%-.120s'='%-.120s'",
acl_user->user.str ? acl_user->user.str : "", safe_str(acl_user->user.str),
acl_user->host.hostname ? acl_user->host.hostname : "", safe_str(acl_user->host.hostname),
new_password); new_password);
thd->clear_error(); thd->clear_error();
result= thd->binlog_query(THD::STMT_QUERY_TYPE, buff, query_length, result= thd->binlog_query(THD::STMT_QUERY_TYPE, buff, query_length,
...@@ -3125,16 +3094,14 @@ find_user_no_anon(const char *host, const char *user, bool exact) ...@@ -3125,16 +3094,14 @@ find_user_no_anon(const char *host, const char *user, bool exact)
{ {
ACL_USER *acl_user=dynamic_element(&acl_users,i,ACL_USER*); ACL_USER *acl_user=dynamic_element(&acl_users,i,ACL_USER*);
DBUG_PRINT("info",("strcmp('%s','%s'), compare_hostname('%s','%s'),", DBUG_PRINT("info",("strcmp('%s','%s'), compare_hostname('%s','%s'),",
user, acl_user->user.str ? acl_user->user.str : "", user, safe_str(acl_user->user.str),
host, host,
acl_user->host.hostname ? acl_user->host.hostname : safe_str(acl_user->host.hostname)));
""));
if ((!acl_user->user.str && !user[0]) || if ((!acl_user->user.str && !user[0]) ||
(acl_user->user.str && !strcmp(user,acl_user->user.str))) (acl_user->user.str && !strcmp(user,acl_user->user.str)))
{ {
if (exact ? !my_strcasecmp(system_charset_info, host, if (exact ? !my_strcasecmp(system_charset_info, host,
acl_user->host.hostname ? safe_str(acl_user->host.hostname)) :
acl_user->host.hostname : "") :
compare_hostname(&acl_user->host,host,host)) compare_hostname(&acl_user->host,host,host))
{ {
DBUG_RETURN(acl_user); DBUG_RETURN(acl_user);
...@@ -3161,6 +3128,13 @@ find_acl_role(const char *user) ...@@ -3161,6 +3128,13 @@ find_acl_role(const char *user)
} }
static ACL_USER_BASE *find_acl_user_base(const char *user, const char *host)
{
if (*host)
return find_user_no_anon(host, user, TRUE);
return find_acl_role(user);
}
/* /*
...@@ -3781,8 +3755,10 @@ abort: ...@@ -3781,8 +3755,10 @@ abort:
Updates the mysql.roles_mapping table and the acl_roles_mappings hash. Updates the mysql.roles_mapping table and the acl_roles_mappings hash.
@param table TABLE to update @param table TABLE to update
@param pair granted role, grantee, with_admin flag. allocated @param user user name of the grantee
in a temporary MEM_ROOT @param host host name of the grantee
@param role role name to grant
@param with_admin WITH ADMIN OPTION flag
@param existing the entry in the acl_roles_mappings hash or NULL. @param existing the entry in the acl_roles_mappings hash or NULL.
it is never NULL if revoke_grant is true. it is never NULL if revoke_grant is true.
it is NULL when a new pair is added, it's not NULL it is NULL when a new pair is added, it's not NULL
...@@ -3790,7 +3766,8 @@ abort: ...@@ -3790,7 +3766,8 @@ abort:
@param revoke_grant true for REVOKE, false for GRANT @param revoke_grant true for REVOKE, false for GRANT
*/ */
static int static int
replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair, replace_roles_mapping_table(TABLE *table, LEX_STRING *user, LEX_STRING *host,
LEX_STRING *role, bool with_admin,
ROLE_GRANT_PAIR *existing, bool revoke_grant) ROLE_GRANT_PAIR *existing, bool revoke_grant)
{ {
DBUG_ENTER("replace_roles_mapping_table"); DBUG_ENTER("replace_roles_mapping_table");
...@@ -3799,12 +3776,9 @@ replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair, ...@@ -3799,12 +3776,9 @@ replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair,
int error; int error;
table->use_all_columns(); table->use_all_columns();
restore_record(table, s->default_values); restore_record(table, s->default_values);
table->field[0]->store(pair->u_hname, strlen(pair->u_hname), table->field[0]->store(host->str, host->length, system_charset_info);
system_charset_info); table->field[1]->store(user->str, user->length, system_charset_info);
table->field[1]->store(pair->u_uname, strlen(pair->u_uname), table->field[2]->store(role->str, role->length, system_charset_info);
system_charset_info);
table->field[2]->store(pair->r_uname, strlen(pair->r_uname),
system_charset_info);
DBUG_ASSERT(!revoke_grant || existing); DBUG_ASSERT(!revoke_grant || existing);
...@@ -3818,12 +3792,12 @@ replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair, ...@@ -3818,12 +3792,12 @@ replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair,
/* No match */ /* No match */
DBUG_RETURN(1); DBUG_RETURN(1);
} }
if (revoke_grant && !pair->with_admin) if (revoke_grant && !with_admin)
{ {
if ((error= table->file->ha_delete_row(table->record[1]))) if ((error= table->file->ha_delete_row(table->record[1])))
{ {
DBUG_PRINT("info", ("error deleting row '%s' '%s' '%s'", DBUG_PRINT("info", ("error deleting row '%s' '%s' '%s'",
pair->u_hname, pair->u_uname, pair->r_uname)); host->str, user->str, role->str));
goto table_error; goto table_error;
} }
/* /*
...@@ -3837,34 +3811,33 @@ replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair, ...@@ -3837,34 +3811,33 @@ replace_roles_mapping_table(TABLE *table, ROLE_GRANT_PAIR *pair,
if (revoke_grant) if (revoke_grant)
existing->with_admin= false; existing->with_admin= false;
else else
existing->with_admin|= pair->with_admin; existing->with_admin|= with_admin;
table->field[3]->store(existing->with_admin + 1); table->field[3]->store(existing->with_admin + 1);
if ((error= table->file->ha_update_row(table->record[1], table->record[0]))) if ((error= table->file->ha_update_row(table->record[1], table->record[0])))
{ {
DBUG_PRINT("info", ("error updating row '%s' '%s' '%s'", DBUG_PRINT("info", ("error updating row '%s' '%s' '%s'",
pair->u_hname, pair->u_uname, pair->r_uname)); host->str, user->str, role->str));
goto table_error; goto table_error;
} }
} }
DBUG_RETURN(0); DBUG_RETURN(0);
} }
table->field[3]->store(pair->with_admin + 1); table->field[3]->store(with_admin + 1);
if ((error= table->file->ha_write_row(table->record[0]))) if ((error= table->file->ha_write_row(table->record[0])))
{ {
DBUG_PRINT("info", ("error inserting row '%s' '%s' '%s'", DBUG_PRINT("info", ("error inserting row '%s' '%s' '%s'",
pair->u_hname, pair->u_uname, pair->r_uname)); host->str, user->str, role->str));
goto table_error; goto table_error;
} }
else else
{ {
/* allocate a new entry that will go in the hash */ /* allocate a new entry that will go in the hash */
ROLE_GRANT_PAIR *hash_entry= new (&mem) ROLE_GRANT_PAIR; ROLE_GRANT_PAIR *hash_entry= new (&mem) ROLE_GRANT_PAIR;
if (hash_entry->init(&mem, pair->u_uname, pair->u_hname, pair->r_uname, if (hash_entry->init(&mem, user->str, host->str, role->str, with_admin))
pair->with_admin))
DBUG_RETURN(1); DBUG_RETURN(1);
my_hash_insert(&acl_roles_mappings, (uchar*) hash_entry); my_hash_insert(&acl_roles_mappings, (uchar*) hash_entry);
} }
...@@ -4209,9 +4182,7 @@ GRANT_TABLE::GRANT_TABLE(GRANT_TABLE *source, char *u) ...@@ -4209,9 +4182,7 @@ GRANT_TABLE::GRANT_TABLE(GRANT_TABLE *source, char *u)
GRANT_NAME::GRANT_NAME(TABLE *form, bool is_routine) GRANT_NAME::GRANT_NAME(TABLE *form, bool is_routine)
{ {
user= get_field(&memex,form->field[2]); user= safe_str(get_field(&memex,form->field[2]));
if (!user)
user= (char*) "";
const char *hostname= get_field(&memex, form->field[0]); const char *hostname= get_field(&memex, form->field[0]);
mysql_mutex_lock(&acl_cache->lock); mysql_mutex_lock(&acl_cache->lock);
...@@ -5363,25 +5334,26 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke) ...@@ -5363,25 +5334,26 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke)
bool result= 0; bool result= 0;
String wrong_users; String wrong_users;
LEX_USER *user, *granted_role; LEX_USER *user, *granted_role;
char *rolename; LEX_STRING rolename;
char *username; LEX_STRING username;
char *hostname; LEX_STRING hostname;
ACL_ROLE *role, *role_as_user; ACL_ROLE *role, *role_as_user;
List_iterator <LEX_USER> user_list(list); List_iterator <LEX_USER> user_list(list);
granted_role= user_list++; granted_role= user_list++;
if (granted_role->user.str == current_role.str) if (granted_role->user.str == current_role.str)
{ {
rolename= thd->security_ctx->priv_role; rolename.str= thd->security_ctx->priv_role;
if (!rolename[0]) if (!rolename.str[0])
{ {
my_error(ER_RESERVED_ROLE, MYF(0), "NONE"); my_error(ER_RESERVED_ROLE, MYF(0), "NONE");
DBUG_RETURN(TRUE); DBUG_RETURN(TRUE);
} }
rolename.length= strlen(rolename.str);
} }
else else
{ {
rolename= granted_role->user.str; rolename= granted_role->user;
} }
TABLE_LIST tables; TABLE_LIST tables;
...@@ -5391,11 +5363,11 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke) ...@@ -5391,11 +5363,11 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke)
mysql_rwlock_wrlock(&LOCK_grant); mysql_rwlock_wrlock(&LOCK_grant);
mysql_mutex_lock(&acl_cache->lock); mysql_mutex_lock(&acl_cache->lock);
if (!(role= find_acl_role(rolename))) if (!(role= find_acl_role(rolename.str)))
{ {
mysql_mutex_unlock(&acl_cache->lock); mysql_mutex_unlock(&acl_cache->lock);
mysql_rwlock_unlock(&LOCK_grant); mysql_rwlock_unlock(&LOCK_grant);
my_error(ER_INVALID_ROLE, MYF(0), rolename); my_error(ER_INVALID_ROLE, MYF(0), rolename.str);
DBUG_RETURN(TRUE); DBUG_RETURN(TRUE);
} }
...@@ -5434,33 +5406,42 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke) ...@@ -5434,33 +5406,42 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke)
result= 1; result= 1;
continue; continue;
} }
username= thd->security_ctx->priv_role; username.str= thd->security_ctx->priv_role;
hostname= const_cast<char*>(""); username.length= strlen(username.str);
hostname= empty_lex_str;
} }
else if (user->user.str == current_user.str) else if (user->user.str == current_user.str)
{ {
role_as_user= NULL; username.str= thd->security_ctx->priv_user;
username= thd->security_ctx->priv_user; username.length= strlen(username.str);
hostname= thd->security_ctx->priv_host; hostname.str= thd->security_ctx->priv_host;
hostname.length= strlen(hostname.str);
} }
else else
{ {
username= user->user;
if (user->host.str)
hostname= user->host;
else
if ((role_as_user= find_acl_role(user->user.str))) if ((role_as_user= find_acl_role(user->user.str)))
hostname= const_cast<char*>(""); hostname= empty_lex_str;
else else
hostname= user->host.str ? user->host.str : host_not_specified.str; hostname= host_not_specified;
username= user->user.str;
} }
ROLE_GRANT_PAIR *hash_entry, *mapping= new (thd->mem_root) ROLE_GRANT_PAIR; ROLE_GRANT_PAIR *hash_entry= find_role_grant_pair(&username, &hostname,
&rolename);
ACL_USER_BASE *grantee= role_as_user;
if (mapping->init(thd->mem_root, username, hostname, rolename, if (!grantee)
thd->lex->with_admin_option)) grantee= find_user_no_anon(hostname.str, username.str, true);
continue;
hash_entry = (ROLE_GRANT_PAIR *) if (!grantee)
my_hash_search(&acl_roles_mappings, (uchar *)mapping->hashkey.str, {
mapping->hashkey.length); append_user(&wrong_users, username.str, hostname.str);
result= 1;
continue;
}
if (!revoke) if (!revoke)
{ {
...@@ -5470,27 +5451,20 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke) ...@@ -5470,27 +5451,20 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke)
} }
else else
{ {
int res= add_role_user_mapping(mapping); add_role_user_mapping(grantee, role);
/* role or user does not exist*/
if (res == -1)
{
append_user(&wrong_users, username, hostname);
result= 1;
continue;
}
/* /*
Check if this grant would cause a cycle. It only needs to be run Check if this grant would cause a cycle. It only needs to be run
if we're granting a role to a role if we're granting a role to a role
*/ */
if (role_as_user && if (role_as_user &&
traverse_role_graph(role, NULL, NULL, NULL, role_explore_detect_cycle, traverse_role_graph(role, NULL, NULL, NULL,
NULL) == 2) role_explore_detect_cycle, NULL) == 2)
{ {
append_user(&wrong_users, username, ""); append_user(&wrong_users, username.str, "");
result= 1; result= 1;
/* need to rollback the mapping added previously */ /* need to remove the mapping added previously */
remove_role_user_mapping(mapping); undo_add_role_user_mapping(grantee, role);
continue; continue;
} }
} }
...@@ -5500,41 +5474,38 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke) ...@@ -5500,41 +5474,38 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke)
/* grant was already removed or never existed */ /* grant was already removed or never existed */
if (!hash_entry) if (!hash_entry)
{ {
append_user(&wrong_users, username, hostname); append_user(&wrong_users, username.str, hostname.str);
result= 1; result= 1;
continue; continue;
} }
if (mapping->with_admin) if (thd->lex->with_admin_option)
{ {
// only revoking an admin option, not the complete grant // only revoking an admin option, not the complete grant
} }
else else
{ {
/* revoke a role grant */ /* revoke a role grant */
int res= remove_role_user_mapping(mapping); remove_role_user_mapping(grantee, role);
if (res == -1)
{
append_user(&wrong_users, username, hostname);
result= 1;
continue;
}
} }
} }
/* write into the roles_mapping table */ /* write into the roles_mapping table */
if (replace_roles_mapping_table(tables.table, mapping, hash_entry, revoke)) if (replace_roles_mapping_table(tables.table,
&username, &hostname, &rolename,
thd->lex->with_admin_option,
hash_entry, revoke))
{ {
append_user(&wrong_users, username, ""); append_user(&wrong_users, username.str, "");
result= 1; result= 1;
if (!revoke) if (!revoke)
{ {
/* need to rollback the mapping added previously */ /* need to remove the mapping added previously */
remove_role_user_mapping(mapping); undo_add_role_user_mapping(grantee, role);
} }
else else
{ {
/* need to rollback the mapping deleted previously */ /* need to restore the mapping deleted previously */
add_role_user_mapping(mapping); add_role_user_mapping(grantee, role);
} }
continue; continue;
} }
...@@ -5556,14 +5527,12 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke) ...@@ -5556,14 +5527,12 @@ bool mysql_grant_role(THD *thd, List <LEX_USER> &list, bool revoke)
{ {
if (!revoke) if (!revoke)
{ {
my_error(ER_CANNOT_GRANT_ROLE, MYF(0), my_error(ER_CANNOT_GRANT_ROLE, MYF(0), rolename.str,
rolename,
wrong_users.c_ptr_safe()); wrong_users.c_ptr_safe());
} }
else else
{ {
my_error(ER_CANNOT_REVOKE_ROLE, MYF(0), my_error(ER_CANNOT_REVOKE_ROLE, MYF(0), rolename.str,
rolename,
wrong_users.c_ptr_safe()); wrong_users.c_ptr_safe());
} }
} }
...@@ -5815,8 +5784,7 @@ static my_bool grant_load_procs_priv(TABLE *p_table) ...@@ -5815,8 +5784,7 @@ static my_bool grant_load_procs_priv(TABLE *p_table)
sql_print_warning("'procs_priv' entry '%s %s@%s' " sql_print_warning("'procs_priv' entry '%s %s@%s' "
"ignored in --skip-name-resolve mode.", "ignored in --skip-name-resolve mode.",
mem_check->tname, mem_check->user, mem_check->tname, mem_check->user,
mem_check->host.hostname ? safe_str(mem_check->host.hostname));
mem_check->host.hostname : "");
continue; continue;
} }
} }
...@@ -5920,9 +5888,8 @@ static my_bool grant_load(THD *thd, TABLE_LIST *tables) ...@@ -5920,9 +5888,8 @@ static my_bool grant_load(THD *thd, TABLE_LIST *tables)
sql_print_warning("'tables_priv' entry '%s %s@%s' " sql_print_warning("'tables_priv' entry '%s %s@%s' "
"ignored in --skip-name-resolve mode.", "ignored in --skip-name-resolve mode.",
mem_check->tname, mem_check->tname,
mem_check->user ? mem_check->user : "", safe_str(mem_check->user),
mem_check->host.hostname ? safe_str(mem_check->host.hostname));
mem_check->host.hostname : "");
continue; continue;
} }
} }
...@@ -7353,10 +7320,8 @@ static bool show_database_privileges(THD *thd, ...@@ -7353,10 +7320,8 @@ static bool show_database_privileges(THD *thd,
const char *user, *host; const char *user, *host;
acl_db=dynamic_element(&acl_dbs,counter,ACL_DB*); acl_db=dynamic_element(&acl_dbs,counter,ACL_DB*);
if (!(user=acl_db->user)) user= safe_str(acl_db->user);
user= ""; host=acl_db->host.hostname;
if (!(host=acl_db->host.hostname))
host= "";
/* /*
We do not make SHOW GRANTS case-sensitive here (like REVOKE), We do not make SHOW GRANTS case-sensitive here (like REVOKE),
...@@ -7442,10 +7407,8 @@ static bool show_table_and_column_privileges(THD *thd, ...@@ -7442,10 +7407,8 @@ static bool show_table_and_column_privileges(THD *thd,
GRANT_TABLE *grant_table= (GRANT_TABLE*) GRANT_TABLE *grant_table= (GRANT_TABLE*)
my_hash_element(&column_priv_hash, index); my_hash_element(&column_priv_hash, index);
if (!(user=grant_table->user)) user= safe_str(grant_table->user);
user= ""; host= grant_table->host.hostname;
if (!(host= grant_table->host.hostname))
host= "";
/* /*
We do not make SHOW GRANTS case-sensitive here (like REVOKE), We do not make SHOW GRANTS case-sensitive here (like REVOKE),
...@@ -7585,10 +7548,8 @@ static int show_routine_grants(THD* thd, ...@@ -7585,10 +7548,8 @@ static int show_routine_grants(THD* thd,
const char *user, *host; const char *user, *host;
GRANT_NAME *grant_proc= (GRANT_NAME*) my_hash_element(hash, index); GRANT_NAME *grant_proc= (GRANT_NAME*) my_hash_element(hash, index);
if (!(user=grant_proc->user)) user= safe_str(grant_proc->user);
user= ""; host= grant_proc->host.hostname;
if (!(host= grant_proc->host.hostname))
host= "";
/* /*
We do not make SHOW GRANTS case-sensitive here (like REVOKE), We do not make SHOW GRANTS case-sensitive here (like REVOKE),
...@@ -7907,10 +7868,9 @@ ACL_USER *check_acl_user(LEX_USER *user_name, ...@@ -7907,10 +7868,9 @@ ACL_USER *check_acl_user(LEX_USER *user_name,
{ {
const char *user,*host; const char *user,*host;
acl_user= dynamic_element(&acl_users, counter, ACL_USER*); acl_user= dynamic_element(&acl_users, counter, ACL_USER*);
if (!(user=acl_user->user.str)) user= safe_str(acl_user->user.str);
user= ""; host=acl_user->host.hostname;
if (!(host=acl_user->host.hostname))
host= "";
if (!strcmp(user_name->user.str,user) && if (!strcmp(user_name->user.str,user) &&
!my_strcasecmp(system_charset_info, user_name->host.str, host)) !my_strcasecmp(system_charset_info, user_name->host.str, host))
break; break;
...@@ -8187,10 +8147,8 @@ static int handle_roles_mappings_table(TABLE *table, bool drop, ...@@ -8187,10 +8147,8 @@ static int handle_roles_mappings_table(TABLE *table, bool drop,
continue; continue;
} }
if (! (host= get_field(thd->mem_root, host_field))) host= safe_str(get_field(thd->mem_root, host_field));
host= ""; user= safe_str(get_field(thd->mem_root, user_field));
if (! (user= get_field(thd->mem_root, user_field)))
user= "";
if (!(strcmp(user_from->user.str, user) || if (!(strcmp(user_from->user.str, user) ||
my_strcasecmp(system_charset_info, user_from->host.str, host))) my_strcasecmp(system_charset_info, user_from->host.str, host)))
...@@ -8199,8 +8157,7 @@ static int handle_roles_mappings_table(TABLE *table, bool drop, ...@@ -8199,8 +8157,7 @@ static int handle_roles_mappings_table(TABLE *table, bool drop,
-1 : result ? result : 1; /* Error or keep result or found. */ -1 : result ? result : 1; /* Error or keep result or found. */
else else
{ {
if (! (role= get_field(thd->mem_root, role_field))) role= safe_str(get_field(thd->mem_root, role_field));
role= "";
if (strcmp(user_from->user.str, role)) if (strcmp(user_from->user.str, role))
continue; continue;
...@@ -8362,10 +8319,8 @@ static int handle_grant_table(TABLE_LIST *tables, uint table_no, bool drop, ...@@ -8362,10 +8319,8 @@ static int handle_grant_table(TABLE_LIST *tables, uint table_no, bool drop,
DBUG_PRINT("info",("scan error: %d", error)); DBUG_PRINT("info",("scan error: %d", error));
continue; continue;
} }
if (! (host= get_field(thd->mem_root, host_field))) host= safe_str(get_field(thd->mem_root, host_field));
host= ""; user= safe_str(get_field(thd->mem_root, user_field));
if (! (user= get_field(thd->mem_root, user_field)))
user= "";
#ifdef EXTRA_DEBUG #ifdef EXTRA_DEBUG
if (table_no != 5) if (table_no != 5)
...@@ -9001,19 +8956,26 @@ bool mysql_create_user(THD *thd, List <LEX_USER> &list, bool handle_as_role) ...@@ -9001,19 +8956,26 @@ bool mysql_create_user(THD *thd, List <LEX_USER> &list, bool handle_as_role)
// every created role is automatically granted to its creator-admin // every created role is automatically granted to its creator-admin
if (handle_as_role) if (handle_as_role)
{ {
ROLE_GRANT_PAIR *pair= new (thd->mem_root) ROLE_GRANT_PAIR; ACL_USER_BASE *grantee= find_acl_user_base(thd->lex->definer->user.str,
thd->lex->definer->host.str);
ACL_ROLE *role= find_acl_role(user_name->user.str);
if (pair->init(thd->mem_root, thd->lex->definer->user.str, /*
thd->lex->definer->host.str, user_name->user.str, true)) just like with routines, views, triggers, and events we allow
{ non-existant definers here with a warning (see sp_process_definer())
result= TRUE; */
break; if (grantee)
} add_role_user_mapping(grantee, role);
add_role_user_mapping(pair);
if (replace_roles_mapping_table(tables[6].table, pair, NULL, false)) if (replace_roles_mapping_table(tables[6].table,
&thd->lex->definer->user,
&thd->lex->definer->host,
&user_name->user, true,
NULL, false))
{ {
append_user(&wrong_users, user_name); append_user(&wrong_users, user_name);
remove_role_user_mapping(pair); if (grantee)
undo_add_role_user_mapping(grantee, role);
result= TRUE; result= TRUE;
} }
} }
...@@ -9261,12 +9223,11 @@ bool mysql_revoke_all(THD *thd, List <LEX_USER> &list) ...@@ -9261,12 +9223,11 @@ bool mysql_revoke_all(THD *thd, List <LEX_USER> &list)
const char *user,*host; const char *user,*host;
acl_db=dynamic_element(&acl_dbs,counter,ACL_DB*); acl_db=dynamic_element(&acl_dbs,counter,ACL_DB*);
if (!(user=acl_db->user))
user= "";
if (!(host=acl_db->host.hostname))
host= "";
if (!strcmp(lex_user->user.str,user) && user= safe_str(acl_db->user);
host= safe_str(acl_db->host.hostname);
if (!strcmp(lex_user->user.str, user) &&
!strcmp(lex_user->host.str, host)) !strcmp(lex_user->host.str, host))
{ {
if (!replace_db_table(tables[1].table, acl_db->db, *lex_user, if (!replace_db_table(tables[1].table, acl_db->db, *lex_user,
...@@ -9293,10 +9254,8 @@ bool mysql_revoke_all(THD *thd, List <LEX_USER> &list) ...@@ -9293,10 +9254,8 @@ bool mysql_revoke_all(THD *thd, List <LEX_USER> &list)
const char *user,*host; const char *user,*host;
GRANT_TABLE *grant_table= GRANT_TABLE *grant_table=
(GRANT_TABLE*) my_hash_element(&column_priv_hash, counter); (GRANT_TABLE*) my_hash_element(&column_priv_hash, counter);
if (!(user=grant_table->user)) user= safe_str(grant_table->user);
user= ""; host= safe_str(grant_table->host.hostname);
if (!(host=grant_table->host.hostname))
host= "";
if (!strcmp(lex_user->user.str,user) && if (!strcmp(lex_user->user.str,user) &&
!strcmp(lex_user->host.str, host)) !strcmp(lex_user->host.str, host))
...@@ -9339,10 +9298,8 @@ bool mysql_revoke_all(THD *thd, List <LEX_USER> &list) ...@@ -9339,10 +9298,8 @@ bool mysql_revoke_all(THD *thd, List <LEX_USER> &list)
{ {
const char *user,*host; const char *user,*host;
GRANT_NAME *grant_proc= (GRANT_NAME*) my_hash_element(hash, counter); GRANT_NAME *grant_proc= (GRANT_NAME*) my_hash_element(hash, counter);
if (!(user=grant_proc->user)) user= safe_str(grant_proc->user);
user= ""; host= safe_str(grant_proc->host.hostname);
if (!(host=grant_proc->host.hostname))
host= "";
if (!strcmp(lex_user->user.str,user) && if (!strcmp(lex_user->user.str,user) &&
!strcmp(lex_user->host.str, host)) !strcmp(lex_user->host.str, host))
...@@ -9488,11 +9445,8 @@ bool sp_revoke_privileges(THD *thd, const char *sp_db, const char *sp_name, ...@@ -9488,11 +9445,8 @@ bool sp_revoke_privileges(THD *thd, const char *sp_db, const char *sp_name,
LEX_USER lex_user; LEX_USER lex_user;
lex_user.user.str= grant_proc->user; lex_user.user.str= grant_proc->user;
lex_user.user.length= strlen(grant_proc->user); lex_user.user.length= strlen(grant_proc->user);
lex_user.host.str= grant_proc->host.hostname ? lex_user.host.str= safe_str(grant_proc->host.hostname);
grant_proc->host.hostname : (char*)""; lex_user.host.length= strlen(lex_user.host.str);
lex_user.host.length= grant_proc->host.hostname ?
strlen(grant_proc->host.hostname) : 0;
if (replace_routine_table(thd,grant_proc,tables[4].table,lex_user, if (replace_routine_table(thd,grant_proc,tables[4].table,lex_user,
grant_proc->db, grant_proc->tname, grant_proc->db, grant_proc->tname,
is_proc, ~(ulong)0, 1) == 0) is_proc, ~(ulong)0, 1) == 0)
...@@ -9971,10 +9925,8 @@ int fill_schema_user_privileges(THD *thd, TABLE_LIST *tables, COND *cond) ...@@ -9971,10 +9925,8 @@ int fill_schema_user_privileges(THD *thd, TABLE_LIST *tables, COND *cond)
{ {
const char *user,*host, *is_grantable="YES"; const char *user,*host, *is_grantable="YES";
acl_user=dynamic_element(&acl_users,counter,ACL_USER*); acl_user=dynamic_element(&acl_users,counter,ACL_USER*);
if (!(user=acl_user->user.str)) user= safe_str(acl_user->user.str);
user= ""; host= safe_str(acl_user->host.hostname);
if (!(host=acl_user->host.hostname))
host= "";
if (no_global_access && if (no_global_access &&
(strcmp(thd->security_ctx->priv_user, user) || (strcmp(thd->security_ctx->priv_user, user) ||
...@@ -10047,10 +9999,8 @@ int fill_schema_schema_privileges(THD *thd, TABLE_LIST *tables, COND *cond) ...@@ -10047,10 +9999,8 @@ int fill_schema_schema_privileges(THD *thd, TABLE_LIST *tables, COND *cond)
const char *user, *host, *is_grantable="YES"; const char *user, *host, *is_grantable="YES";
acl_db=dynamic_element(&acl_dbs,counter,ACL_DB*); acl_db=dynamic_element(&acl_dbs,counter,ACL_DB*);
if (!(user=acl_db->user)) user= safe_str(acl_db->user);
user= ""; host= safe_str(acl_db->host.hostname);
if (!(host=acl_db->host.hostname))
host= "";
if (no_global_access && if (no_global_access &&
(strcmp(thd->security_ctx->priv_user, user) || (strcmp(thd->security_ctx->priv_user, user) ||
...@@ -10120,11 +10070,9 @@ int fill_schema_table_privileges(THD *thd, TABLE_LIST *tables, COND *cond) ...@@ -10120,11 +10070,9 @@ int fill_schema_table_privileges(THD *thd, TABLE_LIST *tables, COND *cond)
{ {
const char *user, *host, *is_grantable= "YES"; const char *user, *host, *is_grantable= "YES";
GRANT_TABLE *grant_table= (GRANT_TABLE*) my_hash_element(&column_priv_hash, GRANT_TABLE *grant_table= (GRANT_TABLE*) my_hash_element(&column_priv_hash,
index); index);
if (!(user=grant_table->user)) user= safe_str(grant_table->user);
user= ""; host= safe_str(grant_table->host.hostname);
if (!(host= grant_table->host.hostname))
host= "";
if (no_global_access && if (no_global_access &&
(strcmp(thd->security_ctx->priv_user, user) || (strcmp(thd->security_ctx->priv_user, user) ||
...@@ -10204,11 +10152,9 @@ int fill_schema_column_privileges(THD *thd, TABLE_LIST *tables, COND *cond) ...@@ -10204,11 +10152,9 @@ int fill_schema_column_privileges(THD *thd, TABLE_LIST *tables, COND *cond)
{ {
const char *user, *host, *is_grantable= "YES"; const char *user, *host, *is_grantable= "YES";
GRANT_TABLE *grant_table= (GRANT_TABLE*) my_hash_element(&column_priv_hash, GRANT_TABLE *grant_table= (GRANT_TABLE*) my_hash_element(&column_priv_hash,
index); index);
if (!(user=grant_table->user)) user= safe_str(grant_table->user);
user= ""; host= safe_str(grant_table->host.hostname);
if (!(host= grant_table->host.hostname))
host= "";
if (no_global_access && if (no_global_access &&
(strcmp(thd->security_ctx->priv_user, user) || (strcmp(thd->security_ctx->priv_user, user) ||
...@@ -10883,8 +10829,7 @@ static bool find_mpvio_user(MPVIO_EXT *mpvio) ...@@ -10883,8 +10829,7 @@ static bool find_mpvio_user(MPVIO_EXT *mpvio)
mpvio->auth_info.user_name_length= strlen(sctx->user); mpvio->auth_info.user_name_length= strlen(sctx->user);
mpvio->auth_info.auth_string= mpvio->acl_user->auth_string.str; mpvio->auth_info.auth_string= mpvio->acl_user->auth_string.str;
mpvio->auth_info.auth_string_length= (unsigned long) mpvio->acl_user->auth_string.length; mpvio->auth_info.auth_string_length= (unsigned long) mpvio->acl_user->auth_string.length;
strmake_buf(mpvio->auth_info.authenticated_as, mpvio->acl_user->user.str ? strmake_buf(mpvio->auth_info.authenticated_as, safe_str(mpvio->acl_user->user.str));
mpvio->acl_user->user.str : "");
DBUG_PRINT("info", ("exit: user=%s, auth_string=%s, authenticated as=%s" DBUG_PRINT("info", ("exit: user=%s, auth_string=%s, authenticated as=%s"
"plugin=%s", "plugin=%s",
...@@ -11722,12 +11667,12 @@ bool acl_authenticate(THD *thd, uint connect_errors, ...@@ -11722,12 +11667,12 @@ bool acl_authenticate(THD *thd, uint connect_errors,
general_log_print(thd, command, "%s@%s as %s on %s", general_log_print(thd, command, "%s@%s as %s on %s",
sctx->user, sctx->host_or_ip, sctx->user, sctx->host_or_ip,
sctx->priv_user[0] ? sctx->priv_user : "anonymous", sctx->priv_user[0] ? sctx->priv_user : "anonymous",
mpvio.db.str ? mpvio.db.str : (char*) ""); safe_str(mpvio.db.str));
} }
else else
general_log_print(thd, command, (char*) "%s@%s on %s", general_log_print(thd, command, (char*) "%s@%s on %s",
sctx->user, sctx->host_or_ip, sctx->user, sctx->host_or_ip,
mpvio.db.str ? mpvio.db.str : (char*) ""); safe_str(mpvio.db.str));
} }
if (res > CR_OK && mpvio.status != MPVIO_EXT::SUCCESS) if (res > CR_OK && mpvio.status != MPVIO_EXT::SUCCESS)
...@@ -11745,7 +11690,7 @@ bool acl_authenticate(THD *thd, uint connect_errors, ...@@ -11745,7 +11690,7 @@ bool acl_authenticate(THD *thd, uint connect_errors,
{ {
#ifndef NO_EMBEDDED_ACCESS_CHECKS #ifndef NO_EMBEDDED_ACCESS_CHECKS
bool is_proxy_user= FALSE; bool is_proxy_user= FALSE;
const char *auth_user = acl_user->user.str ? acl_user->user.str : ""; const char *auth_user = safe_str(acl_user->user.str);
ACL_PROXY_USER *proxy_user; ACL_PROXY_USER *proxy_user;
/* check if the user is allowed to proxy as another user */ /* check if the user is allowed to proxy as another user */
proxy_user= acl_find_proxy_user(auth_user, sctx->host, sctx->ip, proxy_user= acl_find_proxy_user(auth_user, sctx->host, sctx->ip,
...@@ -11765,12 +11710,11 @@ bool acl_authenticate(THD *thd, uint connect_errors, ...@@ -11765,12 +11710,11 @@ bool acl_authenticate(THD *thd, uint connect_errors,
my_snprintf(sctx->proxy_user, sizeof(sctx->proxy_user) - 1, my_snprintf(sctx->proxy_user, sizeof(sctx->proxy_user) - 1,
"'%s'@'%s'", auth_user, "'%s'@'%s'", auth_user,
acl_user->host.hostname ? acl_user->host.hostname : ""); safe_str(acl_user->host.hostname));
/* we're proxying : find the proxy user definition */ /* we're proxying : find the proxy user definition */
mysql_mutex_lock(&acl_cache->lock); mysql_mutex_lock(&acl_cache->lock);
acl_proxy_user= find_user_no_anon(proxy_user->get_proxied_host() ? acl_proxy_user= find_user_no_anon(safe_str(proxy_user->get_proxied_host()),
proxy_user->get_proxied_host() : "",
mpvio.auth_info.authenticated_as, mpvio.auth_info.authenticated_as,
TRUE); TRUE);
if (!acl_proxy_user) if (!acl_proxy_user)
......
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