< prev index next >
src/java.management/share/classes/com/sun/jmx/remote/security/FileLoginModule.java
Print this page
*** 25,45 ****
package com.sun.jmx.remote.security;
import com.sun.jmx.mbeanserver.GetPropertyAction;
import com.sun.jmx.mbeanserver.Util;
- import java.io.BufferedInputStream;
import java.io.File;
- import java.io.FileInputStream;
import java.io.FilePermission;
import java.io.IOException;
import java.security.AccessControlException;
import java.security.AccessController;
import java.util.Arrays;
- import java.util.Hashtable;
import java.util.Map;
- import java.util.Properties;
import javax.security.auth.*;
import javax.security.auth.callback.*;
import javax.security.auth.login.*;
import javax.security.auth.spi.*;
--- 25,41 ----
*** 57,70 ****
* user's name and it is associated with the current {@link Subject}.
* Such principals may be identified and granted management privileges in
* the access control file for JMX remote management or in a Java security
* policy.
*
! * <p> The password file comprises a list of key-value pairs as specified in
! * {@link Properties}. The key represents a user's name and the value is its
! * associated cleartext password. By default, the following password file is
! * used:
* <pre>
* ${java.home}/conf/management/jmxremote.password
* </pre>
* A different password file can be specified via the <code>passwordFile</code>
* configuration option.
--- 53,63 ----
* user's name and it is associated with the current {@link Subject}.
* Such principals may be identified and granted management privileges in
* the access control file for JMX remote management or in a Java security
* policy.
*
! * By default, the following password file is used:
* <pre>
* ${java.home}/conf/management/jmxremote.password
* </pre>
* A different password file can be specified via the <code>passwordFile</code>
* configuration option.
*** 103,112 ****
--- 96,110 ----
*
* <dt> <code>clearPass</code> </dt>
* <dd> if <code>true</code>, this module clears the username and password
* stored in the module's shared state after both phases of authentication
* (login and commit) have completed.</dd>
+ *
+ * <dt> <code>hashPassword</code> </dt>
+ * <dd> if <code>true</code>, this module replaces clear text passwords
+ * with its hash, if present </dd>
+ *
* </dl>
*/
public class FileLoginModule implements LoginModule {
private static final String PASSWORD_FILE_NAME = "jmxremote.password";
*** 133,142 ****
--- 131,141 ----
// Configurable options
private boolean useFirstPass = false;
private boolean tryFirstPass = false;
private boolean storePass = false;
private boolean clearPass = false;
+ private boolean hashPassword = false;
// Authentication status
private boolean succeeded = false;
private boolean commitSucceeded = false;
*** 152,162 ****
private Map<String, ?> options;
private String passwordFile;
private String passwordFileDisplayName;
private boolean userSuppliedPasswordFile;
private boolean hasJavaHomePermission;
! private Properties userCredentials;
/**
* Initialize this <code>LoginModule</code>.
*
* @param subject the <code>Subject</code> to be authenticated.
--- 151,161 ----
private Map<String, ?> options;
private String passwordFile;
private String passwordFileDisplayName;
private boolean userSuppliedPasswordFile;
private boolean hasJavaHomePermission;
! private HashedPasswordManager hashPwdMgr;
/**
* Initialize this <code>LoginModule</code>.
*
* @param subject the <code>Subject</code> to be authenticated.
*** 184,193 ****
--- 183,194 ----
"true".equalsIgnoreCase((String)options.get("useFirstPass"));
storePass =
"true".equalsIgnoreCase((String)options.get("storePass"));
clearPass =
"true".equalsIgnoreCase((String)options.get("clearPass"));
+ hashPassword =
+ "true".equalsIgnoreCase((String)options.get("hashPassword"));
passwordFile = (String)options.get("passwordFile");
passwordFileDisplayName = passwordFile;
userSuppliedPasswordFile = true;
*** 219,239 ****
* is unable to perform the authentication.
*/
public boolean login() throws LoginException {
try {
! loadPasswordFile();
} catch (IOException ioe) {
LoginException le = new LoginException(
"Error: unable to load the password file: " +
passwordFileDisplayName);
throw EnvHelp.initCause(le, ioe);
}
-
- if (userCredentials == null) {
- throw new LoginException
- ("Error: unable to locate the users' credentials.");
}
if (logger.debugOn()) {
logger.debug("login",
"Using password file: " + passwordFileDisplayName);
--- 220,250 ----
* is unable to perform the authentication.
*/
public boolean login() throws LoginException {
try {
! if(hashPwdMgr == null) {
! hashPwdMgr = new HashedPasswordManager(passwordFile, hashPassword);
! } else {
! hashPwdMgr.loadPasswords();
! }
} catch (IOException ioe) {
LoginException le = new LoginException(
"Error: unable to load the password file: " +
passwordFileDisplayName);
throw EnvHelp.initCause(le, ioe);
+ } catch (SecurityException e) {
+ if (userSuppliedPasswordFile || hasJavaHomePermission) {
+ throw e;
+ } else {
+ final FilePermission fp =
+ new FilePermission(passwordFileDisplayName, "read");
+ AccessControlException ace = new AccessControlException(
+ "access denied " + fp.toString());
+ ace.setStackTrace(e.getStackTrace());
+ throw ace;
}
}
if (logger.debugOn()) {
logger.debug("login",
"Using password file: " + passwordFileDisplayName);
*** 435,450 ****
throws LoginException {
// get the username and password
getUsernamePassword(usePasswdFromSharedState);
! String localPassword;
!
! // userCredentials is initialized in login()
! if (((localPassword = userCredentials.getProperty(username)) == null) ||
! (! localPassword.equals(new String(password)))) {
!
// username not found or passwords do not match
if (logger.debugOn()) {
logger.debug("login", "Invalid username or password");
}
throw new FailedLoginException("Invalid username or password");
--- 446,456 ----
throws LoginException {
// get the username and password
getUsernamePassword(usePasswdFromSharedState);
! if (!hashPwdMgr.authenticate(username, new String(password))) {
// username not found or passwords do not match
if (logger.debugOn()) {
logger.debug("login", "Invalid username or password");
}
throw new FailedLoginException("Invalid username or password");
*** 466,507 ****
logger.debug("login",
"User '" + username + "' successfully validated");
}
}
- /*
- * Read the password file.
- */
- private void loadPasswordFile() throws IOException {
- FileInputStream fis;
- try {
- fis = new FileInputStream(passwordFile);
- } catch (SecurityException e) {
- if (userSuppliedPasswordFile || hasJavaHomePermission) {
- throw e;
- } else {
- final FilePermission fp =
- new FilePermission(passwordFileDisplayName, "read");
- AccessControlException ace = new AccessControlException(
- "access denied " + fp.toString());
- ace.setStackTrace(e.getStackTrace());
- throw ace;
- }
- }
- try {
- final BufferedInputStream bis = new BufferedInputStream(fis);
- try {
- userCredentials = new Properties();
- userCredentials.load(bis);
- } finally {
- bis.close();
- }
- } finally {
- fis.close();
- }
- }
-
/**
* Get the username and password.
* This method does not return any value.
* Instead, it sets global name and password variables.
*
--- 472,481 ----
< prev index next >