1 /*
2  * This software is Copyright (c) 2012 Sayantan Datta <std2048 at gmail dot com>
3  * and it is hereby released to the general public under the following terms:
4  * Redistribution and use in source and binary forms, with or without modification, are permitted.
5  * Based on Solar Designer implementation of DES_fmt.c in jtr-v1.7.9
6  */
7 
8 #ifdef HAVE_OPENCL
9 
10 #if FMT_EXTERNS_H
11 extern struct fmt_main fmt_opencl_DES;
12 #elif FMT_REGISTERS_H
13 john_register_one(&fmt_opencl_DES);
14 #else
15 
16 #include <string.h>
17 
18 #include "arch.h"
19 #include "common.h"
20 #include "formats.h"
21 #include "config.h"
22 #include "opencl_DES_bs.h"
23 #include "opencl_DES_hst_dev_shared.h"
24 
25 #define FORMAT_NAME			"traditional crypt(3)"
26 
27 #define BENCHMARK_COMMENT		""
28 #define BENCHMARK_LENGTH		7
29 
30 #define CIPHERTEXT_LENGTH_1		13
31 #define CIPHERTEXT_LENGTH_2		24
32 
33 static struct fmt_tests tests[] = {
34 	{"CCNf8Sbh3HDfQ", "U*U*U*U*"},
35 	{"CCX.K.MFy4Ois", "U*U***U"},
36 	{"CC4rMpbg9AMZ.", "U*U***U*"},
37 	{"XXxzOu6maQKqQ", "*U*U*U*U"},
38 	{"SDbsugeBiC58A", ""},
39 	{"..X8NBuQ4l6uQ", ""},
40 	{NULL}
41 };
42 
43 #define ALGORITHM_NAME			DES_BS_OPENCL_ALGORITHM_NAME
44 
45 #define BINARY_SIZE			(2 * sizeof(WORD))
46 #define SALT_SIZE			sizeof(WORD)
47 
48 #define USE_FULL_UNROLL 		(amd_gcn(device_info[gpu_id]) || nvidia_sm_5x(device_info[gpu_id]))
49 #define USE_BASIC_KERNEL		(cpu(device_info[gpu_id]) || platform_apple(platform_id))
50 
51 void (*opencl_DES_bs_init_global_variables)(void);
52 void (*opencl_DES_bs_select_device)(struct fmt_main *);
53 
54 static  unsigned char DES_IP[64] = {
55 	57, 49, 41, 33, 25, 17, 9, 1,
56 	59, 51, 43, 35, 27, 19, 11, 3,
57 	61, 53, 45, 37, 29, 21, 13, 5,
58 	63, 55, 47, 39, 31, 23, 15, 7,
59 	56, 48, 40, 32, 24, 16, 8, 0,
60 	58, 50, 42, 34, 26, 18, 10, 2,
61 	60, 52, 44, 36, 28, 20, 12, 4,
62 	62, 54, 46, 38, 30, 22, 14, 6
63 };
64 
65 static unsigned char DES_atoi64[0x100] = {
66 	18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33,
67 	34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49,
68 	50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 0, 1,
69 	2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 5, 6, 7, 8, 9, 10,
70 	11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26,
71 	27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 32, 33, 34, 35, 36,
72 	37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52,
73 	53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 0, 1, 2, 3, 4,
74 	5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20,
75 	21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36,
76 	37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52,
77 	53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 0, 1, 2, 3, 4,
78 	5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20,
79 	21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36,
80 	37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52,
81 	53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 0, 1, 2, 3, 4
82 };
83 
init(struct fmt_main * pFmt)84 static void init(struct fmt_main *pFmt)
85 {
86 	opencl_prepare_dev(gpu_id);
87 
88 	if ((USE_BASIC_KERNEL&& !OVERRIDE_AUTO_CONFIG) ||
89 		(OVERRIDE_AUTO_CONFIG && !HARDCODE_SALT && !FULL_UNROLL))
90 		opencl_DES_bs_b_register_functions(pFmt);
91 	else if ((USE_FULL_UNROLL && !OVERRIDE_AUTO_CONFIG) ||
92 		(OVERRIDE_AUTO_CONFIG && HARDCODE_SALT && FULL_UNROLL))
93 		opencl_DES_bs_f_register_functions(pFmt);
94 	else
95 		opencl_DES_bs_h_register_functions(pFmt);
96 
97 	// Check if specific LWS/GWS was requested
98 	opencl_get_user_preferences(FORMAT_LABEL);
99 
100 	opencl_DES_bs_init_global_variables();
101 
102 	if (local_work_size & (local_work_size - 1)) {
103 		if (local_work_size < 4) local_work_size = 4;
104 		else if (local_work_size < 8) local_work_size = 8;
105 		else if (local_work_size < 16) local_work_size = 16;
106 		else if (local_work_size < 32) local_work_size = 32;
107 		else local_work_size = 64;
108 	}
109 }
110 
valid(char * ciphertext,struct fmt_main * pFmt)111 static int valid(char *ciphertext, struct fmt_main *pFmt)
112 {
113 	char *pos;
114 
115 	if (!ciphertext[0] || !ciphertext[1]) return 0;
116 
117 	for (pos = &ciphertext[2]; atoi64[ARCH_INDEX(*pos)] != 0x7F; pos++);
118 	if (*pos && *pos != ',') return 0;
119 
120 	if (atoi64[ARCH_INDEX(*(pos - 1))] & 3) return 0;
121 
122 	switch (pos - ciphertext) {
123 	case CIPHERTEXT_LENGTH_1:
124 		return 1;
125 
126 	case CIPHERTEXT_LENGTH_2:
127 		if (atoi64[ARCH_INDEX(ciphertext[12])] & 3) return 0;
128 		return 2;
129 
130 	default:
131 		return 0;
132 	}
133 }
134 
split(char * ciphertext,int index,struct fmt_main * pFmt)135 static char *split(char *ciphertext, int index, struct fmt_main *pFmt)
136 {
137 	static char out[14];
138 
139 	if (index) {
140 		memcpy(out, &ciphertext[2], 2);
141 		memcpy(&out[2], &ciphertext[13], 11);
142 	} else
143 		memcpy(out, ciphertext, 13);
144 
145 	out[13] = 0;
146 	return out;
147 }
148 
do_IP(WORD in[2])149 static WORD *do_IP(WORD in[2])
150 {
151 	static WORD out[2];
152 	int src, dst;
153 
154 	out[0] = out[1] = 0;
155 	for (dst = 0; dst < 64; dst++) {
156 		src = DES_IP[dst ^ 0x20];
157 
158 		if (in[src >> 5] & (1 << (src & 0x1F)))
159 			out[dst >> 5] |= 1 << (dst & 0x1F);
160 	}
161 
162 	return out;
163 }
164 
raw_get_binary(char * ciphertext)165 static WORD *raw_get_binary(char *ciphertext)
166 {
167 	WORD block[3];
168 	WORD mask;
169 	int ofs, chr, src, dst, value;
170 
171 	if (ciphertext[13]) ofs = 9; else ofs = 2;
172 
173 	block[0] = block[1] = 0;
174 	dst = 0;
175 	for (chr = 0; chr < 11; chr++) {
176 		value = DES_atoi64[ARCH_INDEX(ciphertext[chr + ofs])];
177 		mask = 0x20;
178 
179 		for (src = 0; src < 6; src++) {
180 			if (value & mask)
181 				block[dst >> 5] |= 1 << (dst & 0x1F);
182 			mask >>= 1;
183 			dst++;
184 		}
185 	}
186 
187 	return do_IP(block);
188 }
189 
get_binary_raw(WORD * raw,int count)190 static WORD *get_binary_raw(WORD *raw, int count)
191 {
192 	static WORD out[2];
193 
194 /* For odd iteration counts, swap L and R here instead of doing it one
195  * more time in DES_bs_crypt(). */
196 	count &= 1;
197 	out[count] = raw[0];
198 	out[count ^ 1] = raw[1];
199 
200 	return out;
201 }
202 
203 
raw_get_count(char * ciphertext)204 static WORD raw_get_count(char *ciphertext)
205 {
206 	if (ciphertext[13]) return DES_atoi64[ARCH_INDEX(ciphertext[1])] |
207 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[2])] << 6) |
208 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[3])] << 12) |
209 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[4])] << 18);
210 	else return 25;
211 }
212 
get_binary(char * ciphertext)213 static WORD *get_binary(char *ciphertext)
214 {
215 	return get_binary_raw(
216 		raw_get_binary(ciphertext),
217 		raw_get_count(ciphertext));
218 }
219 
raw_get_salt(char * ciphertext)220 static WORD raw_get_salt(char *ciphertext)
221 {
222 	if (ciphertext[13]) return DES_atoi64[ARCH_INDEX(ciphertext[5])] |
223 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[6])] << 6) |
224 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[7])] << 12) |
225 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[8])] << 18);
226 	else return DES_atoi64[ARCH_INDEX(ciphertext[0])] |
227 		((WORD)DES_atoi64[ARCH_INDEX(ciphertext[1])] << 6);
228 }
229 
get_salt(char * ciphertext)230 static void *get_salt(char *ciphertext)
231 {
232 	static WORD out;
233 
234 	out = raw_get_salt(ciphertext);
235 
236 	return &out;
237 }
238 
239 #define get_hash_0 opencl_DES_bs_get_hash_0
240 #define get_hash_1 opencl_DES_bs_get_hash_1
241 #define get_hash_2 opencl_DES_bs_get_hash_2
242 #define get_hash_3 opencl_DES_bs_get_hash_3
243 #define get_hash_4 opencl_DES_bs_get_hash_4
244 #define get_hash_5 opencl_DES_bs_get_hash_5
245 #define get_hash_6 opencl_DES_bs_get_hash_6
246 
salt_hash(void * salt)247 static int salt_hash(void *salt)
248 {
249 	return *(WORD *)salt & (SALT_HASH_SIZE - 1);
250 }
251 
cmp_all(WORD * binary,int count)252 static int cmp_all(WORD *binary, int count)
253 {
254 	return 1;
255 }
256 
257 struct fmt_main fmt_opencl_DES = {
258 	{
259 		FORMAT_LABEL,
260 		FORMAT_NAME,
261 		ALGORITHM_NAME,
262 		BENCHMARK_COMMENT,
263 		BENCHMARK_LENGTH,
264 		0,
265 		PLAINTEXT_LENGTH,
266 		BINARY_SIZE,
267 		sizeof(WORD),
268 		SALT_SIZE,
269 		sizeof(WORD),
270 		MIN_KEYS_PER_CRYPT,
271 		MAX_KEYS_PER_CRYPT,
272 		FMT_CASE | FMT_TRUNC | FMT_BS | FMT_REMOVE | FMT_MASK,
273 		{ NULL },
274 		{ NULL },
275 		tests
276 	}, {
277 		init,
278 		NULL,
279 		NULL,
280 		fmt_default_prepare,
281 		valid,
282 		split,
283 		(void *(*)(char *))
284 
285 			get_binary,
286 
287 		get_salt,
288 		{ NULL },
289 		fmt_default_source,
290 		{
291 			fmt_default_binary_hash_0,
292 			fmt_default_binary_hash_1,
293 			fmt_default_binary_hash_2,
294 			fmt_default_binary_hash_3,
295 			fmt_default_binary_hash_4,
296 			fmt_default_binary_hash_5,
297 			fmt_default_binary_hash_6
298 		},
299 		salt_hash,
300 		NULL,
301 		NULL,
302 		opencl_DES_bs_set_key,
303 		opencl_DES_bs_get_key,
304 		opencl_DES_bs_clear_keys,
305 		NULL,
306 		{
307 			get_hash_0,
308 			get_hash_1,
309 			get_hash_2,
310 			get_hash_3,
311 			get_hash_4,
312 			get_hash_5,
313 			get_hash_6
314 		},
315 
316 		(int (*)(void *, int))cmp_all,
317 
318 		opencl_DES_bs_cmp_one,
319 		opencl_DES_bs_cmp_exact
320 	}
321 };
322 #endif /* plugin stanza */
323 
324 #endif /* HAVE_OPENCL */
325