Last active
August 29, 2015 14:05
-
-
Save oyyq99999/8e95f9f9f2c55ae84343 to your computer and use it in GitHub Desktop.
md2 algo
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package oyyq.test.hash.md2; | |
import java.util.Arrays; | |
public class Md2Hash { | |
private static class Md2STableGenerator { | |
private static int offset = 0; | |
private static final int[] PI = {3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5, 8, 9, 7, 9, 3, 2, 3, | |
8, 4, 6, 2, 6, 4, 3, 3, 8, 3, 2, 7, 9, 5, 0, 2, | |
8, 8, 4, 1, 9, 7, 1, 6, 9, 3, 9, 9, 3, 7, 5, 1, | |
0, 5, 8, 2, 0, 9, 7, 4, 9, 4, 4, 5, 9, 2, 3, 0, | |
7, 8, 1, 6, 4, 0, 6, 2, 8, 6, 2, 0, 8, 9, 9, 8, | |
6, 2, 8, 0, 3, 4, 8, 2, 5, 3, 4, 2, 1, 1, 7, 0, | |
6, 7, 9, 8, 2, 1, 4, 8, 0, 8, 6, 5, 1, 3, 2, 8, | |
2, 3, 0, 6, 6, 4, 7, 0, 9, 3, 8, 4, 4, 6, 0, 9, | |
5, 5, 0, 5, 8, 2, 2, 3, 1, 7, 2, 5, 3, 5, 9, 4, | |
0, 8, 1, 2, 8, 4, 8, 1, 1, 1, 7, 4, 5, 0, 2, 8, | |
4, 1, 0, 2, 7, 0, 1, 9, 3, 8, 5, 2, 1, 1, 0, 5, | |
5, 5, 9, 6, 4, 4, 6, 2, 2, 9, 4, 8, 9, 5, 4, 9, | |
3, 0, 3, 8, 1, 9, 6, 4, 4, 2, 8, 8, 1, 0, 9, 7, | |
5, 6, 6, 5, 9, 3, 3, 4, 4, 6, 1, 2, 8, 4, 7, 5, | |
6, 4, 8, 2, 3, 3, 7, 8, 6, 7, 8, 3, 1, 6, 5, 2, | |
7, 1, 2, 0, 1, 9, 0, 9, 1, 4, 5, 6, 4, 8, 5, 6, | |
6, 9, 2, 3, 4, 6, 0, 3, 4, 8, 6, 1, 0, 4, 5, 4, | |
3, 2, 6, 6, 4, 8, 2, 1, 3, 3, 9, 3, 6, 0, 7, 2, | |
6, 0, 2, 4, 9, 1, 4, 1, 2, 7, 3, 7, 2, 4, 5, 8, | |
7, 0, 0, 6, 6, 0, 6, 3, 1, 5, 5, 8, 8, 1, 7, 4, | |
8, 8, 1, 5, 2, 0, 9, 2, 0, 9, 6, 2, 8, 2, 9, 2, | |
5, 4, 0, 9, 1, 7, 1, 5, 3, 6, 4, 3, 6, 7, 8, 9, | |
2, 5, 9, 0, 3, 6, 0, 0, 1, 1, 3, 3, 0, 5, 3, 0, | |
5, 4, 8, 8, 2, 0, 4, 6, 6, 5, 2, 1, 3, 8, 4, 1, | |
4, 6, 9, 5, 1, 9, 4, 1, 5, 1, 1, 6, 0, 9, 4, 3, | |
3, 0, 5, 7, 2, 7, 0, 3, 6, 5, 7, 5, 9, 5, 9, 1, | |
9, 5, 3, 0, 9, 2, 1, 8, 6, 1, 1, 7, 3, 8, 1, 9, | |
3, 2, 6, 1, 1, 7, 9, 3, 1, 0, 5, 1, 1, 8, 5, 4, | |
8, 0, 7, 4, 4, 6, 2, 3, 7, 9, 9, 6, 2, 7, 4, 9, | |
5, 6, 7, 3, 5, 1, 8, 8, 5, 7, 5, 2, 7, 2, 4, 8, | |
9, 1, 2, 2, 7, 9, 3, 8, 1, 8, 3, 0, 1, 1, 9, 4, | |
9, 1, 2, 9, 8, 3, 3, 6, 7, 3, 3, 6, 2, 4, 4, 0, | |
6, 5, 6, 6, 4, 3, 0, 8, 6, 0, 2, 1, 3, 9, 4, 9, | |
4, 6, 3, 9, 5, 2, 2, 4, 7, 3, 7, 1, 9, 0, 7, 0, | |
2, 1, 7, 9, 8, 6, 0, 9, 4, 3, 7, 0, 2, 7, 7, 0, | |
5, 3, 9, 2, 1, 7, 1, 7, 6, 2, 9, 3, 1, 7, 6, 7, | |
5, 2, 3, 8, 4, 6, 7, 4, 8, 1, 8, 4, 6, 7, 6, 6, | |
9, 4, 0, 5, 1, 3, 2, 0, 0, 0, 5, 6, 8, 1, 2, 7, | |
1, 4, 5, 2, 6, 3, 5, 6, 0, 8, 2, 7, 7, 8, 5, 7, | |
7, 1, 3, 4, 2, 7, 5, 7, 7, 8, 9, 6, 0, 9, 1, 7, | |
3, 6, 3, 7, 1, 7, 8, 7, 2, 1, 4, 6, 8, 4, 4, 0, | |
9, 0, 1, 2, 2, 4, 9, 5, 3, 4, 3, 0, 1, 4, 6, 5, | |
4, 9, 5, 8, 5, 3, 7, 1, 0, 5, 0, 7, 9, 2, 2, 7, | |
9, 6, 8, 9, 2, 5, 8, 9, 2, 3, 5, 4, 2, 0, 1, 9, | |
9, 5, 6, 1, 1, 2, 1, 2, 9, 0, 2, 1, 9, 6, 0, 8, | |
6, 4, 0, 3, 4, 4, 1, 8, 1, 5, 9, 8, 1, 3, 6, 2, | |
9, 7, 7, 4, 7, 7, 1, 3, 0, 9, 9, 6, 0, 5, 1, 8, | |
7, 0, 7, 2, 1, 1, 3, 4, 9, 9, 9, 9, 9, 9, 8, 3, | |
7, 2, 9, 7, 8, 0, 4, 9, 9, 5, 1, 0, 5, 9, 7, 3, | |
1, 7, 3, 2, 8, 1, 6, 0, 9, 6, 3, 1, 8, 5, 9, 5, | |
0, 2, 4, 4, 5, 9, 4, 5, 5, 3, 4, 6, 9, 0, 8, 3, | |
0, 2, 6, 4, 2, 5, 2, 2, 3, 0, 8, 2, 5, 3, 3, 4, | |
4, 6, 8, 5, 0, 3, 5, 2, 6, 1, 9, 3, 1, 1, 8, 8, | |
1, 7, 1, 0, 1, 0, 0, 0, 3, 1, 3, 7, 8, 3, 8, 7, | |
5, 2, 8, 8, 6, 5, 8, 7, 5, 3, 3, 2, 0, 8, 3, 8, | |
1, 4, 2, 0, 6, 1, 7, 1, 7, 7, 6, 6, 9, 1, 4, 7, | |
3, 0, 3, 5, 9, 8, 2, 5, 3, 4, 9, 0, 4, 2, 8, 7, | |
5, 5, 4, 6, 8, 7, 3, 1, 1, 5, 9, 5, 6, 2, 8, 6, | |
3, 8, 8, 2, 3, 5, 3, 7, 8, 7, 5, 9, 3, 7, 5, 1, | |
9, 5, 7, 7, 8, 1, 8, 5, 7, 7, 8, 0, 5, 3, 2, 1, | |
7, 1, 2, 2, 6, 8, 0, 6, 6, 1, 3, 0, 0, 1, 9, 2, | |
7, 8, 7, 6, 6, 1, 1, 1, 9, 5, 9, 0, 9, 2, 1, 6, | |
4, 2, 0, 1, 9, 8, 9}; | |
private static int[] sTable = null; | |
static int[] getSTable() { | |
if (sTable == null) { | |
offset = 0; | |
sTable = new int[256]; | |
for (int i = 0; i < sTable.length; i++) { | |
sTable[i] = (byte) i; | |
} | |
for (int i = 2; i <= sTable.length; i++) { | |
int j = rand(i); | |
int tmp = sTable[j]; | |
sTable[j] = sTable[i - 1]; | |
sTable[i - 1] = tmp; | |
} | |
} | |
return sTable.clone(); | |
} | |
private static int rand(int n) { | |
int x, y; | |
x = PI[offset++]; | |
y = 10; | |
if (n > 10) { | |
x = x * 10 + PI[offset++]; | |
y = 100; | |
} | |
if (n > 100) { | |
x = x * 10 + PI[offset++]; | |
y = 1000; | |
} | |
return x < n * (y / n) ? x % n : rand(n); | |
} | |
} | |
private static final byte BYTE_ZERO = 0; | |
private static int[] s = Md2STableGenerator.getSTable(); | |
private byte[] c = new byte[16]; | |
private int l = 0; | |
private int offset = 0; | |
private byte[] remaining = new byte[16]; | |
private int[] x = new int[48]; | |
public static void main(String[] args) { | |
Md2Hash md2 = new Md2Hash(); | |
// md2.update("The quick brown fox jumps over the lazy".getBytes()); | |
// md2.update(" dog".getBytes()); | |
// md2.reset(); | |
md2.update("The ".getBytes()); | |
md2.update("quick ".getBytes()); | |
md2.update("brown fox jumps over the lazy dog".getBytes()); | |
md2.digest(); | |
} | |
public void digest() { | |
padding(); | |
update(c, false); | |
for (int i = 0; i < 16; i++) { | |
System.out.print(String.format("%02X", x[i])); | |
} | |
System.out.println(); | |
} | |
public void reset() { | |
offset = 0; | |
l = 0; | |
Arrays.fill(x, BYTE_ZERO); | |
Arrays.fill(c, BYTE_ZERO); | |
} | |
public void update(byte[] data) { | |
update(data, true); | |
} | |
private void padding() { | |
byte padLen = (byte) (16 - offset); | |
byte[] pad = new byte[padLen]; | |
Arrays.fill(pad, padLen); | |
update(pad); | |
} | |
private void update(byte[] data, boolean updateChecksum) { | |
int off = 0; | |
byte[] buf = new byte[16]; | |
while (data.length >= off + 16 - offset) { | |
System.arraycopy(remaining, 0, buf, 0, offset); | |
System.arraycopy(data, off, buf, offset, 16 - offset); | |
off += 16 - offset; | |
offset = 0; | |
for (int j = 0; j < 16; j++) { | |
if (updateChecksum) { | |
c[j] = (byte) (c[j] ^ s[(buf[j] ^ l) & 0xff]); | |
l = c[j]; | |
} | |
x[16 + j] = buf[j]; | |
x[32 + j] = x[16 + j] ^ x[j]; | |
} | |
int t = 0; | |
for (int j = 0; j < 18; j++) { | |
for (int k = 0; k < 48; k++) { | |
t = x[k] = (x[k] ^ s[t]) & 0xff; | |
} | |
t = (t + j) & 0xff; | |
} | |
} | |
if (data.length > off) { | |
System.arraycopy(data, off, remaining, offset, data.length - off); | |
offset += data.length - off; | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment