1 | package com.jsql.util.bruter; | |
2 | ||
3 | // This file is currently unlocked (change this line if you lock the file) | |
4 | // | |
5 | // $Log: MD4.java,v $ | |
6 | // Revision 1.2 1998/01/05 03:41:19 iang | |
7 | // Added references only. | |
8 | // | |
9 | // Revision 1.1.1.1 1997/11/03 22:36:56 hopwood | |
10 | // + Imported to CVS (tagged as 'start'). | |
11 | // | |
12 | // Revision 0.1.0.0 1997/07/14 R. Naffah | |
13 | // + original version | |
14 | // | |
15 | // $Endlog$ | |
16 | /* | |
17 | * Copyright (c) 1997 Systemics Ltd | |
18 | * on behalf of the Cryptix Development Team. All rights reserved. | |
19 | */ | |
20 | ||
21 | import java.security.MessageDigest; | |
22 | ||
23 | /** | |
24 | * Implements the MD4 message digest algorithm in Java. | |
25 | * <p> | |
26 | * <b>References:</b> | |
27 | * <ol> | |
28 | * <li> Ronald L. Rivest, | |
29 | * "<a href="http://www.roxen.com/rfc/rfc1320.html"> | |
30 | * The MD4 Message-Digest Algorithm</a>", | |
31 | * IETF RFC-1320 (informational). | |
32 | * </ol> | |
33 | * | |
34 | * <p><b>$Revision: 1.2 $</b> | |
35 | * @author Raif S. Naffah | |
36 | */ | |
37 | public class DigestMD4 extends MessageDigest implements Cloneable { | |
38 | | |
39 | // MD4 specific object variables | |
40 | //........................................................................... | |
41 | ||
42 | /** | |
43 | * The size in bytes of the input block to the tranformation algorithm. | |
44 | */ | |
45 | private static final int BLOCK_LENGTH = 64; //512 / 8 | |
46 | ||
47 | /** | |
48 | * 4 32-bit words (interim result) | |
49 | */ | |
50 | private int[] context = new int[4]; | |
51 | ||
52 | /** | |
53 | * Number of bytes processed so far mod. 2 power of 64. | |
54 | */ | |
55 | private long count; | |
56 | ||
57 | /** | |
58 | * 512 bits input buffer = 16 x 32-bit words holds until reaches 512 bits. | |
59 | */ | |
60 | private byte[] buffer = new byte[BLOCK_LENGTH]; | |
61 | ||
62 | /** | |
63 | * 512 bits work buffer = 16 x 32-bit words | |
64 | */ | |
65 | private final int[] X = new int[16]; | |
66 | ||
67 | ||
68 | // Constructors | |
69 | //........................................................................... | |
70 | ||
71 | public DigestMD4() { | |
72 | | |
73 | super("MD4"); | |
74 |
1
1. <init> : removed call to com/jsql/util/bruter/DigestMD4::engineReset → KILLED |
this.engineReset(); |
75 | } | |
76 | ||
77 | /** | |
78 | * This constructor is here to implement cloneability of this class. | |
79 | */ | |
80 | private DigestMD4(DigestMD4 md) { | |
81 | | |
82 | this(); | |
83 | this.context = md.context.clone(); | |
84 | this.buffer = md.buffer.clone(); | |
85 | this.count = md.count; | |
86 | } | |
87 | ||
88 | ||
89 | // Cloneable method implementation | |
90 | //........................................................................... | |
91 | ||
92 | /** | |
93 | * Returns a copy of this MD object. | |
94 | */ | |
95 | @Override | |
96 | public Object clone() throws CloneNotSupportedException { | |
97 | ||
98 | Object clone = super.clone(); | |
99 |
1
1. clone : replaced return value with null for com/jsql/util/bruter/DigestMD4::clone → NO_COVERAGE |
return new DigestMD4(this); |
100 | } | |
101 | ||
102 | ||
103 | // JCE methods | |
104 | //........................................................................... | |
105 | ||
106 | /** | |
107 | * Resets this object disregarding any temporary data present at the | |
108 | * time of the invocation of this call. | |
109 | */ | |
110 | @Override | |
111 | public void engineReset() { | |
112 | | |
113 | // initial values of MD4 i.e. A, B, C, D | |
114 | // as per rfc-1320; they are low-order byte first | |
115 | this.context[0] = 0x67452301; | |
116 | this.context[1] = 0xEFCDAB89; | |
117 | this.context[2] = 0x98BADCFE; | |
118 | this.context[3] = 0x10325476; | |
119 | this.count = 0L; | |
120 | | |
121 |
2
1. engineReset : negated conditional → SURVIVED 2. engineReset : changed conditional boundary → KILLED |
for (int i = 0; i < BLOCK_LENGTH; i++) { |
122 | this.buffer[i] = 0; | |
123 | } | |
124 | } | |
125 | ||
126 | /** | |
127 | * Continues an MD4 message digest using the input byte. | |
128 | */ | |
129 | @Override | |
130 | public void engineUpdate(byte b) { | |
131 | | |
132 | // compute number of bytes still unhashed; ie. present in buffer | |
133 |
1
1. engineUpdate : Replaced long modulus with multiplication → NO_COVERAGE |
int i = (int)(this.count % BLOCK_LENGTH); |
134 |
1
1. engineUpdate : Replaced long addition with subtraction → NO_COVERAGE |
this.count++; // update number of bytes |
135 | this.buffer[i] = b; | |
136 | | |
137 |
1
1. engineUpdate : negated conditional → NO_COVERAGE |
if (i == BLOCK_LENGTH - 1) { |
138 |
1
1. engineUpdate : removed call to com/jsql/util/bruter/DigestMD4::transform → NO_COVERAGE |
this.transform(this.buffer, 0); |
139 | } | |
140 | } | |
141 | ||
142 | /** | |
143 | * MD4 block update operation. | |
144 | * <p> | |
145 | * Continues an MD4 message digest operation, by filling the buffer, | |
146 | * transform(ing) data in 512-bit message block(s), updating the variables | |
147 | * context and count, and leaving (buffering) the remaining bytes in buffer | |
148 | * for the next update or finish. | |
149 | * | |
150 | * @param input input block | |
151 | * @param offset start of meaningful bytes in input | |
152 | * @param len count of bytes in input block to consider | |
153 | */ | |
154 | @Override | |
155 | public void engineUpdate(byte[] input, int offset, int len) { | |
156 | | |
157 | // make sure we don't exceed input's allocated size/length | |
158 |
7
1. engineUpdate : changed conditional boundary → SURVIVED 2. engineUpdate : Replaced long addition with subtraction → SURVIVED 3. engineUpdate : negated conditional → KILLED 4. engineUpdate : negated conditional → KILLED 5. engineUpdate : changed conditional boundary → KILLED 6. engineUpdate : negated conditional → KILLED 7. engineUpdate : changed conditional boundary → KILLED |
if (offset < 0 || len < 0 || (long)offset + len > input.length) { |
159 | throw new ArrayIndexOutOfBoundsException(); | |
160 | } | |
161 | | |
162 | // compute number of bytes still unhashed; ie. present in buffer | |
163 |
1
1. engineUpdate : Replaced long modulus with multiplication → KILLED |
int bufferNdx = (int)(this.count % BLOCK_LENGTH); |
164 |
1
1. engineUpdate : Replaced long addition with subtraction → KILLED |
this.count += len; // update number of bytes |
165 |
1
1. engineUpdate : Replaced integer subtraction with addition → KILLED |
int partLen = BLOCK_LENGTH - bufferNdx; |
166 | int i = 0; | |
167 | | |
168 |
2
1. engineUpdate : negated conditional → KILLED 2. engineUpdate : changed conditional boundary → KILLED |
if (len >= partLen) { |
169 | | |
170 |
1
1. engineUpdate : removed call to java/lang/System::arraycopy → KILLED |
System.arraycopy(input, offset, this.buffer, bufferNdx, partLen); |
171 | ||
172 |
1
1. engineUpdate : removed call to com/jsql/util/bruter/DigestMD4::transform → KILLED |
this.transform(this.buffer, 0); |
173 | ||
174 |
4
1. engineUpdate : Replaced integer subtraction with addition → SURVIVED 2. engineUpdate : changed conditional boundary → SURVIVED 3. engineUpdate : Replaced integer addition with subtraction → KILLED 4. engineUpdate : negated conditional → KILLED |
for (i = partLen; i + BLOCK_LENGTH - 1 < len; i+= BLOCK_LENGTH) { |
175 |
2
1. engineUpdate : Replaced integer addition with subtraction → NO_COVERAGE 2. engineUpdate : removed call to com/jsql/util/bruter/DigestMD4::transform → NO_COVERAGE |
this.transform(input, offset + i); |
176 | } | |
177 | | |
178 | bufferNdx = 0; | |
179 | } | |
180 | | |
181 | // buffer remaining input | |
182 |
2
1. engineUpdate : changed conditional boundary → SURVIVED 2. engineUpdate : negated conditional → KILLED |
if (i < len) { |
183 |
3
1. engineUpdate : Replaced integer addition with subtraction → SURVIVED 2. engineUpdate : Replaced integer subtraction with addition → SURVIVED 3. engineUpdate : removed call to java/lang/System::arraycopy → KILLED |
System.arraycopy(input, offset + i, this.buffer, bufferNdx, len - i); |
184 | } | |
185 | } | |
186 | ||
187 | /** | |
188 | * Completes the hash computation by performing final operations such | |
189 | * as padding. At the return of this engineDigest, the MD engine is | |
190 | * reset. | |
191 | * | |
192 | * @return the array of bytes for the resulting hash value. | |
193 | */ | |
194 | @Override | |
195 | public byte[] engineDigest() { | |
196 | | |
197 | // pad output to 56 mod 64; as RFC1320 puts it: congruent to 448 mod 512 | |
198 |
1
1. engineDigest : Replaced long modulus with multiplication → KILLED |
int bufferNdx = (int)(this.count % BLOCK_LENGTH); |
199 |
4
1. engineDigest : changed conditional boundary → SURVIVED 2. engineDigest : Replaced integer subtraction with addition → NO_COVERAGE 3. engineDigest : negated conditional → KILLED 4. engineDigest : Replaced integer subtraction with addition → KILLED |
int padLen = bufferNdx < 56 ? 56 - bufferNdx : 120 - bufferNdx; |
200 | ||
201 | // padding is alwas binary 1 followed by binary 0s | |
202 |
1
1. engineDigest : Replaced integer addition with subtraction → KILLED |
byte[] tail = new byte[padLen + 8]; |
203 | tail[0] = (byte)0x80; | |
204 | ||
205 | // append length before final transform: | |
206 | // save number of bits, casting the long to an array of 8 bytes | |
207 | // save low-order byte first. | |
208 |
2
1. engineDigest : negated conditional → KILLED 2. engineDigest : changed conditional boundary → KILLED |
for (int i = 0; i < 8; i++) { |
209 |
4
1. engineDigest : Replaced Unsigned Shift Right with Shift Left → SURVIVED 2. engineDigest : Replaced integer addition with subtraction → SURVIVED 3. engineDigest : Replaced long multiplication with division → KILLED 4. engineDigest : Replaced integer multiplication with division → KILLED |
tail[padLen + i] = (byte)((this.count * 8) >>> (8 * i)); |
210 | } | |
211 | | |
212 |
1
1. engineDigest : removed call to com/jsql/util/bruter/DigestMD4::engineUpdate → KILLED |
this.engineUpdate(tail, 0, tail.length); |
213 | ||
214 | byte[] result = new byte[16]; | |
215 | | |
216 | // cast this MD4's context (array of 4 ints) into an array of 16 bytes. | |
217 |
2
1. engineDigest : changed conditional boundary → KILLED 2. engineDigest : negated conditional → KILLED |
for (int i = 0; i < 4; i++) { |
218 |
2
1. engineDigest : changed conditional boundary → KILLED 2. engineDigest : negated conditional → KILLED |
for (int j = 0; j < 4; j++) { |
219 |
4
1. engineDigest : Replaced Unsigned Shift Right with Shift Left → KILLED 2. engineDigest : Replaced integer addition with subtraction → KILLED 3. engineDigest : Replaced integer multiplication with division → KILLED 4. engineDigest : Replaced integer multiplication with division → KILLED |
result[i * 4 + j] = (byte)(this.context[i] >>> (8 * j)); |
220 | } | |
221 | } | |
222 | | |
223 | // reset the engine | |
224 |
1
1. engineDigest : removed call to com/jsql/util/bruter/DigestMD4::engineReset → SURVIVED |
this.engineReset(); |
225 | | |
226 |
1
1. engineDigest : replaced return value with null for com/jsql/util/bruter/DigestMD4::engineDigest → KILLED |
return result; |
227 | } | |
228 | ||
229 | ||
230 | // own methods | |
231 | //........................................................................... | |
232 | ||
233 | /** | |
234 | * MD4 basic transformation. | |
235 | * <p> | |
236 | * Transforms context based on 512 bits from input block starting | |
237 | * from the offset'th byte. | |
238 | * | |
239 | * @param block input sub-array. | |
240 | * @param offset starting position of sub-array. | |
241 | */ | |
242 | private void transform(byte[] block, int offset) { | |
243 | ||
244 | // encodes 64 bytes from input block into an array of 16 32-bit | |
245 | // entities. Use A as a temp var. | |
246 |
2
1. transform : negated conditional → KILLED 2. transform : changed conditional boundary → KILLED |
for (int i = 0; i < 16; i++) { |
247 |
14
1. transform : Changed increment from 1 to -1 → KILLED 2. transform : Replaced bitwise AND with OR → KILLED 3. transform : Replaced bitwise OR with AND → KILLED 4. transform : Replaced Shift Left with Shift Right → KILLED 5. transform : Replaced Shift Left with Shift Right → KILLED 6. transform : Replaced bitwise OR with AND → KILLED 7. transform : Changed increment from 1 to -1 → KILLED 8. transform : Changed increment from 1 to -1 → KILLED 9. transform : Replaced bitwise AND with OR → KILLED 10. transform : Replaced bitwise AND with OR → KILLED 11. transform : Replaced Shift Left with Shift Right → KILLED 12. transform : Changed increment from 1 to -1 → KILLED 13. transform : Replaced bitwise AND with OR → KILLED 14. transform : Replaced bitwise OR with AND → KILLED |
this.X[i] = |
248 | (block[offset++] & 0xFF) | |
249 | | (block[offset++] & 0xFF) << 8 | |
250 | | (block[offset++] & 0xFF) << 16 | |
251 | | (block[offset++] & 0xFF) << 24; | |
252 | } | |
253 | ||
254 | int A = this.context[0]; | |
255 | int B = this.context[1]; | |
256 | int C = this.context[2]; | |
257 | int D = this.context[3]; | |
258 | ||
259 | A = this.FF(A, B, C, D, this.X[ 0], 3); | |
260 | D = this.FF(D, A, B, C, this.X[ 1], 7); | |
261 | C = this.FF(C, D, A, B, this.X[ 2], 11); | |
262 | B = this.FF(B, C, D, A, this.X[ 3], 19); | |
263 | A = this.FF(A, B, C, D, this.X[ 4], 3); | |
264 | D = this.FF(D, A, B, C, this.X[ 5], 7); | |
265 | C = this.FF(C, D, A, B, this.X[ 6], 11); | |
266 | B = this.FF(B, C, D, A, this.X[ 7], 19); | |
267 | A = this.FF(A, B, C, D, this.X[ 8], 3); | |
268 | D = this.FF(D, A, B, C, this.X[ 9], 7); | |
269 | C = this.FF(C, D, A, B, this.X[10], 11); | |
270 | B = this.FF(B, C, D, A, this.X[11], 19); | |
271 | A = this.FF(A, B, C, D, this.X[12], 3); | |
272 | D = this.FF(D, A, B, C, this.X[13], 7); | |
273 | C = this.FF(C, D, A, B, this.X[14], 11); | |
274 | B = this.FF(B, C, D, A, this.X[15], 19); | |
275 | ||
276 | A = this.GG(A, B, C, D, this.X[ 0], 3); | |
277 | D = this.GG(D, A, B, C, this.X[ 4], 5); | |
278 | C = this.GG(C, D, A, B, this.X[ 8], 9); | |
279 | B = this.GG(B, C, D, A, this.X[12], 13); | |
280 | A = this.GG(A, B, C, D, this.X[ 1], 3); | |
281 | D = this.GG(D, A, B, C, this.X[ 5], 5); | |
282 | C = this.GG(C, D, A, B, this.X[ 9], 9); | |
283 | B = this.GG(B, C, D, A, this.X[13], 13); | |
284 | A = this.GG(A, B, C, D, this.X[ 2], 3); | |
285 | D = this.GG(D, A, B, C, this.X[ 6], 5); | |
286 | C = this.GG(C, D, A, B, this.X[10], 9); | |
287 | B = this.GG(B, C, D, A, this.X[14], 13); | |
288 | A = this.GG(A, B, C, D, this.X[ 3], 3); | |
289 | D = this.GG(D, A, B, C, this.X[ 7], 5); | |
290 | C = this.GG(C, D, A, B, this.X[11], 9); | |
291 | B = this.GG(B, C, D, A, this.X[15], 13); | |
292 | ||
293 | A = this.HH(A, B, C, D, this.X[ 0], 3); | |
294 | D = this.HH(D, A, B, C, this.X[ 8], 9); | |
295 | C = this.HH(C, D, A, B, this.X[ 4], 11); | |
296 | B = this.HH(B, C, D, A, this.X[12], 15); | |
297 | A = this.HH(A, B, C, D, this.X[ 2], 3); | |
298 | D = this.HH(D, A, B, C, this.X[10], 9); | |
299 | C = this.HH(C, D, A, B, this.X[ 6], 11); | |
300 | B = this.HH(B, C, D, A, this.X[14], 15); | |
301 | A = this.HH(A, B, C, D, this.X[ 1], 3); | |
302 | D = this.HH(D, A, B, C, this.X[ 9], 9); | |
303 | C = this.HH(C, D, A, B, this.X[ 5], 11); | |
304 | B = this.HH(B, C, D, A, this.X[13], 15); | |
305 | A = this.HH(A, B, C, D, this.X[ 3], 3); | |
306 | D = this.HH(D, A, B, C, this.X[11], 9); | |
307 | C = this.HH(C, D, A, B, this.X[ 7], 11); | |
308 | B = this.HH(B, C, D, A, this.X[15], 15); | |
309 | ||
310 |
1
1. transform : Replaced integer addition with subtraction → KILLED |
this.context[0] += A; |
311 |
1
1. transform : Replaced integer addition with subtraction → KILLED |
this.context[1] += B; |
312 |
1
1. transform : Replaced integer addition with subtraction → KILLED |
this.context[2] += C; |
313 |
1
1. transform : Replaced integer addition with subtraction → KILLED |
this.context[3] += D; |
314 | } | |
315 | ||
316 | // The basic MD4 atomic functions. | |
317 | ||
318 | private int FF(int a, int b, int c, int d, int x, int s) { | |
319 | | |
320 |
6
1. FF : Replaced bitwise AND with OR → KILLED 2. FF : Replaced integer addition with subtraction → KILLED 3. FF : Replaced integer addition with subtraction → KILLED 4. FF : Replaced bitwise OR with AND → KILLED 5. FF : Replaced bitwise AND with OR → KILLED 6. FF : Replaced XOR with AND → KILLED |
int t = a + ((b & c) | (~b & d)) + x; |
321 |
5
1. FF : replaced int return with 0 for com/jsql/util/bruter/DigestMD4::FF → KILLED 2. FF : Replaced Shift Left with Shift Right → KILLED 3. FF : Replaced bitwise OR with AND → KILLED 4. FF : Replaced Unsigned Shift Right with Shift Left → KILLED 5. FF : Replaced integer subtraction with addition → KILLED |
return t << s | t >>> (32 - s); |
322 | } | |
323 | | |
324 | private int GG(int a, int b, int c, int d, int x, int s) { | |
325 | | |
326 |
7
1. GG : Replaced integer addition with subtraction → KILLED 2. GG : Replaced bitwise AND with OR → KILLED 3. GG : Replaced bitwise OR with AND → KILLED 4. GG : Replaced integer addition with subtraction → KILLED 5. GG : Replaced integer addition with subtraction → KILLED 6. GG : Replaced bitwise OR with AND → KILLED 7. GG : Replaced bitwise AND with OR → KILLED |
int t = a + ((b & (c | d)) | (c & d)) + x + 0x5A827999; |
327 |
5
1. GG : Replaced Shift Left with Shift Right → KILLED 2. GG : Replaced bitwise OR with AND → KILLED 3. GG : Replaced Unsigned Shift Right with Shift Left → KILLED 4. GG : Replaced integer subtraction with addition → KILLED 5. GG : replaced int return with 0 for com/jsql/util/bruter/DigestMD4::GG → KILLED |
return t << s | t >>> (32 - s); |
328 | } | |
329 | | |
330 | private int HH(int a, int b, int c, int d, int x, int s) { | |
331 | | |
332 |
5
1. HH : Replaced integer addition with subtraction → KILLED 2. HH : Replaced integer addition with subtraction → KILLED 3. HH : Replaced XOR with AND → KILLED 4. HH : Replaced XOR with AND → KILLED 5. HH : Replaced integer addition with subtraction → KILLED |
int t = a + (b ^ c ^ d) + x + 0x6ED9EBA1; |
333 |
5
1. HH : Replaced Shift Left with Shift Right → KILLED 2. HH : Replaced integer subtraction with addition → KILLED 3. HH : Replaced Unsigned Shift Right with Shift Left → KILLED 4. HH : replaced int return with 0 for com/jsql/util/bruter/DigestMD4::HH → KILLED 5. HH : Replaced bitwise OR with AND → KILLED |
return t << s | t >>> (32 - s); |
334 | } | |
335 | } | |
Mutations | ||
74 |
1.1 |
|
99 |
1.1 |
|
121 |
1.1 2.2 |
|
133 |
1.1 |
|
134 |
1.1 |
|
137 |
1.1 |
|
138 |
1.1 |
|
158 |
1.1 2.2 3.3 4.4 5.5 6.6 7.7 |
|
163 |
1.1 |
|
164 |
1.1 |
|
165 |
1.1 |
|
168 |
1.1 2.2 |
|
170 |
1.1 |
|
172 |
1.1 |
|
174 |
1.1 2.2 3.3 4.4 |
|
175 |
1.1 2.2 |
|
182 |
1.1 2.2 |
|
183 |
1.1 2.2 3.3 |
|
198 |
1.1 |
|
199 |
1.1 2.2 3.3 4.4 |
|
202 |
1.1 |
|
208 |
1.1 2.2 |
|
209 |
1.1 2.2 3.3 4.4 |
|
212 |
1.1 |
|
217 |
1.1 2.2 |
|
218 |
1.1 2.2 |
|
219 |
1.1 2.2 3.3 4.4 |
|
224 |
1.1 |
|
226 |
1.1 |
|
246 |
1.1 2.2 |
|
247 |
1.1 2.2 3.3 4.4 5.5 6.6 7.7 8.8 9.9 10.10 11.11 12.12 13.13 14.14 |
|
310 |
1.1 |
|
311 |
1.1 |
|
312 |
1.1 |
|
313 |
1.1 |
|
320 |
1.1 2.2 3.3 4.4 5.5 6.6 |
|
321 |
1.1 2.2 3.3 4.4 5.5 |
|
326 |
1.1 2.2 3.3 4.4 5.5 6.6 7.7 |
|
327 |
1.1 2.2 3.3 4.4 5.5 |
|
332 |
1.1 2.2 3.3 4.4 5.5 |
|
333 |
1.1 2.2 3.3 4.4 5.5 |