Author: brandonwilliams Date: Tue Dec 28 21:55:37 2010 New Revision: 1053457
URL: http://svn.apache.org/viewvc?rev=1053457&view=rev Log: Avoid thread contention in FBUtilities.hash Patch by brandonwilliams and jbellis, reviewed by brandonwilliams for CASSANDRA-1369 Modified: cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/dht/RandomPartitioner.java cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/utils/FBUtilities.java Modified: cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/dht/RandomPartitioner.java URL: http://svn.apache.org/viewvc/cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/dht/RandomPartitioner.java?rev=1053457&r1=1053456&r2=1053457&view=diff ============================================================================== --- cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/dht/RandomPartitioner.java (original) +++ cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/dht/RandomPartitioner.java Tue Dec 28 21:55:37 2010 @@ -80,7 +80,7 @@ public class RandomPartitioner implement public BigIntegerToken getRandomToken() { - BigInteger token = FBUtilities.md5hash(GuidGenerator.guidAsBytes()); + BigInteger token = FBUtilities.hashToBigInteger(GuidGenerator.guidAsBytes()); if ( token.signum() == -1 ) token = token.multiply(BigInteger.valueOf(-1L)); return new BigIntegerToken(token); @@ -126,7 +126,7 @@ public class RandomPartitioner implement { if (key.remaining() == 0) return MINIMUM; - return new BigIntegerToken(FBUtilities.md5hash(key)); + return new BigIntegerToken(FBUtilities.hashToBigInteger(key)); } public Map<Token, Float> describeOwnership(List<Token> sortedTokens) Modified: cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/utils/FBUtilities.java URL: http://svn.apache.org/viewvc/cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/utils/FBUtilities.java?rev=1053457&r1=1053456&r2=1053457&view=diff ============================================================================== --- cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/utils/FBUtilities.java (original) +++ cassandra/branches/cassandra-0.7/src/java/org/apache/cassandra/utils/FBUtilities.java Tue Dec 28 21:55:37 2010 @@ -28,6 +28,7 @@ import java.net.UnknownHostException; import java.nio.ByteBuffer; import java.nio.charset.CharacterCodingException; import java.security.MessageDigest; +import java.security.NoSuchAlgorithmException; import java.util.*; import java.util.concurrent.ExecutionException; import java.util.concurrent.Future; @@ -64,6 +65,22 @@ public class FBUtilities private static volatile InetAddress localInetAddress_; + private static final ThreadLocal<MessageDigest> localMessageDigest = new ThreadLocal<MessageDigest>() + { + @Override + protected MessageDigest initialValue() + { + try + { + return MessageDigest.getInstance("MD5"); + } + catch (NoSuchAlgorithmException e) + { + throw new AssertionError(e); + } + } + }; + public static final int MAX_UNSIGNED_SHORT = 0xFFFF; /** @@ -218,19 +235,20 @@ public class FBUtilities return out; } - public static BigInteger md5hash(ByteBuffer data) + public static BigInteger hashToBigInteger(ByteBuffer data) { - byte[] result = hash("MD5", data); + byte[] result = hash(data); BigInteger hash = new BigInteger(result); return hash.abs(); } - public static byte[] hash(String type, ByteBuffer... data) + public static byte[] hash(ByteBuffer... data) { byte[] result; try { - MessageDigest messageDigest = MessageDigest.getInstance(type); + MessageDigest messageDigest = localMessageDigest.get(); + messageDigest.reset(); for(ByteBuffer block : data) messageDigest.update(block.array(),block.position()+block.arrayOffset(),block.remaining()); result = messageDigest.digest();
