KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > apache > directory > ldapstudio > browser > core > utils > UnixCrypt


1 /*
2  * Licensed to the Apache Software Foundation (ASF) under one
3  * or more contributor license agreements. See the NOTICE file
4  * distributed with this work for additional information
5  * regarding copyright ownership. The ASF licenses this file
6  * to you under the Apache License, Version 2.0 (the
7  * "License"); you may not use this file except in compliance
8  * with the License. You may obtain a copy of the License at
9  *
10  * http://www.apache.org/licenses/LICENSE-2.0
11  *
12  * Unless required by applicable law or agreed to in writing,
13  * software distributed under the License is distributed on an
14  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15  * KIND, either express or implied. See the License for the
16  * specific language governing permissions and limitations
17  * under the License.
18  *
19  */

20
21 /*
22  * @(#)UnixCrypt.java 0.9 96/11/25
23  *
24  * Copyright (c) 1996 Aki Yoshida. All rights reserved.
25  *
26  * Permission to use, copy, modify and distribute this software
27  * for non-commercial or commercial purposes and without fee is
28  * hereby granted provided that this copyright notice appears in
29  * all copies.
30  */

31
32 /**
33  * Unix crypt(3C) utility
34  *
35  * @version 0.9, 11/25/96
36  * @author Aki Yoshida
37  */

38
39 /**
40  * modified April 2001
41  * by Iris Van den Broeke, Daniel Deville
42  */

43
44 package org.apache.directory.ldapstudio.browser.core.utils;
45
46
47    /*
48     * @(#)UnixCrypt.java 0.9 96/11/25
49     *
50     * Copyright (c) 1996 Aki Yoshida. All rights reserved.
51     *
52     * Permission to use, copy, modify and distribute this software
53     * for non-commercial or commercial purposes and without fee is
54     * hereby granted provided that this copyright notice appears in
55     * all copies.
56    */

57   
58   /**
59    * Unix crypt(3C) utility
60    *
61    * @version 0.9, 11/25/96
62    * @author Aki Yoshida
63    */

64   
65   /**
66    * modified April 2001
67    * by Iris Van den Broeke, Daniel Deville
68    */

69   
70   
71   /* ------------------------------------------------------------ */
72   /** Unix Crypt.
73    * Implements the one way cryptography used by Unix systems for
74    * simple password protection.
75    * @version $Id: UnixCrypt.java,v 1.1 2005/10/05 14:09:14 janb Exp $
76    * @author Greg Wilkins (gregw)
77    */

78   public class UnixCrypt extends Object JavaDoc
79   {
80   
81       /* (mostly) Standard DES Tables from Tom Truscott */
82       private static final byte[] IP = { /* initial permutation */
83           58, 50, 42, 34, 26, 18, 10, 2,
84           60, 52, 44, 36, 28, 20, 12, 4,
85           62, 54, 46, 38, 30, 22, 14, 6,
86           64, 56, 48, 40, 32, 24, 16, 8,
87           57, 49, 41, 33, 25, 17, 9, 1,
88           59, 51, 43, 35, 27, 19, 11, 3,
89           61, 53, 45, 37, 29, 21, 13, 5,
90           63, 55, 47, 39, 31, 23, 15, 7};
91   
92       /* The final permutation is the inverse of IP - no table is necessary */
93       private static final byte[] ExpandTr = { /* expansion operation */
94           32, 1, 2, 3, 4, 5,
95           4, 5, 6, 7, 8, 9,
96           8, 9, 10, 11, 12, 13,
97           12, 13, 14, 15, 16, 17,
98           16, 17, 18, 19, 20, 21,
99           20, 21, 22, 23, 24, 25,
100           24, 25, 26, 27, 28, 29,
101           28, 29, 30, 31, 32, 1};
102   
103       private static final byte[] PC1 = { /* permuted choice table 1 */
104           57, 49, 41, 33, 25, 17, 9,
105           1, 58, 50, 42, 34, 26, 18,
106           10, 2, 59, 51, 43, 35, 27,
107           19, 11, 3, 60, 52, 44, 36,
108       
109           63, 55, 47, 39, 31, 23, 15,
110           7, 62, 54, 46, 38, 30, 22,
111           14, 6, 61, 53, 45, 37, 29,
112           21, 13, 5, 28, 20, 12, 4};
113   
114       private static final byte[] Rotates = { /* PC1 rotation schedule */
115           1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1};
116   
117   
118       private static final byte[] PC2 = { /* permuted choice table 2 */
119           9, 18, 14, 17, 11, 24, 1, 5,
120           22, 25, 3, 28, 15, 6, 21, 10,
121           35, 38, 23, 19, 12, 4, 26, 8,
122           43, 54, 16, 7, 27, 20, 13, 2,
123   
124           0, 0, 41, 52, 31, 37, 47, 55,
125           0, 0, 30, 40, 51, 45, 33, 48,
126           0, 0, 44, 49, 39, 56, 34, 53,
127           0, 0, 46, 42, 50, 36, 29, 32};
128   
129       private static final byte[][] S = { /* 48->32 bit substitution tables */
130           /* S[1] */
131           {14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7,
132            0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8,
133            4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0,
134            15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13},
135           /* S[2] */
136           {15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10,
137            3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5,
138            0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15,
139            13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9},
140           /* S[3] */
141           {10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8,
142            13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1,
143            13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7,
144            1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12},
145          /* S[4] */
146          {7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15,
147           13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9,
148           10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4,
149           3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14},
150          /* S[5] */
151          {2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9,
152           14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6,
153           4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14,
154           11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3},
155          /* S[6] */
156          {12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11,
157           10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8,
158           9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6,
159           4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13},
160          /* S[7] */
161          {4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1,
162           13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6,
163           1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2,
164           6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12},
165          /* S[8] */
166          {13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7,
167           1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2,
168           7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8,
169           2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11}};
170  
171      private static final byte[] P32Tr = { /* 32-bit permutation function */
172          16, 7, 20, 21,
173          29, 12, 28, 17,
174          1, 15, 23, 26,
175          5, 18, 31, 10,
176          2, 8, 24, 14,
177          32, 27, 3, 9,
178          19, 13, 30, 6,
179          22, 11, 4, 25};
180  
181      private static final byte[] CIFP = { /* compressed/interleaved permutation */
182          1, 2, 3, 4, 17, 18, 19, 20,
183          5, 6, 7, 8, 21, 22, 23, 24,
184          9, 10, 11, 12, 25, 26, 27, 28,
185          13, 14, 15, 16, 29, 30, 31, 32,
186  
187          33, 34, 35, 36, 49, 50, 51, 52,
188          37, 38, 39, 40, 53, 54, 55, 56,
189          41, 42, 43, 44, 57, 58, 59, 60,
190          45, 46, 47, 48, 61, 62, 63, 64};
191  
192      private static final byte[] ITOA64 = { /* 0..63 => ascii-64 */
193          (byte)'.',(byte) '/',(byte) '0',(byte) '1',(byte) '2',(byte) '3',(byte) '4',(byte) '5',
194          (byte)'6',(byte) '7',(byte) '8',(byte) '9',(byte) 'A',(byte) 'B',(byte) 'C',(byte) 'D',
195          (byte)'E',(byte) 'F',(byte) 'G',(byte) 'H',(byte) 'I',(byte) 'J',(byte) 'K',(byte) 'L',
196          (byte)'M',(byte) 'N',(byte) 'O',(byte) 'P',(byte) 'Q',(byte) 'R',(byte) 'S',(byte) 'T',
197          (byte)'U',(byte) 'V',(byte) 'W',(byte) 'X',(byte) 'Y',(byte) 'Z',(byte) 'a',(byte) 'b',
198          (byte)'c',(byte) 'd',(byte) 'e',(byte) 'f',(byte) 'g',(byte) 'h',(byte) 'i',(byte) 'j',
199          (byte)'k',(byte) 'l',(byte) 'm',(byte) 'n',(byte) 'o',(byte) 'p',(byte) 'q',(byte) 'r',
200          (byte)'s',(byte) 't',(byte) 'u',(byte) 'v',(byte) 'w',(byte) 'x',(byte) 'y',(byte) 'z'};
201  
202      /* ===== Tables that are initialized at run time ==================== */
203  
204      private static byte[] A64TOI = new byte[128]; /* ascii-64 => 0..63 */
205  
206      /* Initial key schedule permutation */
207      private static long[][] PC1ROT = new long[16][16];
208  
209      /* Subsequent key schedule rotation permutations */
210      private static long[][][] PC2ROT = new long[2][16][16];
211  
212      /* Initial permutation/expansion table */
213      private static long[][] IE3264 = new long[8][16];
214  
215      /* Table that combines the S, P, and E operations. */
216      private static long[][] SPE = new long[8][64];
217  
218      /* compressed/interleaved => final permutation table */
219      private static long[][] CF6464 = new long[16][16];
220  
221  
222      /* ==================================== */
223  
224      static {
225          byte[] perm = new byte[64];
226          byte[] temp = new byte[64];
227  
228          // inverse table.
229
for (int i=0; i<64; i++) A64TOI[ITOA64[i]] = (byte)i;
230  
231          // PC1ROT - bit reverse, then PC1, then Rotate, then PC2
232
for (int i=0; i<64; i++) perm[i] = (byte)0;;
233          for (int i=0; i<64; i++) {
234              int k;
235              if ((k = (int)PC2[i]) == 0) continue;
236              k += Rotates[0]-1;
237              if ((k%28) < Rotates[0]) k -= 28;
238              k = (int)PC1[k];
239              if (k > 0) {
240                  k--;
241                  k = (k|0x07) - (k&0x07);
242                  k++;
243              }
244              perm[i] = (byte)k;
245          }
246          init_perm(PC1ROT, perm, 8);
247  
248          // PC2ROT - PC2 inverse, then Rotate, then PC2
249
for (int j=0; j<2; j++) {
250              int k;
251              for (int i=0; i<64; i++) perm[i] = temp[i] = 0;
252              for (int i=0; i<64; i++) {
253                  if ((k = (int)PC2[i]) == 0) continue;
254                  temp[k-1] = (byte)(i+1);
255              }
256              for (int i=0; i<64; i++) {
257                  if ((k = (int)PC2[i]) == 0) continue;
258                  k += j;
259                  if ((k%28) <= j) k -= 28;
260                  perm[i] = temp[k];
261              }
262  
263              init_perm(PC2ROT[j], perm, 8);
264          }
265  
266          // Bit reverse, intial permupation, expantion
267
for (int i=0; i<8; i++) {
268              for (int j=0; j<8; j++) {
269                  int k = (j < 2)? 0: IP[ExpandTr[i*6+j-2]-1];
270                  if (k > 32) k -= 32;
271                  else if (k > 0) k--;
272                  if (k > 0) {
273                      k--;
274                      k = (k|0x07) - (k&0x07);
275                      k++;
276                  }
277                  perm[i*8+j] = (byte)k;
278              }
279          }
280  
281          init_perm(IE3264, perm, 8);
282  
283          // Compression, final permutation, bit reverse
284
for (int i=0; i<64; i++) {
285              int k = IP[CIFP[i]-1];
286              if (k > 0) {
287                  k--;
288                  k = (k|0x07) - (k&0x07);
289                  k++;
290              }
291              perm[k-1] = (byte)(i+1);
292          }
293  
294          init_perm(CF6464, perm, 8);
295  
296          // SPE table
297
for (int i=0; i<48; i++)
298              perm[i] = P32Tr[ExpandTr[i]-1];
299          for (int t=0; t<8; t++) {
300              for (int j=0; j<64; j++) {
301                  int k = (((j >> 0) & 0x01) << 5) | (((j >> 1) & 0x01) << 3) |
302                      (((j >> 2) & 0x01) << 2) | (((j >> 3) & 0x01) << 1) |
303                      (((j >> 4) & 0x01) << 0) | (((j >> 5) & 0x01) << 4);
304                  k = S[t][k];
305                  k = (((k >> 3) & 0x01) << 0) | (((k >> 2) & 0x01) << 1) |
306                      (((k >> 1) & 0x01) << 2) | (((k >> 0) & 0x01) << 3);
307                  for (int i=0; i<32; i++) temp[i] = 0;
308                  for (int i=0; i<4; i++) temp[4*t+i] = (byte)((k >> i) & 0x01);
309                  long kk = 0;
310                  for (int i=24; --i>=0; ) kk = ((kk<<1) |
311                                                 ((long)temp[perm[i]-1])<<32 |
312                                                 ((long)temp[perm[i+24]-1]));
313  
314                  SPE[t][j] = to_six_bit(kk);
315              }
316          }
317      }
318  
319      /**
320       * You can't call the constructer.
321       */

322      private UnixCrypt() { }
323  
324      /**
325       * Returns the transposed and split code of a 24-bit code
326       * into a 4-byte code, each having 6 bits.
327       */

328      private static int to_six_bit(int num) {
329          return (((num << 26) & 0xfc000000) | ((num << 12) & 0xfc0000) |
330                  ((num >> 2) & 0xfc00) | ((num >> 16) & 0xfc));
331      }
332  
333      /**
334       * Returns the transposed and split code of two 24-bit code
335       * into two 4-byte code, each having 6 bits.
336       */

337      private static long to_six_bit(long num) {
338          return (((num << 26) & 0xfc000000fc000000L) | ((num << 12) & 0xfc000000fc0000L) |
339                  ((num >> 2) & 0xfc000000fc00L) | ((num >> 16) & 0xfc000000fcL));
340      }
341    
342      /**
343       * Returns the permutation of the given 64-bit code with
344       * the specified permutataion table.
345       */

346      private static long perm6464(long c, long[][]p) {
347          long out = 0L;
348          for (int i=8; --i>=0; ) {
349              int t = (int)(0x00ff & c);
350              c >>= 8;
351              long tp = p[i<<1][t&0x0f];
352              out |= tp;
353              tp = p[(i<<1)+1][t>>4];
354              out |= tp;
355          }
356          return out;
357      }
358  
359      /**
360       * Returns the permutation of the given 32-bit code with
361       * the specified permutataion table.
362       */

363      private static long perm3264(int c, long[][]p) {
364          long out = 0L;
365          for (int i=4; --i>=0; ) {
366              int t = (0x00ff & c);
367              c >>= 8;
368              long tp = p[i<<1][t&0x0f];
369              out |= tp;
370              tp = p[(i<<1)+1][t>>4];
371              out |= tp;
372          }
373          return out;
374      }
375  
376      /**
377       * Returns the key schedule for the given key.
378       */

379      private static long[] des_setkey(long keyword) {
380          long K = perm6464(keyword, PC1ROT);
381          long[] KS = new long[16];
382          KS[0] = K&~0x0303030300000000L;
383      
384          for (int i=1; i<16; i++) {
385              KS[i] = K;
386              K = perm6464(K, PC2ROT[Rotates[i]-1]);
387  
388              KS[i] = K&~0x0303030300000000L;
389          }
390          return KS;
391      }
392  
393      /**
394       * Returns the DES encrypted code of the given word with the specified
395       * environment.
396       */

397      private static long des_cipher(long in, int salt, int num_iter, long[] KS) {
398          salt = to_six_bit(salt);
399          long L = in;
400          long R = L;
401          L &= 0x5555555555555555L;
402          R = (R & 0xaaaaaaaa00000000L) | ((R >> 1) & 0x0000000055555555L);
403          L = ((((L << 1) | (L << 32)) & 0xffffffff00000000L) |
404               ((R | (R >> 32)) & 0x00000000ffffffffL));
405      
406          L = perm3264((int)(L>>32), IE3264);
407          R = perm3264((int)(L&0xffffffff), IE3264);
408  
409          while (--num_iter >= 0) {
410              for (int loop_count=0; loop_count<8; loop_count++) {
411                  long kp;
412                  long B;
413                  long k;
414  
415                  kp = KS[(loop_count<<1)];
416                  k = ((R>>32) ^ R) & salt & 0xffffffffL;
417                  k |= (k<<32);
418                  B = (k ^ R ^ kp);
419  
420                  L ^= (SPE[0][(int)((B>>58)&0x3f)] ^ SPE[1][(int)((B>>50)&0x3f)] ^
421                        SPE[2][(int)((B>>42)&0x3f)] ^ SPE[3][(int)((B>>34)&0x3f)] ^
422                        SPE[4][(int)((B>>26)&0x3f)] ^ SPE[5][(int)((B>>18)&0x3f)] ^
423                        SPE[6][(int)((B>>10)&0x3f)] ^ SPE[7][(int)((B>>2)&0x3f)]);
424  
425                  kp = KS[(loop_count<<1)+1];
426                  k = ((L>>32) ^ L) & salt & 0xffffffffL;
427                  k |= (k<<32);
428                  B = (k ^ L ^ kp);
429  
430                  R ^= (SPE[0][(int)((B>>58)&0x3f)] ^ SPE[1][(int)((B>>50)&0x3f)] ^
431                        SPE[2][(int)((B>>42)&0x3f)] ^ SPE[3][(int)((B>>34)&0x3f)] ^
432                        SPE[4][(int)((B>>26)&0x3f)] ^ SPE[5][(int)((B>>18)&0x3f)] ^
433                        SPE[6][(int)((B>>10)&0x3f)] ^ SPE[7][(int)((B>>2)&0x3f)]);
434              }
435              // swap L and R
436
L ^= R;
437              R ^= L;
438              L ^= R;
439          }
440          L = ((((L>>35) & 0x0f0f0f0fL) | (((L&0xffffffff)<<1) & 0xf0f0f0f0L))<<32 |
441               (((R>>35) & 0x0f0f0f0fL) | (((R&0xffffffff)<<1) & 0xf0f0f0f0L)));
442  
443          L = perm6464(L, CF6464);
444  
445          return L;
446      }
447  
448      /**
449       * Initializes the given permutation table with the mapping table.
450       */

451      private static void init_perm(long[][] perm, byte[] p,int chars_out) {
452          for (int k=0; k<chars_out*8; k++) {
453  
454              int l = p[k] - 1;
455              if (l < 0) continue;
456              int i = l>>2;
457              l = 1<<(l&0x03);
458              for (int j=0; j<16; j++) {
459                  int s = ((k&0x07)+((7-(k>>3))<<3));
460                  if ((j & l) != 0x00) perm[i][j] |= (1L<<s);
461              }
462          }
463      }
464  
465      /**
466       * Encrypts String into crypt (Unix) code.
467       * @param key the key to be encrypted
468       * @param setting the salt to be used
469       * @return the encrypted String
470       */

471      public static String JavaDoc crypt(String JavaDoc key, String JavaDoc setting)
472      {
473          long constdatablock = 0L; /* encryption constant */
474          byte[] cryptresult = new byte[13]; /* encrypted result */
475          long keyword = 0L;
476          /* invalid parameters! */
477          if(key==null||setting==null)
478              return "*"; // will NOT match under ANY circumstances!
479

480          int keylen = key.length();
481  
482          for (int i=0; i<8 ; i++) {
483              keyword = (keyword << 8) | ((i < keylen)? 2*key.charAt(i): 0);
484          }
485  
486          long[] KS = des_setkey(keyword);
487  
488          int salt = 0;
489          for (int i=2; --i>=0;) {
490              char c = (i < setting.length())? setting.charAt(i): '.';
491              cryptresult[i] = (byte)c;
492              salt = (salt<<6) | (0x00ff&A64TOI[c]);
493          }
494  
495          long rsltblock = des_cipher(constdatablock, salt, 25, KS);
496  
497          cryptresult[12] = ITOA64[(((int)rsltblock)<<2)&0x3f];
498          rsltblock >>= 4;
499          for (int i=12; --i>=2; ) {
500              cryptresult[i] = ITOA64[((int)rsltblock)&0x3f];
501              rsltblock >>= 6;
502          }
503  
504          return new String JavaDoc(cryptresult, 0x00, 0, 13);
505      }
506  
507      public static void main(String JavaDoc[] arg)
508      {
509          if (arg.length!=2)
510          {
511              System.err.println("Usage - java org.mortbay.util.UnixCrypt <key> <salt>");
512              System.exit(1);
513          }
514  
515          System.err.println("Crypt="+crypt(arg[0],arg[1]));
516      }
517      
518  }
519
Popular Tags