4 * Implements the MD5 Message-Digest Algorithm as specified in
5 * RFC 1321. This implementation is a simple one, in that it
6 * needs every input byte to be buffered before doing any
7 * calculations. I do not expect this file to be used for
8 * general purpose MD5'ing of large amounts of data, only for
9 * generating hashed passwords from limited input.
11 * Sverre H. Huseby <sverrehu@online.no>
13 * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group
14 * Portions Copyright (c) 1994, Regents of the University of California
16 * This file is imported from PostgreSQL 8.1.3., and modified by
17 * Taiki Yamaguchi <yamaguchi@sraoss.co.jp>
20 * $Header: /cvsroot/pgpool/pgpool-II/md5.c,v 1.1.1.1.6.1 2009/08/22 04:19:49 t-ishii Exp $
30 typedef unsigned char uint8; /* == 8 bits */
31 typedef unsigned int uint32; /* == 32 bits */
50 #define F(x, y, z) (((x) & (y)) | ((~x) & (z)))
51 #define G(x, y, z) (((x) & (z)) | ((y) & (~z)))
52 #define H(x, y, z) ((x) ^ (y) ^ (z))
53 #define I(x, y, z) ((y) ^ ((x) | (~z)))
55 #define ROTATE_LEFT(x, n) (((x) << (n)) | ((x) >> (32 - (n))))
57 #define FF(a, b, c, d, x, s, ac) { \
58 (a) += F((b), (c), (d)) + (x) + (uint32)(ac); \
59 (a) = ROTATE_LEFT((a), (s)); \
63 #define GG(a, b, c, d, x, s, ac) { \
64 (a) += G((b), (c), (d)) + (x) + (uint32)(ac); \
65 (a) = ROTATE_LEFT((a), (s)); \
69 #define HH(a, b, c, d, x, s, ac) { \
70 (a) += H((b), (c), (d)) + (x) + (uint32)(ac); \
71 (a) = ROTATE_LEFT((a), (s)); \
75 #define II(a, b, c, d, x, s, ac) { \
76 (a) += I((b), (c), (d)) + (x) + (uint32)(ac); \
77 (a) = ROTATE_LEFT((a), (s)); \
83 0xd76aa478, 0xe8c7b756, 0x242070db, 0xc1bdceee, 0xf57c0faf, 0x4787c62a, 0xa8304613, 0xfd469501,
84 0x698098d8, 0x8b44f7af, 0xffff5bb1, 0x895cd7be, 0x6b901122, 0xfd987193, 0xa679438e, 0x49b40821,
86 0xf61e2562, 0xc040b340, 0x265e5a51, 0xe9b6c7aa, 0xd62f105d, 0x02441453, 0xd8a1e681, 0xe7d3fbc8,
87 0x21e1cde6, 0xc33707d6, 0xf4d50d87, 0x455a14ed, 0xa9e3e905, 0xfcefa3f8, 0x676f02d9, 0x8d2a4c8a,
89 0xfffa3942, 0x8771f681, 0x6d9d6122, 0xfde5380c, 0xa4beea44, 0x4bdecfa9, 0xf6bb4b60, 0xbebfbc70,
90 0x289b7ec6, 0xeaa127fa, 0xd4ef3085, 0x04881d05, 0xd9d4d039, 0xe6db99e5, 0x1fa27cf8, 0xc4ac5665,
92 0xf4292244, 0x432aff97, 0xab9423a7, 0xfc93a039, 0x655b59c3, 0x8f0ccc92, 0xffeff47d, 0x85845dd1,
93 0x6fa87e4f, 0xfe2ce6e0, 0xa3014314, 0x4e0811a1, 0xf7537e82, 0xbd3af235, 0x2ad7d2bb, 0xeb86d391
103 * The returned array is allocated using malloc. the caller should free it
104 * when it is no longer needed.
107 createPaddedCopyWithLength(uint8 *b, uint32 *l)
110 * uint8 *b - message to be digested
111 * uint32 *l - length of b
118 len_low; /* 64-bit value split into 32-bit sections */
120 len = ((b == NULL) ? 0 : *l);
121 newLen448 = len + 64 - (len % 64) - 8;
122 if (newLen448 <= len)
126 if ((ret = (uint8 *) malloc(sizeof(uint8) * *l)) == NULL)
130 memcpy(ret, b, sizeof(uint8) * len);
134 for (q = len + 1; q < newLen448; q++)
137 /* append length as a 64 bit bitcount */
139 /* split into two 32-bit values */
140 /* we only look at the bottom 32-bits */
141 len_high = len >> 29;
144 ret[q++] = (len_low & 0xff);
146 ret[q++] = (len_low & 0xff);
148 ret[q++] = (len_low & 0xff);
150 ret[q++] = (len_low & 0xff);
151 ret[q++] = (len_high & 0xff);
153 ret[q++] = (len_high & 0xff);
155 ret[q++] = (len_high & 0xff);
157 ret[q] = (len_high & 0xff);
163 doTheRounds(uint32 X[16], uint32 state[4])
176 FF(a, b, c, d, X[ 0], S11, T[ 0]);
177 FF(d, a, b, c, X[ 1], S12, T[ 1]);
178 FF(c, d, a, b, X[ 2], S13, T[ 2]);
179 FF(b, c, d, a, X[ 3], S14, T[ 3]);
180 FF(a, b, c, d, X[ 4], S11, T[ 4]);
181 FF(d, a, b, c, X[ 5], S12, T[ 5]);
182 FF(c, d, a, b, X[ 6], S13, T[ 6]);
183 FF(b, c, d, a, X[ 7], S14, T[ 7]);
184 FF(a, b, c, d, X[ 8], S11, T[ 8]);
185 FF(d, a, b, c, X[ 9], S12, T[ 9]);
186 FF(c, d, a, b, X[10], S13, T[10]);
187 FF(b, c, d, a, X[11], S14, T[11]);
188 FF(a, b, c, d, X[12], S11, T[12]);
189 FF(d, a, b, c, X[13], S12, T[13]);
190 FF(c, d, a, b, X[14], S13, T[14]);
191 FF(b, c, d, a, X[15], S14, T[15]);
193 GG(a, b, c, d, X[ 1], S21, T[16]);
194 GG(d, a, b, c, X[ 6], S22, T[17]);
195 GG(c, d, a, b, X[11], S23, T[18]);
196 GG(b, c, d, a, X[ 0], S24, T[19]);
197 GG(a, b, c, d, X[ 5], S21, T[20]);
198 GG(d, a, b, c, X[10], S22, T[21]);
199 GG(c, d, a, b, X[15], S23, T[22]);
200 GG(b, c, d, a, X[ 4], S24, T[23]);
201 GG(a, b, c, d, X[ 9], S21, T[24]);
202 GG(d, a, b, c, X[14], S22, T[25]);
203 GG(c, d, a, b, X[ 3], S23, T[26]);
204 GG(b, c, d, a, X[ 8], S24, T[27]);
205 GG(a, b, c, d, X[13], S21, T[28]);
206 GG(d, a, b, c, X[ 2], S22, T[29]);
207 GG(c, d, a, b, X[ 7], S23, T[30]);
208 GG(b, c, d, a, X[12], S24, T[31]);
210 HH(a, b, c, d, X[ 5], S31, T[32]);
211 HH(d, a, b, c, X[ 8], S32, T[33]);
212 HH(c, d, a, b, X[11], S33, T[34]);
213 HH(b, c, d, a, X[14], S34, T[35]);
214 HH(a, b, c, d, X[ 1], S31, T[36]);
215 HH(d, a, b, c, X[ 4], S32, T[37]);
216 HH(c, d, a, b, X[ 7], S33, T[38]);
217 HH(b, c, d, a, X[10], S34, T[39]);
218 HH(a, b, c, d, X[13], S31, T[40]);
219 HH(d, a, b, c, X[ 0], S32, T[41]);
220 HH(c, d, a, b, X[ 3], S33, T[42]);
221 HH(b, c, d, a, X[ 6], S34, T[43]);
222 HH(a, b, c, d, X[ 9], S31, T[44]);
223 HH(d, a, b, c, X[12], S32, T[45]);
224 HH(c, d, a, b, X[15], S33, T[46]);
225 HH(b, c, d, a, X[ 2], S34, T[47]);
227 II(a, b, c, d, X[ 0], S41, T[48]);
228 II(d, a, b, c, X[ 7], S42, T[49]);
229 II(c, d, a, b, X[14], S43, T[50]);
230 II(b, c, d, a, X[ 5], S44, T[51]);
231 II(a, b, c, d, X[12], S41, T[52]);
232 II(d, a, b, c, X[ 3], S42, T[53]);
233 II(c, d, a, b, X[10], S43, T[54]);
234 II(b, c, d, a, X[ 1], S44, T[55]);
235 II(a, b, c, d, X[ 8], S41, T[56]);
236 II(d, a, b, c, X[15], S42, T[57]);
237 II(c, d, a, b, X[ 6], S43, T[58]);
238 II(b, c, d, a, X[13], S44, T[59]);
239 II(a, b, c, d, X[ 4], S41, T[60]);
240 II(d, a, b, c, X[11], S42, T[61]);
241 II(c, d, a, b, X[ 2], S43, T[62]);
242 II(b, c, d, a, X[ 9], S44, T[63]);
251 calculateDigestFromBuffer(uint8 *b, uint32 len, uint8 sum[16])
254 * uint8 *b - message to be digested
255 * uint32 len - length of b
256 * uint8 sum[16] - md5 digest calculated from b
265 register uint32 *wbp;
271 state[0] = 0x67452301;
272 state[1] = 0xEFCDAB89;
273 state[2] = 0x98BADCFE;
274 state[3] = 0x10325476;
276 if ((input = createPaddedCopyWithLength(b, &l)) == NULL)
281 if ((newI = i + 16 * 4) > l)
284 for (j = 0; j < 16; j++)
286 wbp = (workBuff + j);
296 doTheRounds(workBuff, state);
302 for (i = 0; i < 4; i++)
305 sum[j++] = (k & 0xff);
307 sum[j++] = (k & 0xff);
309 sum[j++] = (k & 0xff);
311 sum[j++] = (k & 0xff);
317 bytesToHex(uint8 b[16], char *s)
319 static const char *hex = "0123456789abcdef";
323 for (q = 0, w = 0; q < 16; q++)
325 s[w++] = hex[(b[q] >> 4) & 0x0F];
326 s[w++] = hex[b[q] & 0x0F];
338 * Calculates the MD5 sum of the bytes in a buffer.
340 * SYNOPSIS int pool_md5_hash(const void *buff, size_t len, char *hexsum)
342 * INPUT buff the buffer containing the bytes that you want
344 * len number of bytes in the buffer.
346 * OUTPUT hexsum the MD5 sum as a '\0'-terminated string of
347 * hexadecimal digits. an MD5 sum is 16 bytes long.
348 * each byte is represented by two heaxadecimal
349 * characters. you thus need to provide an array
350 * of 33 characters, including the trailing '\0'.
352 * RETURNS false on failure (out of memory for internal buffers) or
355 * STANDARDS MD5 is described in RFC 1321.
357 * AUTHOR Sverre H. Huseby <sverrehu@online.no>
358 * MODIFIED by Taiki Yamaguchi <yamaguchi@sraoss.co.jp>
362 pool_md5_hash(const void *buff, size_t len, char *hexsum)
366 if (!calculateDigestFromBuffer((uint8 *) buff, len, sum))
367 return 0; /* failed */
369 bytesToHex(sum, hexsum);
370 return 1; /* success */
374 * Computes MD5 checksum of "passwd" (a null-terminated string) followed
375 * by "salt" (which need not be null-terminated).
377 * Output format is a 32-hex-digit MD5 checksum.
378 * Hence, the output buffer "buf" must be at least 33 bytes long.
380 * Returns 1 if okay, 0 on error (out of memory).
383 pool_md5_encrypt(const char *passwd, const char *salt, size_t salt_len,
386 size_t passwd_len = strlen(passwd);
387 char *crypt_buf = malloc(passwd_len + salt_len);
391 return 0; /* failed */
394 * Place salt at the end because it may be known by users trying to crack
397 strcpy(crypt_buf, passwd);
398 memcpy(crypt_buf + passwd_len, salt, salt_len);
400 ret = pool_md5_hash(crypt_buf, passwd_len + salt_len, buf);