2007-08-09 15:03:39 +00:00
< ? php
2009-08-29 13:57:50 +00:00
$USER = $_GET [ " user " ];
2009-06-13 20:04:22 +00:00
$privileges = array ( " " => array ( " All privileges " => " " ));
2009-09-22 10:51:40 +00:00
$result = $connection -> query ( " SHOW PRIVILEGES " );
2007-08-10 15:09:17 +00:00
while ( $row = $result -> fetch_assoc ()) {
2009-07-13 21:46:16 +00:00
foreach ( explode ( " , " , ( $row [ " Privilege " ] == " Grant option " ? " " : $row [ " Context " ])) as $context ) {
$privileges [ $context ][ $row [ " Privilege " ]] = $row [ " Comment " ];
2007-08-10 15:09:17 +00:00
}
}
$privileges [ " Server Admin " ] += $privileges [ " File access on server " ];
2009-06-21 23:20:32 +00:00
$privileges [ " Databases " ][ " Create routine " ] = $privileges [ " Procedures " ][ " Create routine " ]; // MySQL bug #30305
unset ( $privileges [ " Procedures " ][ " Create routine " ]);
2007-08-10 15:09:17 +00:00
$privileges [ " Columns " ] = array ();
foreach ( array ( " Select " , " Insert " , " Update " , " References " ) as $val ) {
$privileges [ " Columns " ][ $val ] = $privileges [ " Tables " ][ $val ];
}
unset ( $privileges [ " Server Admin " ][ " Usage " ]);
foreach ( $privileges [ " Tables " ] as $key => $val ) {
unset ( $privileges [ " Databases " ][ $key ]);
}
2008-07-10 15:39:24 +00:00
$new_grants = array ();
2007-08-09 15:03:39 +00:00
if ( $_POST ) {
foreach ( $_POST [ " objects " ] as $key => $val ) {
$new_grants [ $val ] = (( array ) $new_grants [ $val ]) + (( array ) $_POST [ " grants " ][ $key ]);
}
}
$grants = array ();
$old_pass = " " ;
2009-09-22 10:51:40 +00:00
if ( isset ( $_GET [ " host " ]) && ( $result = $connection -> query ( " SHOW GRANTS FOR " . $connection -> quote ( $USER ) . " @ " . $connection -> quote ( $_GET [ " host " ])))) { //! use information_schema for MySQL 5 - column names in column privileges are not escaped
2007-08-09 15:03:39 +00:00
while ( $row = $result -> fetch_row ()) {
2009-06-13 20:04:22 +00:00
if ( preg_match ( '~GRANT (.*) ON (.*) TO ~' , $row [ 0 ], $match ) && preg_match_all ( '~ *([^(,]*[^ ,(])( *\\([^)]+\\))?~' , $match [ 1 ], $matches , PREG_SET_ORDER )) { //! escape the part between ON and TO
foreach ( $matches as $val ) {
$grants [ " $match[2] $val[2] " ][ $val [ 1 ]] = true ;
2009-07-13 16:03:51 +00:00
if ( ereg ( ' WITH GRANT OPTION' , $row [ 0 ])) { //! don't check inside strings and identifiers
2009-06-13 20:04:22 +00:00
$grants [ " $match[2] $val[2] " ][ " GRANT OPTION " ] = true ;
2007-08-10 15:09:17 +00:00
}
2007-08-09 15:03:39 +00:00
}
}
if ( preg_match ( " ~ IDENTIFIED BY PASSWORD '([^']+)~ " , $row [ 0 ], $match )) {
$old_pass = $match [ 1 ];
}
}
}
if ( $_POST && ! $error ) {
2009-09-22 10:51:40 +00:00
$old_user = ( isset ( $_GET [ " host " ]) ? $connection -> quote ( $USER ) . " @ " . $connection -> quote ( $_GET [ " host " ]) : " '' " );
$new_user = $connection -> quote ( $_POST [ " user " ]) . " @ " . $connection -> quote ( $_POST [ " host " ]); // if $_GET["host"] is not set then $new_user is always different
$pass = $connection -> quote ( $_POST [ " pass " ]);
2007-08-09 15:03:39 +00:00
if ( $_POST [ " drop " ]) {
2009-07-30 08:12:54 +00:00
query_redirect ( " DROP USER $old_user " , ME . " privileges= " , lang ( 'User has been dropped.' ));
2009-06-13 20:04:22 +00:00
} else {
2007-08-11 06:25:58 +00:00
if ( $old_user == $new_user ) {
2009-06-22 00:53:51 +00:00
queries ( " SET PASSWORD FOR $new_user = " . ( $_POST [ " hashed " ] ? $pass : " PASSWORD( $pass ) " ));
2009-06-13 20:04:22 +00:00
} else {
2009-09-22 10:51:40 +00:00
$error = ! queries (( $connection -> server_info < 5 ? " GRANT USAGE ON *.* TO " : " CREATE USER " ) . " $new_user IDENTIFIED BY " . ( $_POST [ " hashed " ] ? " PASSWORD " : " " ) . " $pass " );
2007-08-11 06:25:58 +00:00
}
2009-06-13 20:04:22 +00:00
if ( ! $error ) {
$revoke = array ();
foreach ( $new_grants as $object => $grant ) {
if ( isset ( $_GET [ " grant " ])) {
$grant = array_filter ( $grant );
}
$grant = array_keys ( $grant );
if ( isset ( $_GET [ " grant " ])) {
2009-06-21 23:20:32 +00:00
// no rights to mysql.user table
2009-06-13 20:04:22 +00:00
$revoke = array_diff ( array_keys ( array_filter ( $new_grants [ $object ], 'strlen' )), $grant );
} elseif ( $old_user == $new_user ) {
$old_grant = array_keys (( array ) $grants [ $object ]);
$revoke = array_diff ( $old_grant , $grant );
$grant = array_diff ( $grant , $old_grant );
unset ( $grants [ $object ]);
}
if ( preg_match ( '~^(.+)\\s*(\\(.*\\))?$~U' , $object , $match ) && (
2009-12-03 21:02:04 +00:00
! grant ( " REVOKE " , $revoke , $match [ 2 ], " ON $match[1] FROM $new_user " ) //! SQL injection
|| ! grant ( " GRANT " , $grant , $match [ 2 ], " ON $match[1] TO $new_user " )
2009-06-13 20:04:22 +00:00
)) {
$error = true ;
break ;
2007-08-09 15:03:39 +00:00
}
}
}
2009-06-13 20:04:22 +00:00
if ( ! $error && isset ( $_GET [ " host " ])) {
if ( $old_user != $new_user ) {
2009-06-22 00:53:51 +00:00
queries ( " DROP USER $old_user " );
2007-08-10 15:09:17 +00:00
} elseif ( ! isset ( $_GET [ " grant " ])) {
2007-08-09 15:03:39 +00:00
foreach ( $grants as $object => $revoke ) {
if ( preg_match ( '~^(.+)(\\(.*\\))?$~U' , $object , $match )) {
2009-06-22 00:53:51 +00:00
queries ( " REVOKE " . grant ( array_keys ( $revoke ), $match [ 2 ]) . " ON $match[1] FROM $new_user " );
2007-08-09 15:03:39 +00:00
}
}
}
}
2009-10-13 20:01:52 +00:00
queries_redirect ( ME . " privileges= " , ( isset ( $_GET [ " host " ]) ? lang ( 'User has been altered.' ) : lang ( 'User has been created.' )), ! $error );
2009-06-13 20:04:22 +00:00
if ( $old_user != $new_user ) {
2009-06-22 05:22:41 +00:00
// delete new user in case of an error
2009-09-22 10:51:40 +00:00
$connection -> query ( " DROP USER $new_user " );
2009-06-13 20:04:22 +00:00
}
2007-08-09 15:03:39 +00:00
}
}
2009-07-20 12:12:55 +00:00
2009-08-29 13:57:50 +00:00
page_header (( isset ( $_GET [ " host " ]) ? lang ( 'Username' ) . " : " . h ( " $USER @ $_GET[host] " ) : lang ( 'Create user' )), $error , array ( " privileges " => array ( '' , lang ( 'Privileges' ))));
2007-08-09 15:03:39 +00:00
if ( $_POST ) {
$row = $_POST ;
$grants = $new_grants ;
} else {
2009-09-22 10:51:40 +00:00
$row = $_GET + array ( " host " => $connection -> result ( $connection -> query ( " SELECT SUBSTRING_INDEX(CURRENT_USER, '@', -1) " ))); // create user on the same domain by default
2007-08-09 15:03:39 +00:00
$row [ " pass " ] = $old_pass ;
if ( strlen ( $old_pass )) {
$row [ " hashed " ] = true ;
}
$grants [ " " ] = true ;
}
?>
< form action = " " method = " post " >
2009-05-01 10:41:33 +00:00
< table cellspacing = " 0 " >
2009-07-28 16:20:50 +00:00
< tr >< th >< ? php echo lang ( 'Username' ); ?> <td><input name="user" maxlength="16" value="<?php echo h($row["user"]); ?>">
< tr >< th >< ? php echo lang ( 'Server' ); ?> <td><input name="host" maxlength="60" value="<?php echo h($row["host"]); ?>">
2009-09-25 12:03:30 +00:00
< tr >< th >< ? php echo lang ( 'Password' ); ?> <td><input id="pass" name="pass" value="<?php echo h($row["pass"]); ?>">
2009-12-17 13:22:28 +00:00
< ? php if ( ! $row [ " hashed " ]) { ?> <script type="text/javascript">typePassword(document.getElementById('pass'));</script><?php } ?>
< ? php echo checkbox ( " hashed " , 1 , $row [ " hashed " ], lang ( 'Hashed' ), " typePassword(this.form['pass'], this.checked); " ); ?>
2007-08-09 15:03:39 +00:00
</ table >
< ? php
//! MAX_* limits, REQUIRE
2009-05-01 10:41:33 +00:00
echo " <table cellspacing='0'> \n " ;
2009-07-11 20:30:40 +00:00
echo " <thead><tr><th colspan='2'> " . lang ( 'Privileges' );
2007-08-09 15:03:39 +00:00
$i = 0 ;
2008-01-08 15:46:32 +00:00
foreach ( $grants as $object => $grant ) {
2009-07-28 16:20:50 +00:00
echo '<th>' . ( $object != " *.* " ? " <input name='objects[ $i ]' value=' " . h ( $object ) . " ' size='10'> " : " <input type='hidden' name='objects[ $i ]' value='*.*' size='10'>*.* " ); //! separate db, table, columns, PROCEDURE|FUNCTION, routine
2008-01-08 15:46:32 +00:00
$i ++ ;
}
2009-07-11 20:30:40 +00:00
echo " </thead> \n " ;
2007-08-09 15:03:39 +00:00
foreach ( array (
2009-06-13 20:04:22 +00:00
" " => " " ,
2007-08-09 15:03:39 +00:00
" Server Admin " => lang ( 'Server' ),
" Databases " => lang ( 'Database' ),
" Tables " => lang ( 'Table' ),
" Columns " => lang ( 'Column' ),
" Procedures " => lang ( 'Routine' ),
2008-01-08 15:46:32 +00:00
) as $context => $desc ) {
foreach (( array ) $privileges [ $context ] as $privilege => $comment ) {
2009-07-28 16:20:50 +00:00
echo " <tr " . odd () . " ><td " . ( $desc ? " > $desc <td " : " colspan='2' " ) . ' lang="en" title="' . h ( $comment ) . '">' . h ( $privilege );
2008-01-08 15:46:32 +00:00
$i = 0 ;
2007-08-09 15:03:39 +00:00
foreach ( $grants as $object => $grant ) {
2009-07-28 16:20:50 +00:00
$name = " 'grants[ $i ][ " . h ( strtoupper ( $privilege )) . " ]' " ;
2008-01-08 15:46:32 +00:00
$value = $grant [ strtoupper ( $privilege )];
if ( $context == " Server Admin " && $object != ( isset ( $grants [ " *.* " ]) ? " *.* " : " " )) {
2009-07-11 20:30:40 +00:00
echo " <td> " ;
2008-01-08 15:46:32 +00:00
} elseif ( isset ( $_GET [ " grant " ])) {
2009-07-28 16:28:47 +00:00
echo " <td><select name= $name ><option><option value='1' " . ( $value ? " selected " : " " ) . " > " . lang ( 'Grant' ) . " <option value='0' " . ( $value == " 0 " ? " selected " : " " ) . " > " . lang ( 'Revoke' ) . " </select> " ;
2008-01-08 15:46:32 +00:00
} else {
2009-12-17 13:22:28 +00:00
echo " <td align='center'><input type='checkbox' name= $name value='1' " . ( $value ? " checked " : " " ) . ( $privilege == " All privileges " ? " id='grants- $i -all' " : ( $privilege == " Grant option " ? " " : " onclick= \" if (this.checked) formUncheck('grants- $i -all'); \" " )) . " > " ; //! uncheck all except grant if all is checked
2007-08-09 15:03:39 +00:00
}
2008-01-08 15:46:32 +00:00
$i ++ ;
2007-08-09 15:03:39 +00:00
}
}
}
2008-01-08 15:46:32 +00:00
echo " </table> \n " ;
2007-08-09 15:03:39 +00:00
?>
< p >
2009-07-11 20:30:40 +00:00
< input type = " hidden " name = " token " value = " <?php echo $token ; ?> " >
< input type = " submit " value = " <?php echo lang('Save'); ?> " >
< ? php if ( isset ( $_GET [ " host " ])) { ?> <input type="submit" name="drop" value="<?php echo lang('Drop'); ?>"<?php echo $confirm; ?>><?php } ?>
2007-08-09 15:03:39 +00:00
</ form >