check_user_privileges.lib.php 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165
  1. <?php
  2. /* vim: set expandtab sw=4 ts=4 sts=4: */
  3. /**
  4. * Get user's global privileges and some db-specific privileges
  5. *
  6. * @package PhpMyAdmin
  7. */
  8. if (! defined('PHPMYADMIN')) {
  9. exit;
  10. }
  11. /**
  12. *
  13. */
  14. $GLOBALS['is_superuser'] = PMA_isSuperuser();
  15. /**
  16. * sets privilege information extracted from SHOW GRANTS result
  17. *
  18. * Detection for some CREATE privilege.
  19. *
  20. * Since MySQL 4.1.2, we can easily detect current user's grants using $userlink
  21. * (no control user needed) and we don't have to try any other method for
  22. * detection
  23. *
  24. * @todo fix to get really all privileges, not only explicitly defined for this user
  25. * from MySQL manual: (http://dev.mysql.com/doc/refman/5.0/en/show-grants.html)
  26. * SHOW GRANTS displays only the privileges granted explicitly to the named
  27. * account. Other privileges might be available to the account, but they are not
  28. * displayed. For example, if an anonymous account exists, the named account
  29. * might be able to use its privileges, but SHOW GRANTS will not display them.
  30. *
  31. * @return void
  32. */
  33. function PMA_analyseShowGrant()
  34. {
  35. if (PMA_Util::cacheExists('is_create_db_priv', true)) {
  36. $GLOBALS['is_create_db_priv'] = PMA_Util::cacheGet('is_create_db_priv', true);
  37. $GLOBALS['is_process_priv'] = PMA_Util::cacheGet('is_process_priv', true);
  38. $GLOBALS['is_reload_priv'] = PMA_Util::cacheGet('is_reload_priv', true);
  39. $GLOBALS['db_to_create'] = PMA_Util::cacheGet('db_to_create', true);
  40. $GLOBALS['dbs_where_create_table_allowed']
  41. = PMA_Util::cacheGet('dbs_where_create_table_allowed', true);
  42. return;
  43. }
  44. // defaults
  45. $GLOBALS['is_create_db_priv'] = false;
  46. $GLOBALS['is_process_priv'] = true;
  47. $GLOBALS['is_reload_priv'] = false;
  48. $GLOBALS['db_to_create'] = '';
  49. $GLOBALS['dbs_where_create_table_allowed'] = array();
  50. $rs_usr = PMA_DBI_try_query('SHOW GRANTS');
  51. if (! $rs_usr) {
  52. return;
  53. }
  54. $re0 = '(^|(\\\\\\\\)+|[^\\\\])'; // non-escaped wildcards
  55. $re1 = '(^|[^\\\\])(\\\)+'; // escaped wildcards
  56. while ($row = PMA_DBI_fetch_row($rs_usr)) {
  57. // extract db from GRANT ... ON *.* or GRANT ... ON db.*
  58. $db_name_offset = strpos($row[0], ' ON ') + 4;
  59. $show_grants_dbname = substr(
  60. $row[0], $db_name_offset,
  61. strpos($row[0], '.', $db_name_offset) - $db_name_offset
  62. );
  63. $show_grants_dbname
  64. = PMA_Util::unQuote($show_grants_dbname, '`');
  65. $show_grants_str = substr($row[0], 6, (strpos($row[0], ' ON ') - 6));
  66. if ($show_grants_str == 'RELOAD') {
  67. $GLOBALS['is_reload_priv'] = true;
  68. }
  69. /**
  70. * @todo if we find CREATE VIEW but not CREATE, do not offer
  71. * the create database dialog box
  72. */
  73. if ($show_grants_str == 'ALL'
  74. || $show_grants_str == 'ALL PRIVILEGES'
  75. || $show_grants_str == 'CREATE'
  76. || strpos($show_grants_str, 'CREATE,') !== false
  77. ) {
  78. if ($show_grants_dbname == '*') {
  79. // a global CREATE privilege
  80. $GLOBALS['is_create_db_priv'] = true;
  81. $GLOBALS['is_reload_priv'] = true;
  82. $GLOBALS['db_to_create'] = '';
  83. $GLOBALS['dbs_where_create_table_allowed'][] = '*';
  84. // @todo we should not break here, cause GRANT ALL *.*
  85. // could be revoked by a later rule like GRANT SELECT ON db.*
  86. break;
  87. } else {
  88. // this array may contain wildcards
  89. $GLOBALS['dbs_where_create_table_allowed'][] = $show_grants_dbname;
  90. $dbname_to_test = PMA_Util::backquote($show_grants_dbname);
  91. if ($GLOBALS['is_create_db_priv']) {
  92. // no need for any more tests if we already know this
  93. continue;
  94. }
  95. // does this db exist?
  96. if ((preg_match('/' . $re0 . '%|_/', $show_grants_dbname)
  97. && ! preg_match('/\\\\%|\\\\_/', $show_grants_dbname))
  98. || (! PMA_DBI_try_query('USE ' . preg_replace('/' . $re1 . '(%|_)/', '\\1\\3', $dbname_to_test))
  99. && substr(PMA_DBI_getError(), 1, 4) != 1044)
  100. ) {
  101. /**
  102. * Do not handle the underscore wildcard
  103. * (this case must be rare anyway)
  104. */
  105. $GLOBALS['db_to_create'] = preg_replace(
  106. '/' . $re0 . '%/', '\\1...',
  107. $show_grants_dbname
  108. );
  109. $GLOBALS['db_to_create'] = preg_replace(
  110. '/' . $re1 . '(%|_)/', '\\1\\3',
  111. $GLOBALS['db_to_create']
  112. );
  113. $GLOBALS['is_create_db_priv'] = true;
  114. /**
  115. * @todo collect $GLOBALS['db_to_create'] into an array,
  116. * to display a drop-down in the "Create database" dialog
  117. */
  118. // we don't break, we want all possible databases
  119. //break;
  120. } // end if
  121. } // end elseif
  122. } // end if
  123. } // end while
  124. PMA_DBI_free_result($rs_usr);
  125. // must also cacheUnset() them in
  126. // libraries/plugins/auth/AuthenticationCookie.class.php
  127. PMA_Util::cacheSet('is_create_db_priv', $GLOBALS['is_create_db_priv'], true);
  128. PMA_Util::cacheSet('is_process_priv', $GLOBALS['is_process_priv'], true);
  129. PMA_Util::cacheSet('is_reload_priv', $GLOBALS['is_reload_priv'], true);
  130. PMA_Util::cacheSet('db_to_create', $GLOBALS['db_to_create'], true);
  131. PMA_Util::cacheSet(
  132. 'dbs_where_create_table_allowed',
  133. $GLOBALS['dbs_where_create_table_allowed'],
  134. true
  135. );
  136. } // end function
  137. if (!PMA_DRIZZLE) {
  138. PMA_analyseShowGrant();
  139. } else {
  140. // todo: for simple_user_policy only database with user's login can be created
  141. // (unless logged in as root)
  142. $GLOBALS['is_create_db_priv'] = $GLOBALS['is_superuser'];
  143. $GLOBALS['is_process_priv'] = false;
  144. $GLOBALS['is_reload_priv'] = false;
  145. $GLOBALS['db_to_create'] = '';
  146. $GLOBALS['dbs_where_create_table_allowed'] = array('*');
  147. }
  148. ?>