You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tomcat.apache.org by ma...@apache.org on 2014/09/25 21:32:18 UTC
svn commit: r1627597 - in /tomcat/trunk/java/org/apache/catalina:
CredentialHandler.java realm/MessageDigestCredentialHandler.java
Author: markt
Date: Thu Sep 25 19:32:18 2014
New Revision: 1627597
URL: http://svn.apache.org/r1627597
Log:
Add support for the salt$iter$pwd format
Modified:
tomcat/trunk/java/org/apache/catalina/CredentialHandler.java
tomcat/trunk/java/org/apache/catalina/realm/MessageDigestCredentialHandler.java
Modified: tomcat/trunk/java/org/apache/catalina/CredentialHandler.java
URL: http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/catalina/CredentialHandler.java?rev=1627597&r1=1627596&r2=1627597&view=diff
==============================================================================
--- tomcat/trunk/java/org/apache/catalina/CredentialHandler.java (original)
+++ tomcat/trunk/java/org/apache/catalina/CredentialHandler.java Thu Sep 25 19:32:18 2014
@@ -20,5 +20,5 @@ public interface CredentialHandler {
boolean matches(String inputCredentials, String storedCredentials);
- String mutate(String inputCredentials);
+ String mutate(String inputCredentials, byte[] salt, int iterations);
}
Modified: tomcat/trunk/java/org/apache/catalina/realm/MessageDigestCredentialHandler.java
URL: http://svn.apache.org/viewvc/tomcat/trunk/java/org/apache/catalina/realm/MessageDigestCredentialHandler.java?rev=1627597&r1=1627596&r2=1627597&view=diff
==============================================================================
--- tomcat/trunk/java/org/apache/catalina/realm/MessageDigestCredentialHandler.java (original)
+++ tomcat/trunk/java/org/apache/catalina/realm/MessageDigestCredentialHandler.java Thu Sep 25 19:32:18 2014
@@ -32,6 +32,28 @@ import org.apache.tomcat.util.codec.bina
import org.apache.tomcat.util.res.StringManager;
import org.apache.tomcat.util.security.ConcurrentMessageDigest;
+/**
+ * This credential handler supports the following forms of stored passwords:
+ * <ul>
+ * <li><b>encodedCredential</b> - a hex encoded digest of the password digested
+ * using the configured digest</li>
+ * <li><b>{MD5}encodedCredential</b> - a Base64 encoded MD5 digest of the
+ * password</li>
+ * <li><b>{SHA}encodedCredential</b> - a Base64 encoded SHA1 digest of the
+ * password</li>
+ * <li><b>{SSHA}encodedCredential</b> - 20 character salt followed by the salted
+ * SHA1 digest Base64 encoded</li>
+ * <li><b>salt$iterationCount$encodedCredential</b> - a hex encoded salt,
+ * iteration code and a hex encoded credential, each separated by $</li>
+ * </ul>
+ *
+ * Prefixes of {MD5} and {SHA}
+ * <p>
+ * If the stored password form does not included an iteration count then an
+ * iteration count of 1 is used.
+ * <p>
+ * If the stored password form does not include salt then no salt is used.
+ */
public class MessageDigestCredentialHandler implements CredentialHandler {
private static final Log log = LogFactory.getLog(MessageDigestCredentialHandler.class);
@@ -126,9 +148,20 @@ public class MessageDigestCredentialHand
return Arrays.equals(userDigestBytes, serverDigestBytes);
+ } else if (storedCredentials.indexOf('$') > -1) {
+ int sep1 = storedCredentials.indexOf('$');
+ int sep2 = storedCredentials.indexOf('$', sep1);
+ String hexSalt = storedCredentials.substring(0, sep1);
+ int iterations = Integer.parseInt(storedCredentials.substring(sep1 + 1, sep2));
+ String hexEncoded = storedCredentials.substring(sep2 + 1);
+ byte[] salt = HexUtils.fromHexString(hexSalt);
+
+ String userDigest = mutate(inputCredentials, salt, iterations);
+
+ return hexEncoded.equalsIgnoreCase(userDigest);
} else {
// Hex hashes should be compared case-insensitively
- String userDigest = mutate(inputCredentials);
+ String userDigest = mutate(inputCredentials, null, 1);
return storedCredentials.equalsIgnoreCase(userDigest);
}
}
@@ -136,12 +169,19 @@ public class MessageDigestCredentialHand
@Override
- public String mutate(String inputCredentials) {
+ public String mutate(String inputCredentials, byte[] salt, int iterations) {
if (digest == null) {
return inputCredentials;
} else {
- return HexUtils.toHexString(ConcurrentMessageDigest.digest(digest,
- inputCredentials.getBytes(encoding)));
+ byte[] userDigest;
+ if (salt == null) {
+ userDigest = ConcurrentMessageDigest.digest(digest, iterations,
+ inputCredentials.getBytes(encoding));
+ } else {
+ userDigest = ConcurrentMessageDigest.digest(digest, iterations,
+ salt, inputCredentials.getBytes(encoding));
+ }
+ return HexUtils.toHexString(userDigest);
}
}
}
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@tomcat.apache.org
For additional commands, e-mail: dev-help@tomcat.apache.org