01: /*-------------------------------------------------------------------------
02: *
03: * Copyright (c) 2003-2005, PostgreSQL Global Development Group
04: *
05: * IDENTIFICATION
06: * $PostgreSQL: pgjdbc/org/postgresql/util/MD5Digest.java,v 1.10 2005/01/11 08:25:49 jurka Exp $
07: *
08: *-------------------------------------------------------------------------
09: */
10: package org.postgresql.util;
11:
12: /**
13: * MD5-based utility function to obfuscate passwords before network
14: * transmission.
15: *
16: * @author Jeremy Wohl
17: */
18:
19: import java.security.*;
20:
21: public class MD5Digest {
22: private MD5Digest() {
23: }
24:
25: /*
26: * Encodes user/password/salt information in the following way:
27: * MD5(MD5(password + user) + salt)
28: *
29: * @param user The connecting user.
30: * @param password The connecting user's password.
31: * @param salt A four-salt sent by the server.
32: *
33: * @return A 35-byte array, comprising the string "md5" and an MD5 digest.
34: */
35: public static byte[] encode(String user, String password,
36: byte[] salt) {
37: MessageDigest md;
38: byte[] temp_digest, pass_digest;
39: byte[] hex_digest = new byte[35];
40:
41: try {
42: md = MessageDigest.getInstance("MD5");
43:
44: md.update(password.getBytes("US-ASCII"));
45: md.update(user.getBytes("US-ASCII"));
46: temp_digest = md.digest();
47:
48: bytesToHex(temp_digest, hex_digest, 0);
49: md.update(hex_digest, 0, 32);
50: md.update(salt);
51: pass_digest = md.digest();
52:
53: bytesToHex(pass_digest, hex_digest, 3);
54: hex_digest[0] = (byte) 'm';
55: hex_digest[1] = (byte) 'd';
56: hex_digest[2] = (byte) '5';
57: } catch (Exception e) {
58: ; // "MessageDigest failure; " + e
59: }
60:
61: return hex_digest;
62: }
63:
64: /*
65: * Turn 16-byte stream into a human-readable 32-byte hex string
66: */
67: private static void bytesToHex(byte[] bytes, byte[] hex, int offset) {
68: final char lookup[] = { '0', '1', '2', '3', '4', '5', '6', '7',
69: '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' };
70:
71: int i, c, j, pos = offset;
72:
73: for (i = 0; i < 16; i++) {
74: c = bytes[i] & 0xFF;
75: j = c >> 4;
76: hex[pos++] = (byte) lookup[j];
77: j = (c & 0xF);
78: hex[pos++] = (byte) lookup[j];
79: }
80: }
81: }
|