Develop and Download Open Source Software

Browse Subversion Repository

Contents of /branches/mty-makai/mty.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 25 - (show annotations) (download) (as text)
Sat Mar 17 12:20:48 2007 UTC (17 years ago) by chapuni
Original Path: mty/mty.c
File MIME type: text/x-csrc
File size: 32783 byte(s)
key_inc() にて、 N_STRIDE の変更に弱い部分が1箇所あったので清書。
1 /***********************************************************************
2 *
3 * file: mty.cpp
4 *
5 * ‚Ü‚ A‘Ň‚Ä‰ŽB
6 *
7 * $Id$
8 *
9 */
10
11 #define DEBUG 0
12 #define USE_DT 1
13
14 #ifndef DEBUG
15 #define NDEBUG
16 #endif
17
18 #include <assert.h>
19 #include <ctype.h>
20 #include <errno.h>
21 #include <malloc.h>
22 #include <limits.h>
23 #include <stdarg.h>
24 #include <stddef.h>
25 #include <stdio.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <time.h>
29
30 #ifdef __GNUC__
31
32 #include <stdint.h>
33 #define ALIGN_PREFIX(n)
34 #define ALIGN_SUFFIX(n) __attribute__ ((aligned(n)))
35 #ifdef __SSE__
36 typedef unsigned DQWORD_T __attribute__ ((mode(V4SI)));
37 #endif
38
39 #else
40
41 #include <xmmintrin.h>
42 #define ALIGN_PREFIX(n) __declspec(align(16))
43 #define ALIGN_SUFFIX(n)
44
45 /* inttypes.h */
46 typedef __int8 int8_t;
47 typedef __int32 int32_t;
48 typedef unsigned __int32 uint32_t;
49 typedef unsigned __int64 uint64_t;
50
51 typedef __m128 DQWORD_T;
52
53 #endif
54
55 #if defined(WIN32)
56
57 #include <windows.h>
58 #include <sys/timeb.h>
59
60 #elif defined(__GNUC__)
61
62 #include <sys/mman.h>
63 #include <sys/time.h>
64
65 #endif
66
67 #include "crypt64.h"
68 #include "dt4.h"
69
70 #if defined(USE_MMX)
71
72 #define N_STRIDE 6
73 typedef uint64_t WS_T;
74 typedef uint32_t ALU_T;
75
76 #define CRYPT64_CLOBBER /* "%ecx", "%edx", */
77
78 #elif defined(USE_64) /* 64-bit ALU */
79
80 #define N_STRIDE 6
81 typedef uint64_t WS_T;
82 typedef uint64_t ALU_T;
83
84 #define CRYPT64_CLOBBER /* "%rcx", "%rdx",*/ "%r8", "%r9",
85
86 #elif defined(USE_64_XMM)
87
88 #define N_STRIDE 7
89 typedef DQWORD_T WS_T;
90 typedef uint64_t ALU_T;
91
92 #define CRYPT64_CLOBBER /* "%rcx", "%rdx",*/
93
94 #else /* XMM */
95
96 #define N_STRIDE 7
97 typedef DQWORD_T WS_T;
98 typedef uint32_t ALU_T;
99
100 #define CRYPT64_CLOBBER /* "%ecx", "%edx", */
101
102 #endif
103
104 #define N_I (sizeof(WS_T) / sizeof(uint32_t))
105 #define N_ALU (sizeof(WS_T) / sizeof(ALU_T))
106 #define ALU_BITS (CHAR_BIT * sizeof(ALU_T))
107
108 /* ŒŽ“]’u PC1 */
109 static int const tr_pc1[8][7] =
110 {
111 { 8, 16, 24, 56, 52, 44, 36},
112 { 7, 15, 23, 55, 51, 43, 35},
113 { 6, 14, 22, 54, 50, 42, 34},
114 { 5, 13, 21, 53, 49, 41, 33},
115 { 4, 12, 20, 28, 48, 40, 32},
116 { 3, 11, 19, 27, 47, 39, 31},
117 { 2, 10, 18, 26, 46, 38, 30},
118 { 1, 9, 17, 25, 45, 37, 29},
119 };
120
121 /* LRĹI“]’u */
122 static int const tr_fp[64 + 2] =
123 {
124 39, 7, 47, 15, 55, 23, 63, 31,
125 38, 6, 46, 14, 54, 22, 62, 30,
126 37, 5, 45, 13, 53, 21, 61, 29,
127 36, 4, 44, 12, 52, 20, 60, 28,
128 35, 3, 43, 11, 51, 19, 59, 27,
129 34, 2, 42, 10, 50, 18, 58, 26,
130 33, 1, 41, 9, 49, 17, 57, 25,
131 32, 0, 40, 8, 48, 16, 56, 24,
132 64, 64,
133 };
134
135 /* ŒŽƒVƒtƒgƒXƒPƒWƒ…[ƒ‹
136 KEY::k[2] ‚đćґň‚É—p‚˘‚ÄŽć‚čo‚ľ‚ĚŠČ‘f‰ť‚đ}‚é */
137 static int ks_ls[] =
138 {
139 1, 1, 2, -1,
140 2, -1, 2, -1,
141 2, -1, 2, -1,
142 2, -1, 1, 2,
143 -1, 2, -1, 2,
144 -1, 2, -1, 2,
145 -1, 2, -1, 1 - 28,
146 };
147
148 /* 1ƒrƒbƒg•Ş */
149 typedef union SLICE
150 {
151 uint32_t i[N_I]; /* 32-bit initializer */
152 ALU_T a[N_ALU]; /* C ‚Ĺˆľ‚˘‚₡‚˘ƒTƒCƒY */
153 WS_T w; /* ƒGƒ“ƒR[ƒh‚Ĺˆľ‚¤ƒTƒCƒY */
154 } SLICE;
155
156 /* crypt64() ‚Ş‹ň‚¤ƒpƒ‰ƒ[ƒ^ */
157 struct PARAM
158 {
159 SLICE lr[2][32];
160 SLICE t[32];
161 SLICE hit[10][64];
162 SLICE hiti[10][26];
163 };
164
165 /* ŒŽ‚ÍLR ‚ƁA‚ť‚ĚƒRƒs[‚Ş•K—v
166 KEY::k[0] LR
167 KEY::k[1] LR‚ĚƒRƒs[(č—]‚đČ‚­‚˝‚ß)
168 KEY::k[2][0][i].a[0] ŽŸŒŽ‚Ö‚Ě‘•Ş */
169 struct KEY
170 {
171 SLICE k[2][2][28];
172 SLICE ks[28];
173 };
174
175 /* ŠżŽšƒNƒ‰ƒX•\ */
176 unsigned char cp932[0x10000] = {
177 #include "cp932.inc"
178 };
179
180 /* ŒŽ•śŽš—ń */
181 unsigned char key[8 + 8];
182 unsigned char okey[8 + 8];
183
184 /* ŒŽƒNƒ‰ƒX */
185 struct
186 {
187 unsigned cls;
188 unsigned map[256];
189 } kcls[8 + 8];
190
191 #define KCLS_AN 1
192 #define KCLS_KA 2
193 #define KCLS_K1 4
194 #define KCLS_DT0 64
195 #define KCLS_DT1 128
196 #define KCLS_K2 256
197
198 #if USE_DT
199 /* ŒŽƒLƒ—pŽŤ‘ƒCƒ“ƒfƒNƒX */
200 struct DT *kd[8 + 8];
201
202 /* ŽŤ‘ƒCƒ“ƒfƒNƒX */
203 struct DT *dtidx[0x100 + 1];
204 #endif
205
206 /* Žw’肳‚ę‚˝ƒNƒ‰ƒX‚Ć“ü‚Á‚Ä‚˘‚éƒL[‚Š‚çAclassify ‚đs‚¤ */
207 void
208 key_make_map(int n)
209 {
210 int i, j;
211 unsigned c = kcls[n].map[key[n]];
212
213 if (3 <= n && n < 7 && kd[n - 3])
214 {
215 /* ŽŤ‘‚ĚƒPƒc‚Ě•śŽšBŒă‚ë‚Ƀiƒjƒ„ƒ‰ƒLƒƒƒ‰ƒNƒ^‚Ş—ˆ‚é */
216 c = kd[n - 3]->c[0];
217 if ((0x81 <= c && c <= 0x9F)
218 || (0xE0 <= c && c <= 0xFC))
219 c = KCLS_K2;
220 else
221 c = (cp932[256 * key[n]]
222 | cp932[256 * (key[n] ^ 0x80)]);
223 #if DEBUG>=1
224 printf("*n=%d, key=%02X, cls=%04X\n",
225 n,
226 key[n],
227 c);
228 #endif
229 }
230 else if (2 <= n && n < 6 && kd[n - 2])
231 {
232 return;
233 }
234 else if (1 <= n && n < 5 && kd[n - 1])
235 {
236 return;
237 }
238 else if (1 <= n && n < 5 && !kd[n - 1]
239 //&& (c & KCLS_K2)
240 && (c & KCLS_DT1))
241 {
242 /* ŠżŽš2•śŽš‚đE‚Á‚Ä‚˘‚Ť‚܂ */
243 #if DEBUG>=1
244 printf("(%d)%02X %02X(%02X:%02X:%02X:%02X)\n",
245 n, key[n - 1], key[n],
246 cp932[(256 * key[n - 1] + key[n])],
247 cp932[(256 * key[n - 1] + key[n]) ^ 0x0080],
248 cp932[(256 * key[n - 1] + key[n]) ^ 0x8000],
249 cp932[(256 * key[n - 1] + key[n]) ^ 0x8080]);
250 #endif
251 if (n != 1 && n != 2
252 && (cp932[(256 * key[n - 1] + key[n]) ^ 0x0080] & KCLS_DT1))
253 key[n] ^= 0x80;
254 else if (n != 2 && n != 3
255 && (cp932[(256 * key[n - 1] + key[n]) ^ 0x8000] & KCLS_DT1))
256 key[n - 1] ^= 0x80;
257 else if (n > 3 && (cp932[(256 * key[n - 1] + key[n]) ^ 0x8080] & KCLS_DT1))
258 key[n - 1] ^= 0x80, key[n] ^= 0x80;
259 if (cp932[256 * key[n - 1] + key[n]] & KCLS_DT1)
260 {
261 for (kd[n - 1] = dtidx[key[n - 1]];
262 kd[n - 1]->c[1] != key[n];
263 kd[n - 1]++)
264 assert(kd[n - 1]->c[0] == key[n - 1]);
265 #if DEBUG>=1
266 printf("(%02X%02X:%02X%02X)%c%c%c%c\n",
267 kd[n - 1]->c[0],
268 kd[n - 1]->c[1],
269 kd[n - 1]->c[2],
270 kd[n - 1]->c[3],
271 kd[n - 1]->c[0],
272 kd[n - 1]->c[1],
273 kd[n - 1]->c[2],
274 kd[n - 1]->c[3]);
275 #endif
276 return;
277 }
278 }
279 else if (n < 4 && (c & KCLS_DT0) && kd[n] == NULL)
280 {
281 /* ƒJƒ^ƒJƒi–„‚ߍž‚Ý‚˘‚Ť‚Ü‚ˇ */
282 assert(kd[n] == NULL);
283 #if DEBUG>=1
284 printf("n=%d, key=%02X\n", n, key[n]);
285 #endif
286 kd[n] = dtidx[key[n]];
287 if (!kd[n]
288 && !(n == 1 || n == 2)
289 && dtidx[key[n] ^ 0x80])
290 {
291 key[n] ^= 0x80;
292 kd[n] = dtidx[key[n]];
293 }
294 if (kd[n])
295 return;
296 }
297 else
298 {
299 kd[n] = NULL;
300 }
301
302 /* ĹŒă‚Ě•”•Ş‚Í class map ‚đśŹ‚ˇ‚é•K—vƒiƒV */
303 if (n >= 6)
304 return;
305
306 for (i = 0; i < 256; i++)
307 {
308 unsigned bm = 0;
309 #if 1
310 if (c & KCLS_K1)
311 {
312 if (cp932[256 * key[n] + i] & KCLS_K1)
313 bm |= KCLS_K2 | (cp932[256 * key[n] + i] & KCLS_DT1);
314 if (cp932[256 * (key[n] ^ 0x80) + i] & KCLS_K1)
315 bm |= KCLS_K2 | (cp932[256 * (key[n] ^ 0x80) + i] & KCLS_DT1);
316 #if 0
317 bm |= ((cp932[256 * key[n] + i] & KCLS_K1)
318 || (cp932[256 * (key[n] ^ 0x80) + i] & KCLS_K1)
319 ? KCLS_K2 : 0);
320 #endif
321 }
322 if (c & (KCLS_AN | KCLS_KA | KCLS_K2))
323 for (j = 0; j < 256; j++)
324 {
325 bm |= cp932[256 * i + j] & (KCLS_AN | KCLS_KA | KCLS_K1
326 | KCLS_DT0);
327 #if 0
328 if (j >= 127 && !(n == 0 || n == 1))
329 break;
330 #endif
331 }
332 kcls[n + 1].map[i] = bm;
333 #endif
334 if (i >= 128 && !(n == 0 || n == 1))
335 kcls[n + 1].map[i - 128] |= kcls[n + 1].map[i];
336 }
337
338 if (n < 6)
339 kcls[n + 1].map[0x00] = kcls[n + 1].map[0x80] = 0;
340 if (n == 6)
341 kcls[7].map[0x00] |= KCLS_AN;
342 }
343
344 unsigned
345 dt_get(int kdn,
346 int xn,
347 int n,
348 int ch)
349 {
350 int i;
351 #if DEBUG>=1
352 printf("*dt_get(%d)%c%c%c%c(%02X%02X:%02X%02X)->ch=%d",
353 n,
354 kd[kdn]->c[0], kd[kdn]->c[1], kd[kdn]->c[2], kd[kdn]->c[3],
355 kd[kdn]->c[0], kd[kdn]->c[1], kd[kdn]->c[2], kd[kdn]->c[3],
356 ch);
357 #endif
358 /* ‚Ü‚¸‚͐”‚Ś‚é */
359 for (i = 0;
360 kd[kdn][i].c[xn] == kd[kdn]->c[xn];
361 i++)
362 ;
363 assert(i > 0);
364 kd[kdn] += ch % i;
365 #if DEBUG>=1
366 printf("/%d\n dt_get: %c%c%c%c(%02X%02X:%02X%02X)->ch=%d\n",
367 i,
368 kd[kdn]->c[0], kd[kdn]->c[1], kd[kdn]->c[2], kd[kdn]->c[3],
369 kd[kdn]->c[0], kd[kdn]->c[1], kd[kdn]->c[2], kd[kdn]->c[3],
370 ch);
371 #endif
372 return kd[kdn]->c[n];
373 }
374
375 /* ƒ}ƒbƒv‚Š‚ç•śŽš‚đE‚Á‚ăZƒbƒg */
376 unsigned
377 key_set(int n, unsigned ch)
378 {
379 int cnt = 0, i;
380
381 if (3 <= n && n < 7 && kd[n - 3])
382 {
383 return dt_get(n - 3, 2, 3, ch);
384 return kd[n - 3]->c[3];
385 }
386 else if (2 <= n && n < 6 && kd[n - 2])
387 {
388 return dt_get(n - 2, 1, 2, ch);
389 return kd[n - 2]->c[2];
390 }
391 else if (1 <= n && n < 5 && kd[n - 1])
392 {
393 return dt_get(n - 1, 0, 1, ch);
394 return kd[n - 1]->c[1];
395 }
396
397 #if DEBUG>=3
398 if (cnt == 0)
399 {
400 printf("n=%d, ch=%d, (n-1)=%02X\n", n, ch, key[n - 1]);
401 int j;
402 for (i = 0; i < 16; i++)
403 {
404 printf("map[0x%02X] =", 16 * i);
405 for (j = 0; j < 16; j++)
406 printf(" %03X", kcls[n].map[16 * i + j]);
407 printf("\n");
408 }
409 }
410 #endif
411 for (i = 0; i < 256; i++)
412 {
413 if (kcls[n].map[i])
414 {
415 if (ch-- == 0)
416 return i;
417 cnt++;
418 }
419 if (n != 1 && n != 2 && i >= 127)
420 break;
421 }
422 /* ŒŠ‚Â‚Š‚ç‚ȂЂÁ‚˝‚Ě‚Ĺ‚ŕ‚˘‚Á‚Ř‚ń */
423 assert(cnt > 0);
424 ch %= cnt;
425 for (i = 0; i < 256; i++)
426 if (kcls[n].map[i])
427 {
428 if (ch-- == 0)
429 return i;
430 }
431 assert(!"not matched");
432 return 0;
433 }
434
435 /* bitwise key ‚đƒZƒbƒg */
436 static
437 void
438 key_set64(struct KEY *key64,
439 int n,
440 unsigned k,
441 unsigned vk,
442 unsigned sk)
443 {
444 int i, j;
445 if (!((vk | sk) & 0x7F))
446 return;
447
448 for (i = 0; i < 7; i++)
449 {
450 if (n == 7 && i < N_STRIDE) continue;
451 if (sk & (1 << i))
452 {
453 /* ƒZƒbƒg */
454 int o = tr_pc1[n][6 - i] - 1;
455 if (o < 28)
456 {
457 assert(o >= 0);
458 for (j = 0; j < N_ALU; j++)
459 key64->k[0][0][o].a[j]
460 = key64->k[0][1][o].a[j]
461 = -!!(k & (1 << i));
462 }
463 else
464 {
465 assert(o >= 28);
466 assert(o < 56);
467 for (j = 0; j < N_ALU; j++)
468 key64->k[1][0][o - 28].a[j]
469 = key64->k[1][1][o - 28].a[j]
470 = -!!(k & (1 << i));
471 }
472 }
473 else if (vk & (1 << i))
474 {
475 /* ”˝“] */
476 int o = tr_pc1[n][6 - i] - 1;
477 if (o < 28)
478 {
479 assert(o >= 0);
480 for (j = 0; j < N_ALU; j++)
481 key64->k[0][0][o].a[j]
482 = key64->k[0][1][o].a[j]
483 = ~key64->k[0][0][o].a[j];
484 }
485 else
486 {
487 assert(o >= 28);
488 assert(o < 56);
489 for (j = 0; j < N_ALU; j++)
490 key64->k[1][0][o - 28].a[j]
491 = key64->k[1][1][o - 28].a[j]
492 = ~key64->k[1][0][o - 28].a[j];
493 }
494 }
495 }
496 }
497
498 /* Žw’肳‚ę‚˝ƒNƒ‰ƒX‚ĚŠJŽn’l‚ÉƒŠƒZƒbƒg
499 ’ź‘O‚Ě•śŽš‚ĚƒNƒ‰ƒX‚É”›‚ç‚ę‚é */
500 int
501 key_reset(int n)
502 {
503 if (n >= 8)
504 return 1;
505 if (n == 7)
506 {
507 key[7] = 0;
508 return 1;
509 }
510
511 /* 0-2 •śŽš–ڂ̓‰ƒ“ƒ_ƒ€‚ÉŒˆ‚ß‚é
512 3 •śŽš–ÚˆČ~‚͏‰Šú’l‚É */
513 if (n >= 3)
514 key[n] = key_set(n, 0);
515 else
516 key[n] = key_set(n, rand());
517
518 #if DEBUG>=3
519 printf("key[%d]=%02X ncls=%04X\n", n, key[n], kcls[n].map[key[n]]);
520 #endif
521
522 /* ƒZƒbƒg‚ł‚ę‚˝•śŽš‚đŒł‚ÉAŽŸƒLƒƒƒ‰‚Ě•śŽšƒNƒ‰ƒX‚đŒˆ‚ß‚é */
523 key_make_map(n);
524
525 return key_reset(n + 1);
526 }
527
528 /* Žw’肳‚ę‚˝ŒŽ‹óŠÔ‚Ě’†‚ŁAƒL[‚đ‚ЂƂi‚ß‚é
529 ˆŔ‘S‚ɃCƒ“ƒNƒŠƒƒ“ƒg‚Ĺ‚Ť‚˝ę‡ true ‚đ•Ô‚ˇ */
530 static
531 int
532 key_inc(int n)
533 {
534 if (n >= 8)
535 return 0;
536 else if (n == 7)
537 {
538 /* ĹŒă‚ĚƒoƒCƒg */
539 key[7] = (key[7] + (1 << N_STRIDE)) & 0x7F;
540 if (key[7]) return 1;
541 else return 0;
542 }
543 else if (key_inc(n + 1)
544 /*
545 && key_inc(n + 1)
546 && key_inc(n + 1)
547 && key_inc(n + 1)*/
548 )
549 return 1;
550
551 /* Salt ‚̓Cƒ“ƒNƒŠƒƒ“ƒg‚ľ‚Č‚˘–ń‘Ђɂˇ‚é */
552 if (n == 1 || n == 2)
553 return 1;
554
555 #if DEBUG>=3
556 printf("key_inc(n=%d,ck=%02X)\n", n, key[n]);
557 #endif
558
559 /* ŽŤ‘Œę‚̓Cƒ“ƒNƒŠƒƒ“ƒg‚ľ‚Ä‚˘‚˘–ń‘Ђɂˇ‚é */
560 if (3 <= n && n < 7 && kd[n - 3])
561 {
562 if ((key[n - 3] & 0x7F) == ((kd[n - 3] + 1)->c[0] & 0x7F)
563 && (key[n - 2] & 0x7F) == ((kd[n - 3] + 1)->c[1] & 0x7F)
564 && (key[n - 1] & 0x7F) == ((kd[n - 3] + 1)->c[2] & 0x7F))
565 {
566 memcpy(&key[n - 3], &(++kd[n - 3])->c[0], 4);
567 #if DEBUG>=2
568 printf(">dt_get:%c%c%c%c(%02X%02X:%02X%02X)\n",
569 kd[n - 3]->c[0], kd[n - 3]->c[1], kd[n - 3]->c[2], kd[n - 3]->c[3],
570 kd[n - 3]->c[0], kd[n - 3]->c[1], kd[n - 3]->c[2], kd[n - 3]->c[3]);
571 #endif
572 return 1;
573 }
574 else
575 {
576 return 0;
577 }
578 }
579 else if (2 <= n && n < 6 && kd[n - 2])
580 {
581 if ((key[n - 2] & 0x7F) == ((kd[n - 2] + 1)->c[0] & 0x7F)
582 && (key[n - 1] & 0x7F) == ((kd[n - 2] + 1)->c[1] & 0x7F))
583 {
584 memcpy(&key[n - 2], &(++kd[n - 2])->c[0], 4);
585 #if DEBUG>=2
586 printf(">dt_get:%c%c%c%c(%02X%02X:%02X%02X)\n",
587 kd[n - 2]->c[0], kd[n - 2]->c[1], kd[n - 2]->c[2], kd[n - 2]->c[3],
588 kd[n - 2]->c[0], kd[n - 2]->c[1], kd[n - 2]->c[2], kd[n - 2]->c[3]);
589 #endif
590 return 1;
591 }
592 else
593 {
594 return 0;
595 }
596 if (kd[n - 2]->c[0] == key[n - 2])
597 return 1;
598 else
599 return 0;
600 }
601 else if (1 <= n && n < 5 && kd[n - 1])
602 {
603 unsigned c2 = kd[n - 1]->c[0];
604 if ((0x81 <= c2 && c2 <= 0x9F)
605 || (0xE0 <= c2 && c2 <= 0xFC))
606 {
607 kd[n - 1] = NULL;
608 #if 0
609 if (!(n == 1 && n == 2))
610 key[n] &= 0x7F;
611 if (!(n == 2 && n == 3))
612 key[n - 1] &= 0x7F;
613 #endif
614 key_make_map(n - 1);
615 }
616 else if ((key[n - 1] & 0x7F) == ((kd[n - 1] + 1)->c[0] & 0x7F))
617 {
618 memcpy(&key[n - 1], &(++kd[n - 1])->c[0], 4);
619 #if DEBUG>=2
620 printf(">dt_get:%c%c%c%c(%02X%02X:%02X%02X)\n",
621 kd[n - 1]->c[0], kd[n - 1]->c[1], kd[n - 1]->c[2], kd[n - 1]->c[3],
622 kd[n - 1]->c[0], kd[n - 1]->c[1], kd[n - 1]->c[2], kd[n - 1]->c[3]);
623 #endif
624 return 1;
625 }
626 else
627 {
628 return 0;
629 }
630 #if 0
631 if (kd[n - 1]->c[0] == key[n - 1])
632 return 1;
633 else
634 return 0;
635 #endif
636 }
637 else if (n < 4 && kd[n])
638 {
639 if (0 && kd[n]->c[0] == key[n])
640 return 1;
641 kd[n] = NULL;
642 #if 0
643 if (!(n == 1 || n == 2))
644 key[n] &= 0x7F;
645 #endif
646 }
647
648 /* ŽŔŰ‚É‘‚₾‚Ă݂é */
649 assert(n >= 3);
650 for (;;)
651 {
652 if (n <= 3
653 && !(key[n] & 0x80)
654 && kcls[n].map[key[n] ^ 0x80] & (KCLS_DT0))
655 {
656 /* ”źŠpƒJƒ^ƒJƒi‚Ě1ƒoƒCƒg–Ú */
657 key[n] ^= 0x80;
658 }
659 else
660 {
661 key[n] = (key[n] & 0x7F) + 1;
662 if (key[n] >= 0x80)
663 return 0;
664 }
665
666 if (kcls[n].map[key[n]])
667 {
668 key_make_map(n);
669 key_reset(n + 1);
670 return 1;
671 }
672 }
673 while (++key[n] < 0x80)
674 {
675 if (kcls[n].map[key[n]])
676 {
677 key_make_map(n);
678 key_reset(n + 1);
679 return 1;
680 }
681 }
682 return 0;
683 }
684
685 /* ŒŽ‚đŠŽ‘S‚ÉƒŠƒZƒbƒg‚ˇ‚é
686 Salt‚ŕƒZƒbƒg‚ľ’ꂎ */
687 static
688 void
689 key_init()
690 {
691 int i, j;
692
693 #if USE_DT
694 /* ŽŤ‘‚đAƒCƒ“ƒfƒNƒX‚đě‚č‚Č‚Ş‚çƒ}ƒbƒv‚ɂ͂߂ą‚ń‚ŐŔ‚­
695 ŽŤ‘‚̓R[ƒh‡¸‡‚É•Ŕ‚ń‚Ĺ‚é‚ŕ‚̂Ƃˇ‚é */
696 for (i = 0; i < dtcnt; i++)
697 {
698 unsigned c = dt[i].c[0];
699
700 assert(dt[i].c[0]
701 && dt[i].c[1]
702 && dt[i].c[2]
703 && dt[i].c[3]);
704
705 /* BSD ŽI‚Ĺ‚ľ‚É‚ť‚¤‚Č•śŽš‚ÍŽc”O‚Č‚Ş‚çœŠO */
706 assert((dt[i].c[0] & 0x7F)
707 && (dt[i].c[1] & 0x7F)
708 && (dt[i].c[2] & 0x7F)
709 && (dt[i].c[3] & 0x7F));
710
711 /* ƒCƒ“ƒfƒNƒX */
712 if (!dtidx[c])
713 dtidx[c] = &dt[i];
714
715 if ((0x81 <= c && c <= 0x9F)
716 || (0xE0 <= c && c <= 0xFC))
717 {
718 /* ‘SŠp‚Ȃ̂ŁA2ƒoƒCƒg‚Ť‚Ü‚Á‚˝Žž“_‚Ĺ—§‚Ä‚é */
719 cp932[256 * c + dt[i].c[1]] |= KCLS_DT1;
720 }
721 else if (0xA1 <= c && c <= 0xDF)
722 {
723 /* ”źŠpƒJƒi */
724 for (j = 0; j < 256; j++)
725 cp932[256 * c + j] |= KCLS_DT0;
726 }
727 }
728 /* ƒPƒcA‚ż‚¤‚Š”Ôl */
729 dtidx[0x100] = &dt[i];
730 #endif
731
732 key[8] = 0;
733
734 /* ‰Šúƒ}ƒbƒv‚đ‘g‚Ţ */
735 for (i = 0; i < 256; i++)
736 {
737 unsigned bm = 0;
738 kcls[0].map[i] = 0;
739 for (j = 0; j < 256; j++)
740 bm |= cp932[256 * i + j];
741 kcls[0].map[i] = bm & (KCLS_AN | KCLS_KA | KCLS_K1
742 | KCLS_DT0
743 );
744 if (i >= 128)
745 kcls[0].map[i - 128] |= kcls[0].map[i];
746 }
747
748 key_reset(0);
749 }
750
751 /***************************************************************
752 *
753 * ‰ÂŽ‹•śŽš—ń‚ɕϊˇ
754 * n = 0, flag !=0 ‚ĹŒÄ‚Ô‚ą‚Ć
755 *
756 * ptr ‚ĹŽw‚ł‚ę‚é•śŽš—ń‚́A•ĎŠˇ‚ÉŹŒ÷‚ľ‚˝‚珑‚ŤŠˇ‚Ś‚ç‚ę‚é
757 *
758 * ŹŒ÷‚ľ‚˝‚ç flg, ޏ”s‚ľ‚˝‚ç 0 ‚đ•Ô‚ˇB
759 *
760 */
761
762 unsigned
763 translate(unsigned char *ptr,
764 int n,
765 unsigned flag)
766 {
767 int r;
768 unsigned char buf[32];
769 unsigned s0 = (n == 1 || n == 2 ? 0x00 : 0x80);
770 unsigned s1 = (n == 0 || n == 1 ? 0x00 : 0x80);
771 unsigned c0 = ptr[n] << 8;
772 unsigned c1 = ptr[n + 1];
773 unsigned cs0 = c0 ^ (s0 << 8);
774 unsigned cs1 = c1 ^ s1;
775
776 if (n >= 8)
777 return flag;
778
779 if (n == 7)
780 {
781 int i;
782 /* ĹŒă‚Ě1•śŽš */
783 if (!(ptr[7] & 0x7F))
784 return flag;
785
786 for (i = 0x00; i <= 0x7E; i++)
787 {
788 if (cp932[c0 | i] & KCLS_K1)
789 {
790 ptr[8] = i;
791 return flag;
792 }
793 if (cp932[c0 | (0x80 + i)] & KCLS_K1)
794 {
795 ptr[8] = 0x80 + i;
796 return flag;
797 }
798 }
799
800 ptr[7] ^= 0x80; c0 = ptr[7] << 8;
801 for (i = 0x00; i <= 0x7E; i++)
802 {
803 if (cp932[c0 | i] & KCLS_K1)
804 {
805 ptr[8] = i;
806 return flag;
807 }
808 if (cp932[c0 | (0x80 + i)] & KCLS_K1)
809 {
810 ptr[8] = 0x80 + i;
811 return flag;
812 }
813 }
814 ptr[7] ^= 0x80; c0 = ptr[7] << 8;
815 }
816
817 /* K1 */
818 if (cp932[c0 | c1] & KCLS_K1)
819 {
820 r = translate(ptr, n + 2, flag);
821 if (r)
822 return r;
823 }
824 if (s0
825 && cp932[cs0 | c1] & KCLS_K1)
826 {
827 memcpy(buf, ptr, sizeof(buf));
828 buf[n] ^= s0;
829 r = translate(buf, n + 2, flag);
830 if (r)
831 {
832 memcpy(ptr, buf, sizeof(buf));
833 return r;
834 }
835 }
836 if (s1
837 && cp932[c0 | cs1] & KCLS_K1)
838 {
839 memcpy(buf, ptr, sizeof(buf));
840 buf[n + 1] ^= s1;
841 r = translate(buf, n + 2, flag);
842 if (r)
843 {
844 memcpy(ptr, buf, sizeof(buf));
845 return r;
846 }
847 }
848 if (s0 && s1
849 && cp932[cs0 | cs1] & KCLS_K1)
850 {
851 memcpy(buf, ptr, sizeof(buf));
852 buf[n] ^= s0;
853 buf[n + 1] ^= s1;
854 r = translate(buf, n + 2, flag);
855 if (r)
856 {
857 memcpy(ptr, buf, sizeof(buf));
858 return r;
859 }
860 }
861
862 /* AN */
863 if (cp932[c0] & (KCLS_AN | KCLS_KA))
864 {
865 r = translate(ptr, n + 1, flag);
866 if (r)
867 return r;
868 }
869 if (s0 && cp932[cs0] & (KCLS_AN | KCLS_KA))
870 {
871 memcpy(buf, ptr, sizeof(buf));
872 buf[n] ^= s0;
873 r = translate(buf, n + 1, flag);
874 if (r)
875 {
876 memcpy(ptr, buf, sizeof(buf));
877 return r;
878 }
879 }
880
881 /* KA */
882 /* KG */
883 /* KD */
884 /* AD */
885
886 return 0;
887 }
888
889 /***************************************************************
890 *
891 * Salt ‚ĚƒZƒbƒg
892 * ƒIƒyƒ‰ƒ“ƒh‚ĚƒIƒtƒZƒbƒg‚đ‘‚ŤŠˇ‚ڂĉń‚Á‚Ä‚é‚̂ŒˆÓ
893 *
894 */
895
896 #if N_STRIDE == 6
897 #define C(c,i,j,o) (*(int8_t *)((c) + (loo - crypt64_sta) + los[6 * (i) + (j) + (o)]))
898 #elif N_STRIDE == 7
899 #define C(c,i,j,o) (*(int32_t *)((c) + (loo - crypt64_sta) + los[6 * (i) + (j) + (o)]))
900 #endif
901
902 void
903 set_salt(signed char *code,
904 unsigned char const *k)
905 {
906 int i, j;
907
908 for (i = 0; i < 2; i++)
909 {
910 unsigned s = k[1 + i] & 255;
911 if (s > 'z')
912 s = 0;
913 else if (s >= 'a')
914 s = s - 'a' + 2 + 10 + 26;
915 else if (s >= 'A')
916 s = s - 'A' + 2 + 10;
917 else if (s >= '.')
918 s = s - '.';
919 else
920 s = 0;
921
922 #if DEBUG>=1
923 printf("Salt %d:%3o\n", i, s & 63);
924 #endif
925 for (j = 0; j < 6; j++)
926 {
927 #if DEBUG>=2
928 //printf("Salt %d:%d %+3d:%+3d",
929 printf("Salt %d:%d %08lX:%08lX",
930 i, j,
931 C(code, i, j, 0),
932 C(code, i, j, 24));
933 #endif
934 if (s & (1 << j))
935 {
936 C(code, i, j, 0) = sizeof(WS_T) * (((4 * i + j + 15) & 31) - 16);
937 C(code, i, j, 24) = sizeof(WS_T) * (((4 * i + j - 1) & 31) - 16);
938 }
939 else
940 {
941 C(code, i, j, 0) = sizeof(WS_T) * (((4 * i + j - 1) & 31) - 16);
942 C(code, i, j, 24) = sizeof(WS_T) * (((4 * i + j + 15) & 31) - 16);
943 }
944 C(code, i, j, 12) = sizeof(WS_T) * (((4 * i + j + 7) & 31) - 16);
945 C(code, i, j, 36) = sizeof(WS_T) * (((4 * i + j + 23) & 31) - 16);
946 #if DEBUG>=2
947 //printf(" => %+3d:%+3d\n",
948 printf(" => %08lX:%08lX\n",
949 C(code, i, j, 0),
950 C(code, i, j, 24));
951 #endif
952 }
953 }
954 }
955
956 /***************************************************************
957 *
958 * ƒIƒyƒR[ƒh‚đ“WŠJ
959 *
960 * r EAX, ECX, EDX, EBX
961 * SIB, EBP, ESI, EDI
962 *
963 */
964
965 /* ofs8(i) ‚ŕ‚ľ‚­‚Í ofs32(i) ‚đśŹ */
966 static
967 signed char *
968 disp_rm(signed char *pc,
969 unsigned d,
970 unsigned i,
971 long ofs)
972 {
973 assert(i != 4); /* SP ‚ł͂Ȃ­ SIB ‚ɂȂé */
974 if (-128 <= ofs && ofs <= 127)
975 {
976 /* short ofs
977 01 ddd sss [ofs.b] */
978 pc[0] = (0100
979 | ((d << 3) & 0070)
980 | (i & 0007));
981 pc[1] = ofs;
982 return pc + 2;
983 }
984 else
985 {
986 /* long ofs
987 10 ddd sss [ofs.l] */
988 pc[0] = (0200
989 | ((d << 3) & 0070)
990 | (i & 0007));
991 *(long *)&pc[1] = ofs; /* XXX unaligned */
992 return pc + 5;
993 }
994 }
995
996 #define PTR_T 7 /* DI(LR+16) */
997 #define OFS_T (64 + 32 - 16)
998
999 #ifdef USE_64 /* ALU 64 */
1000
1001 /*
1002 * 0x49 0xF7 11-010-ddd not
1003 * 0x49 op 11-sss-ddd
1004 *
1005 * 0x4C op rm
1006 * 0x4C 0x8B rm load
1007 * 0x4C 0x89 rm store
1008 *
1009 */
1010
1011 #define OP_MOV 0x8B
1012 #define OP_STOR 0x89
1013 #define OP_AND 0x23
1014 #define OP_OR 0x0B
1015 #define OP_XOR 0x33
1016
1017 static
1018 signed char *
1019 reg_op(signed char *pc,
1020 unsigned op,
1021 unsigned d,
1022 unsigned s)
1023 {
1024 pc[0] = 0x4D; /* 49 */
1025 pc[1] = op & 0xFD;
1026 /* 11 ddd sss */
1027 pc[2] = (0300
1028 | ((s << 3) & 0070)
1029 | (d & 0007));
1030 return pc + 3;
1031 }
1032
1033 static
1034 signed char *
1035 reg_mem(signed char *pc,
1036 unsigned op,
1037 unsigned d,
1038 unsigned i,
1039 long ofs)
1040 {
1041 pc[0] = 0x4C;
1042 pc[1] = op;
1043 return disp_rm(pc + 2, d, i, ofs);
1044 }
1045
1046 #else /* MMX or XMM */
1047
1048 #define OP_MOV 0x6F
1049 #define OP_STOR 0x7F
1050 #define OP_AND 0xDB
1051 #define OP_ANDN 0xDF
1052 #define OP_OR 0xEB
1053 #define OP_XOR 0xEF
1054
1055 static
1056 signed char *
1057 reg_op(signed char *pc,
1058 unsigned op,
1059 unsigned d,
1060 unsigned s)
1061 {
1062 #ifndef USE_MMX
1063 *pc++ = 0x66;
1064 #endif
1065 pc[0] = 0x0F;
1066 pc[1] = op;
1067 /* 11 ddd sss */
1068 pc[2] = (0300
1069 | ((d << 3) & 0070)
1070 | (s & 0007));
1071 return pc + 3;
1072 }
1073
1074 static
1075 signed char *
1076 reg_mem(signed char *pc,
1077 unsigned op,
1078 unsigned d,
1079 unsigned i,
1080 int ofs)
1081 {
1082 #ifndef USE_MMX
1083 *pc++ = 0x66;
1084 #endif
1085 pc[0] = 0x0F;
1086 pc[1] = op;
1087 return disp_rm(pc + 2, d, i, ofs);
1088 }
1089
1090 #endif
1091
1092 /***************************************************************
1093 *
1094 * —^‚Ś‚ç‚ę‚˝ŽŽ‚đ‰đÍE–˝—ߐśŹ
1095 *
1096 * ^ ć“ŞŒĹ’č
1097 * $ ––”öŒĹ’č
1098 * ? ”CˆÓ‚Ě1•śŽš
1099 * * ”CˆÓ‚Ě0•śŽšˆČă
1100 * & ‘召‹ć•ĘƒiƒVAƒOƒ‹[ƒv‚ÉŽg‚í‚ę‚˝ę‡Acapitalize
1101 * () ƒOƒ‹[ƒv‰ť
1102 * \s or
1103 * \1 ˆę’v‚ľ‚˝ƒOƒ‹[ƒv(ŽŔ‘Ě)
1104 * $(fn) ƒeƒLƒXƒg‚đ“WŠJ(ƒOƒ‹[ƒv‚̓Nƒ‰ƒX‚Ć‚ľ‚Ĉľ‚í‚ę‚é)
1105 *
1106 * ˆČ‰şAƒNƒ‰ƒX“WŠJ‚Ěƒƒ^ƒLƒƒƒ‰
1107 * [A-Z] •śŽšƒNƒ‰ƒX’č‹` ^ ‚Í”r‘ź
1108 * {} 0•śŽšˆČă
1109 * {n} n•śŽš
1110 * {n,} n•śŽšˆČă
1111 * {,n} n•śŽšˆČ‰ş
1112 * {m,n} m-n•śŽš
1113 *
1114 */
1115
1116 static
1117 int
1118 cv64(int c)
1119 {
1120 if ('.' <= c && c <= '/')
1121 return c - '.';
1122 else if ('0' <= c && c <= '9')
1123 return c - '0' + 2;
1124 else if ('A' <= c && c <= 'Z')
1125 return c - 'A' + 2 + 10;
1126 else if ('a' <= c && c <= 'z')
1127 return c - 'a' + 2 + 10 + 26;
1128 else
1129 return -1;
1130 }
1131
1132 static
1133 int
1134 expr_make(signed char *iptr,
1135 int ofs,
1136 char const *expr,
1137 int len)
1138 {
1139 /* ć“ސ§–ń */
1140 signed char *o_iptr = iptr;
1141 unsigned op = OP_MOV;
1142 int i;
1143
1144 if (expr[0] == '^')
1145 {
1146 if (len == 0 || ofs > 0)
1147 return -1;
1148 expr++;
1149 len--;
1150 }
1151
1152 /* ˆę•śŽš‚“WŠJ */
1153 for (i = 0; i < len; i++)
1154 {
1155 int c = expr[i];
1156
1157 if (c == '$')
1158 {
1159 assert(op != OP_MOV);
1160 if (ofs < 10)
1161 return 0;
1162 else if (ofs > 10)
1163 return -1;
1164 return iptr - o_iptr;
1165 }
1166
1167 if (ofs >= 10)
1168 return -1;
1169
1170 if (c == '[')
1171 {
1172 /* ƒNƒ‰ƒX‚đ‚܂Ƃ߂é */
1173 unsigned oop; /* MOVQ */
1174 int j;
1175 int cs[64];
1176 memset(cs, 0, 64 * sizeof(int));
1177 for (i++; c = expr[i], c != ']'; i++)
1178 {
1179 c = cv64(c);
1180 if (c < 0)
1181 return -1;
1182 if (expr[i + 1] == '-')
1183 {
1184 int ce = cv64(expr[i + 2]);
1185 if (ce < 0)
1186 return -1;
1187 while (c <= ce)
1188 cs[c++]++;
1189 i += 2;
1190 }
1191 else
1192 cs[c]++;
1193 }
1194 assert(c == ']');
1195
1196 /* ƒ}ƒbƒv‚ł‚ę‚˝ƒ‚ƒm‚Š‚ç–˝—ß‚đśŹ‚ˇ‚é */
1197 oop = OP_MOV;
1198 for (j = 0; j < 64; j++)
1199 if (cs[j])
1200 {
1201 if (ofs == 9 && (j & 3))
1202 continue;
1203 iptr = reg_mem(iptr,
1204 oop,
1205 1, /* MM1/R9 */
1206 PTR_T,
1207 sizeof(WS_T) * (OFS_T + (64 * ofs + j)));
1208 oop = OP_OR;
1209 }
1210 if (oop != OP_OR)
1211 {
1212 if (ofs == 9)
1213 return -1;
1214 }
1215 else
1216 {
1217 iptr = reg_op(iptr,
1218 op,
1219 0, /* MM0/R8 */
1220 1); /* MM1/R9 */
1221 op = OP_AND;
1222 }
1223 ofs++;
1224 }
1225 else if (c == '?')
1226 {
1227 ofs++;
1228 }
1229 else if ((c = cv64(c)) >= 0)
1230 {
1231 if (ofs == 9 && (c & 3))
1232 return -1;
1233 iptr = reg_mem(iptr,
1234 op,
1235 0, /* MM0/R8 */
1236 PTR_T,
1237 sizeof(WS_T) * (OFS_T + (64 * ofs + c)));
1238 op = OP_AND;
1239 ofs++;
1240 }
1241 else
1242 return -1;
1243 }
1244
1245 return iptr - o_iptr;
1246 }
1247 /*
1248 Fighters ^FIGHTERS ^BayStars ^Red[Ss]tar/ ^REDSTAR/ ^Parsifal ^VALKYRIE ^Valkyrie
1249 ^Dr.Death ^IamCHONO ^RAGNAROK ^MARAOH.. ^MARAOH// ......... God[Ff]ather GODFATHER
1250 ^maraGULO[./] BLACKJACK ^[Bb]lackjack ^BlackJack [Pp]atagonia PATAGONIA ^JC.PENNEY
1251 ^JC.Penney ^syombolic ROCKNROLL stammerB4U Ms.Erie.W. MARA.w/w/w R3[0-4]SKYLINE
1252 100000[Gg]et. 100000GET.
1253 */
1254 signed char *
1255 expr_parse(signed char *iptr,
1256 int codesiz_limit,
1257 char const *expr)
1258 {
1259 /* ƒtƒ@ƒCƒ‹‚đ“ǂݍž‚Ţ
1260 ‚ą‚̔łł͎蔲‚Ť‚Ĺ 64K §ŒŔ */
1261 #define TARGET_SIZ 65536
1262 char expr_buf[TARGET_SIZ + 1];
1263 FILE *fp;
1264 size_t sz;
1265
1266 fp = fopen("target.txt", "rb");
1267 assert(fp != NULL);
1268 memset(expr_buf, 0, TARGET_SIZ + 1);
1269 sz = fread(expr_buf, sizeof(char), TARGET_SIZ, fp);
1270 fclose(fp);
1271
1272 /* XXX ƒ^[ƒQƒbƒg‚ĚƒTƒCƒY‚đƒ`ƒFƒbƒN */
1273 if (sz == TARGET_SIZ)
1274 {
1275 /* ƒg[ƒNƒ“‚Ěƒgƒ‰ƒo[ƒX */
1276 char *ds, *pe, *ps;
1277 for (ds = &expr_buf[TARGET_SIZ - 1];
1278 !isspace(*ds);
1279 ds--)
1280 assert(ds >= expr_buf);
1281 for (pe = ds++; isspace(*pe); pe--)
1282 assert(pe >= expr_buf);
1283 for (ps = pe++; !isspace(*ps); ps--)
1284 assert(ps >= expr_buf);
1285 fprintf(stderr, "WARNING: <");
1286 ps++;
1287 while (ps < pe)
1288 fputc(*ps++, stderr);
1289 fprintf(stderr, ">‚ć‚čŒă‚ë‚Ěƒ^[ƒQƒbƒg<%s(ry>‚̓I‡hƒ‹\n",
1290 ds);
1291 *pe = 0;
1292 }
1293
1294 /* MM7 ‚Ƀ^[ƒQƒbƒg–ˆ‚É”äŠrŒ‹‰Ę‚đ OR ‚ľ‚Ä‚˘‚­‚˝‚ß
1295 ‚Ü‚¸‚̓[ƒƒNƒŠƒA */
1296 iptr = reg_op(iptr, OP_XOR, 7, 7); /* MM7/R15 := 0 */
1297
1298 /* ‡ŒJ‚č‚É parse */
1299 expr = expr_buf;
1300 while (expr[0])
1301 {
1302 char const *p;
1303 int i;
1304
1305 /* “Ş‚Ě Whitespace ‚đ“ǂݔň‚΂ˇ */
1306 while (isspace(expr[0]))
1307 expr++;
1308
1309 if (!expr[0])
1310 break;
1311
1312 /* ƒg[ƒNƒ“‚đŘ‚čo‚ˇ */
1313 for (p = expr; expr[0] && !isspace(expr[0]); expr++)
1314 ;
1315
1316 /* “WŠJ‚ˇ‚é */
1317 for (i = 0; i < 10; i++)
1318 {
1319 int n = expr_make(iptr, i, p, expr - p);
1320 if (n < 0)
1321 break;
1322 #if DEBUG>=1
1323 if (n > 0)
1324 {
1325 int j;
1326 for (j = 0; &p[j] < expr; j++)
1327 putchar(p[j]);
1328 printf(": of=%d len=%d\n", i, expr - p);
1329 }
1330 #endif
1331 /* 1ƒ^[ƒQƒbƒg•Ş‚Ě”äŠrŒ‹‰Ę‚đ MM7 ‚ɒljÁ */
1332 if (n > 0)
1333 iptr = reg_op(iptr + n,
1334 OP_OR,
1335 7, /* MM7/R15 */
1336 0); /* MM0/R8 */
1337 }
1338 }
1339
1340 /* MM7 ‚ɐśŹ‚ł‚ę‚˝Œ‹‰Ę‚đ t[31] ‚ÉŠi”[ */
1341 return reg_mem(iptr,
1342 OP_STOR,
1343 7, /* MM7/R15 */
1344 PTR_T,
1345 sizeof(WS_T) * (64 + 31 - 16));
1346 }
1347
1348 static
1349 unsigned
1350 usec()
1351 {
1352 #if !defined(WIN32)
1353 struct timeval tv;
1354 gettimeofday(&tv, NULL);
1355 return 100 * tv.tv_sec + (tv.tv_usec / 10000);
1356 #else
1357 struct timeb tm;
1358 ftime(&tm);
1359 return 100 * tm.time + tm.millitm / 10;
1360 #endif
1361 }
1362
1363 static
1364 int
1365 log_printf(FILE *ofp, char const *fmt, ...)
1366 {
1367 int r;
1368 va_list ap;
1369 va_start(ap, fmt);
1370 vfprintf(stdout, fmt, ap);
1371 r = vfprintf(ofp, fmt, ap);
1372 va_end(ap);
1373 if (r > 0)
1374 return r;
1375 perror("log_printf");
1376 exit(errno);
1377 }
1378
1379 /***************************************************************
1380 *
1381 * ƒƒCƒ“ƒ‹[ƒv‚Ć‚Š
1382 *
1383 */
1384
1385 /* ’萔€ */
1386 #if N_STRIDE == 7
1387 static SLICE const sk6[N_STRIDE] =
1388 {
1389 {0xAAAAAAAAUL, 0xAAAAAAAAUL, 0xAAAAAAAAUL, 0xAAAAAAAAUL},
1390 {0xCCCCCCCCUL, 0xCCCCCCCCUL, 0xCCCCCCCCUL, 0xCCCCCCCCUL},
1391 {0xF0F0F0F0UL, 0xF0F0F0F0UL, 0xF0F0F0F0UL, 0xF0F0F0F0UL},
1392 {0xFF00FF00UL, 0xFF00FF00UL, 0xFF00FF00UL, 0xFF00FF00UL},
1393 {0xFFFF0000UL, 0xFFFF0000UL, 0xFFFF0000UL, 0xFFFF0000UL},
1394 {0x00000000UL, 0xFFFFFFFFUL, 0x00000000UL, 0xFFFFFFFFUL},
1395 {0x00000000UL, 0x00000000UL, 0xFFFFFFFFUL, 0xFFFFFFFFUL},
1396 };
1397 #elif N_STRIDE == 6
1398 static SLICE const sk6[N_STRIDE] =
1399 {
1400 {0xAAAAAAAAUL, 0xAAAAAAAAUL},
1401 {0xCCCCCCCCUL, 0xCCCCCCCCUL},
1402 {0xF0F0F0F0UL, 0xF0F0F0F0UL},
1403 {0xFF00FF00UL, 0xFF00FF00UL},
1404 {0xFFFF0000UL, 0xFFFF0000UL},
1405 {0x00000000UL, 0xFFFFFFFFUL},
1406 };
1407 #endif
1408
1409 #ifdef WIN32
1410 typedef int (__fastcall *CRYPT64_PP)(ALU_T const *k, ALU_T *lr);
1411 #endif
1412
1413 ALIGN_PREFIX(16) struct KEY key64 ALIGN_SUFFIX(16);
1414 ALIGN_PREFIX(16) struct PARAM param64 ALIGN_SUFFIX(16);
1415
1416 int
1417 main(int argc, char *argv[])
1418 {
1419 int i, j;
1420 int mincnt;
1421 signed char *code = NULL;
1422 FILE *ofp;
1423 int n_iter;
1424 int cr;
1425
1426 #define N_TS 4
1427 struct
1428 {
1429 unsigned t;
1430 int c;
1431 } ts[N_TS];
1432
1433 #ifdef WIN32
1434 HANDLE h;
1435 #endif
1436
1437 #ifndef __GNUC__
1438 CRYPT64_PP d_crypt64;
1439 #endif
1440
1441 #if 0
1442 if (argc < 2)
1443 {
1444 fprintf(stderr, "ŽŽ‚Ť‚Ú‚ń‚Ę\n");
1445 return 1;
1446 }
1447 #endif
1448
1449 assert((1 << N_STRIDE) == N_ALU * ALU_BITS);
1450
1451 /* t[16] ‚́A“ŕ•”‰‰ŽZ‚ĹŽg—p‚ˇ‚éAall 1 ‚Ş“ü‚Á‚Ä‚˘‚é */
1452 for (i = 0; i < N_ALU; i++)
1453 param64.t[16].a[i] = -1;
1454
1455 /* ŒĹ’čƒL[‚ĚƒRƒs[ */
1456 for (i = 0; i < N_STRIDE; i++)
1457 {
1458 int o = tr_pc1[7][6 - i] - 1;
1459 if (o < 28)
1460 {
1461 key64.k[0][0][o] = key64.k[0][1][o] = sk6[i];
1462 }
1463 else
1464 {
1465 o -= 28;
1466 key64.k[1][0][o] = key64.k[1][1][o] = sk6[i];
1467 }
1468 }
1469
1470 /* ƒL[ƒXƒPƒWƒ…[ƒ‹‚đ‚ą‚ą‚ɉŸ‚ľž‚߂è‚­
1471 ]—ˆ‚Í crypt64.S “ŕ‚ĹŠŽŒ‹‚ˇ‚é‚悤‚Ɉř‚˘‚Ä‚˘‚˝ */
1472 for (i = 0; i < 28; i++)
1473 key64.ks[i].a[0] = sizeof(WS_T) * ks_ls[i];
1474
1475 /* Salt‚đ‰Á–Ą‚ľ‚Č‚˘ę‡‚́AƒR[ƒh—Ěˆć‚đ
1476 writable —Ěˆć‚É“WŠJ‚ľ‚Č‚­‚Ä‚ŕ‚悢B
1477 [XXX] OS‚É‚ć‚Á‚ẮA‘ž&ŽŔs‰Â”\—Ěˆć‚đę—p‚ĚƒT[ƒ”ƒBƒX‚Ĺ
1478 Žć“ž‚ľ‚Ȃ݂ę‚΂Ȃç‚Č‚˘‚ŕ‚Ě‚ŕ‚ ‚邊‚ŕ‚ľ‚ę‚Č‚˘‚̂ŁA’ˆÓ */
1479 #ifdef WIN32
1480 h = CreateFileMapping(INVALID_HANDLE_VALUE,
1481 NULL,
1482 PAGE_EXECUTE_READWRITE,
1483 0, 0x20000000,
1484 NULL);
1485 #ifndef FILE_MAP_EXECUTE
1486 #define FILE_MAP_EXECUTE SECTION_MAP_EXECUTE /* XXX cygwin */
1487 #endif
1488 if (SUCCEEDED(h))
1489 code = (signed char *)MapViewOfFile(h,
1490 FILE_MAP_EXECUTE | FILE_MAP_WRITE,
1491 0, 0x10000000,
1492 0);
1493 #else
1494 code = (signed char *)mmap(NULL,
1495 0x10000000,
1496 PROT_EXEC | PROT_READ | PROT_WRITE,
1497 MAP_PRIVATE | MAP_ANON,
1498 1, /* fd */
1499 0);
1500 if ((void *)code == MAP_FAILED)
1501 code =NULL;
1502 #endif
1503
1504 /* ƒƒ‚ƒŠ‚ŞŠm•ۂłŤ‚Ä‚˘‚Č‚˘ę‡‚Ě‚˘‚ń‚ż‚Ť‘΍ô */
1505 if (code == NULL)
1506 code = (signed char *)malloc(crypt64_end - crypt64_sta + 1024 * 1024);
1507 assert(code != NULL);
1508
1509 /* Prologue ‚đ“WŠJ */
1510 memcpy(code, crypt64_sta, crypt64_end - crypt64_sta);
1511 #ifndef __GNUC__
1512 d_crypt64 = (CRYPT64_PP)code;
1513 #endif
1514 memcpy(expr_parse(code + (crypt64_end - crypt64_sta),
1515 1024 * 1024 - (crypt64_ep_end - crypt64_ep),
1516 argv[1]),
1517 crypt64_ep,
1518 crypt64_ep_end - crypt64_ep);
1519
1520 /* ƒL[‚̏‰Šú‰ť */
1521 srand(time(NULL));
1522 key_init();
1523 set_salt(code, key);
1524 for (i = 0; i < 8; i++)
1525 key_set64(&key64, i, okey[i] = key[i], 0, 0x7F);
1526
1527 #if DEBUG>=1
1528 printf("key=%p param=%p\n", &key64, &param64);
1529 #endif
1530 assert(!((ptrdiff_t)&key64 & (sizeof(WS_T) - 1)));
1531 assert(!((ptrdiff_t)&param64 & (sizeof(WS_T) - 1)));
1532
1533 if ((ofp = fopen("log.txt", "at")) == NULL)
1534 {
1535 perror("log.txt");
1536 return errno;
1537 }
1538
1539 setvbuf(ofp, NULL, _IONBF, BUFSIZ); /* XXX MSVCRT ‚Ĺ‚Í _IOLBF ‚ŞŠú‘Ň’Ę‚č‚É“Žě‚ľ‚Č‚˘ */
1540
1541 for (i = 0; i < N_TS; i++)
1542 ts[i].t = ts[i].c = 0;
1543
1544 mincnt = 0x7FFFFFFF;
1545 n_iter = 0;
1546 cr = 0;
1547 /* ’Tőƒ‹[ƒv‚ž‚ź‚Á‚Ć */
1548 for (;;)
1549 {
1550 int32_t cnt;
1551 int k, kk;
1552
1553 /* ŒŽ‚ĚƒZƒbƒg */
1554 for (i = 0; i < 8; i++)
1555 {
1556 key_set64(&key64, i, key[i], key[i] ^ okey[i], 0);
1557 okey[i] = key[i];
1558 }
1559
1560 /* ŒÄ‚Ô!
1561 LR ‰Šú‰ť‚́AƒTƒuƒ‚ƒWƒ…[ƒ‹“ŕ‚ōs‚¤‚ׂľ
1562 FASTCALL ‚ɏ€‚ś‚˝ŒÄ‚яo‚ľ‚Ě‚˝‚߁A
1563 ƒzƒ“ƒg‚Í‚˘‚낢‚냌ƒWƒXƒ^‚Ş”j‰ó‚ł‚ę‚éƒnƒYc‚Č‚ń‚ž‚ށB */
1564 #ifdef __GNUC__
1565 asm volatile("call *%3"
1566 : "=a"(cnt)
1567 : "c"(key64.k), "d"(param64.lr),
1568 "m"(code)
1569 //"m"(crypt64_sta)
1570 : CRYPT64_CLOBBER "memory");
1571 #else
1572 cnt = (*d_crypt64)(key64.k[0][0][0].a, param64.lr[0][0].a);
1573 #endif
1574 if (mincnt > cnt && cnt > 0)
1575 {
1576 mincnt = cnt;
1577 if (cr)
1578 fprintf(stderr, "\n");
1579 cr = 0;
1580 fprintf(stderr, "cycle=%d\n", (int)cnt);
1581 }
1582
1583 /* ƒqƒbƒg‚ľ‚˝‚Ć‚Ť‚̏ˆ— */
1584 for (kk = 0; kk < N_ALU; kk++)
1585 {
1586 ALU_T t;
1587
1588 t = param64.t[31].a[kk];
1589 if (!t)
1590 continue;
1591
1592 for (k = 0; k < ALU_BITS; k++)
1593 {
1594 char hash[16];
1595 unsigned char buf[32];
1596
1597 if (!(t & ((ALU_T)1 << k)))
1598 continue;
1599
1600 /* XXX Žč”˛‚Ť‚Ě‚˝‚߁Aƒ[ƒN‚ɂ͂ݏo‚Ä‚˘‚é 2 ƒrƒbƒg‚đ‚ą‚ą‚Ĺ—Ž‚Ć‚ˇ
1601 ƒqƒbƒg‚ˇ‚é‚˝‚Ń‚Éç’ˇ‚ɍs‚í‚ę‚邪A‹C‚É‚ľ‚Ă͂˘‚Š‚ń */
1602 for (i = 0; i < N_ALU; i++)
1603 param64.t[0].a[i] = param64.t[1].a[i] = 0;
1604 for (i = 1; i < 11; i++)
1605 {
1606 unsigned c = 0;
1607 for (j = 0; j < 6; j++)
1608 c = (c << 1) | !!(param64.lr[0][tr_fp[6 * i + j]].a[kk] & ((ALU_T)1 << k));
1609 hash[i - 1] = c["./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"];
1610 }
1611 hash[10] = 0;
1612
1613 memcpy(buf, key, 32);
1614 buf[8] = buf[9] = 0;
1615 buf[7] = (buf[7] & -(1 << N_STRIDE) & 0x7F) + ALU_BITS * kk + k;
1616 if (translate(buf, 0, 1))
1617 {
1618 if (cr)
1619 fprintf(stderr, "\n");
1620 cr = 0;
1621 log_printf(ofp,
1622 "Ÿ%s #%-10.10s(%02X %02X %02X %02X %02X %02X %02X %02X/%02X)\n",
1623 hash,
1624 buf,
1625 buf[0], buf[1], buf[2], buf[3],
1626 buf[4], buf[5], buf[6], buf[7],
1627 buf[8]);
1628 }
1629 else
1630 {
1631 #if DEBUG>=1
1632 if (cr)
1633 fprintf(stderr, "\n");
1634 cr = 0;
1635 log_printf(ofp,
1636 "Ÿ%s (%02X %02X %02X %02X %02X %02X %02X %02X )\n",
1637 hash,
1638 buf[0], buf[1], buf[2], buf[3],
1639 buf[4], buf[5], buf[6], buf[7]);
1640 #endif
1641 }
1642 }
1643 }
1644
1645 if (++n_iter - ts[0].c >= 8192)
1646 {
1647 int t = usec();
1648 if (ts[N_TS - 1].c)
1649 {
1650 int a = (100 << N_STRIDE) * (n_iter - ts[N_TS - 1].c) / (t - ts[N_TS - 1].t);
1651 fprintf(stderr,
1652 "%8d.%03d(ktrips/sec)\r",
1653 a / 1000,
1654 a % 1000);
1655 cr++;
1656 }
1657 for (i = N_TS - 1; i >= 1; i--)
1658 ts[i] = ts[i - 1];
1659 ts[0].c = n_iter;
1660 ts[0].t = t;
1661 for (i = 1; i < N_TS; i++)
1662 if (ts[i].c)
1663 break;
1664 else
1665 ts[i] = ts[i - 1];
1666 }
1667 #if 1
1668 if (!key_inc(3))
1669 {
1670 #if DEBUG>=2
1671 printf("********************************\n");
1672 #endif
1673 key_reset(0);
1674 set_salt(code, key);
1675 for (i = 0; i < 8; i++)
1676 key_set64(&key64, i, okey[i] = key[i], 0, 0x7F);
1677 }
1678 #endif
1679 }
1680
1681 return 0;
1682 }
1683
1684 /*
1685 * Local Variables:
1686 * tab-width: 4
1687 * End:
1688 *
1689 * EOF */

Properties

Name Value
svn:eol-style native

Back to OSDN">Back to OSDN
ViewVC Help
Powered by ViewVC 1.1.26