1 /*
   2  * Copyright (c) 1997, 2011, Oracle and/or its affiliates. All rights reserved.
   3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
   4  *
   5  * This code is free software; you can redistribute it and/or modify it
   6  * under the terms of the GNU General Public License version 2 only, as
   7  * published by the Free Software Foundation.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 package com.sun.crypto.provider;
  27 
  28 import java.security.InvalidKeyException;
  29 
  30 /**
  31  * This is the internal DES class responsible for encryption and
  32  * decryption of a byte array of size <code>DES_BLOCK_SIZE</code>.
  33  *
  34  * @author Gigi Ankeny
  35  * @author Jan Luehe
  36  *
  37  *
  38  * @see DESConstants
  39  * @see DESCipher
  40  */
  41 
  42 class DESCrypt extends SymmetricCipher implements DESConstants {
  43     private static final int[] s0p = {
  44         0x00410100, 0x00010000, 0x40400000, 0x40410100, 0x00400000,
  45         0x40010100, 0x40010000, 0x40400000, 0x40010100, 0x00410100,
  46         0x00410000, 0x40000100, 0x40400100, 0x00400000, 0x00000000,
  47         0x40010000, 0x00010000, 0x40000000, 0x00400100, 0x00010100,
  48         0x40410100, 0x00410000, 0x40000100, 0x00400100, 0x40000000,
  49         0x00000100, 0x00010100, 0x40410000, 0x00000100, 0x40400100,
  50         0x40410000, 0x00000000, 0x00000000, 0x40410100, 0x00400100,
  51         0x40010000, 0x00410100, 0x00010000, 0x40000100, 0x00400100,
  52         0x40410000, 0x00000100, 0x00010100, 0x40400000, 0x40010100,
  53         0x40000000, 0x40400000, 0x00410000, 0x40410100, 0x00010100,
  54         0x00410000, 0x40400100, 0x00400000, 0x40000100, 0x40010000,
  55         0x00000000, 0x00010000, 0x00400000, 0x40400100, 0x00410100,
  56         0x40000000, 0x40410000, 0x00000100, 0x40010100,
  57     };
  58 
  59     private static final int[] s1p = {
  60         0x08021002, 0x00000000, 0x00021000, 0x08020000, 0x08000002,
  61         0x00001002, 0x08001000, 0x00021000, 0x00001000, 0x08020002,
  62         0x00000002, 0x08001000, 0x00020002, 0x08021000, 0x08020000,
  63         0x00000002, 0x00020000, 0x08001002, 0x08020002, 0x00001000,
  64         0x00021002, 0x08000000, 0x00000000, 0x00020002, 0x08001002,
  65         0x00021002, 0x08021000, 0x08000002, 0x08000000, 0x00020000,
  66         0x00001002, 0x08021002, 0x00020002, 0x08021000, 0x08001000,
  67         0x00021002, 0x08021002, 0x00020002, 0x08000002, 0x00000000,
  68         0x08000000, 0x00001002, 0x00020000, 0x08020002, 0x00001000,
  69         0x08000000, 0x00021002, 0x08001002, 0x08021000, 0x00001000,
  70         0x00000000, 0x08000002, 0x00000002, 0x08021002, 0x00021000,
  71         0x08020000, 0x08020002, 0x00020000, 0x00001002, 0x08001000,
  72         0x08001002, 0x00000002, 0x08020000, 0x00021000,
  73     };
  74 
  75     private static final int[] s2p = {
  76         0x20800000, 0x00808020, 0x00000020, 0x20800020, 0x20008000,
  77         0x00800000, 0x20800020, 0x00008020, 0x00800020, 0x00008000,
  78         0x00808000, 0x20000000, 0x20808020, 0x20000020, 0x20000000,
  79         0x20808000, 0x00000000, 0x20008000, 0x00808020, 0x00000020,
  80         0x20000020, 0x20808020, 0x00008000, 0x20800000, 0x20808000,
  81         0x00800020, 0x20008020, 0x00808000, 0x00008020, 0x00000000,
  82         0x00800000, 0x20008020, 0x00808020, 0x00000020, 0x20000000,
  83         0x00008000, 0x20000020, 0x20008000, 0x00808000, 0x20800020,
  84         0x00000000, 0x00808020, 0x00008020, 0x20808000, 0x20008000,
  85         0x00800000, 0x20808020, 0x20000000, 0x20008020, 0x20800000,
  86         0x00800000, 0x20808020, 0x00008000, 0x00800020, 0x20800020,
  87         0x00008020, 0x00800020, 0x00000000, 0x20808000, 0x20000020,
  88         0x20800000, 0x20008020, 0x00000020, 0x00808000,
  89     };
  90 
  91     private static final int[] s3p = {
  92         0x00080201, 0x02000200, 0x00000001, 0x02080201, 0x00000000,
  93         0x02080000, 0x02000201, 0x00080001, 0x02080200, 0x02000001,
  94         0x02000000, 0x00000201, 0x02000001, 0x00080201, 0x00080000,
  95         0x02000000, 0x02080001, 0x00080200, 0x00000200, 0x00000001,
  96         0x00080200, 0x02000201, 0x02080000, 0x00000200, 0x00000201,
  97         0x00000000, 0x00080001, 0x02080200, 0x02000200, 0x02080001,
  98         0x02080201, 0x00080000, 0x02080001, 0x00000201, 0x00080000,
  99         0x02000001, 0x00080200, 0x02000200, 0x00000001, 0x02080000,
 100         0x02000201, 0x00000000, 0x00000200, 0x00080001, 0x00000000,
 101         0x02080001, 0x02080200, 0x00000200, 0x02000000, 0x02080201,
 102         0x00080201, 0x00080000, 0x02080201, 0x00000001, 0x02000200,
 103         0x00080201, 0x00080001, 0x00080200, 0x02080000, 0x02000201,
 104         0x00000201, 0x02000000, 0x02000001, 0x02080200,
 105     };
 106 
 107     private static final int[] s4p = {
 108         0x01000000, 0x00002000, 0x00000080, 0x01002084, 0x01002004,
 109         0x01000080, 0x00002084, 0x01002000, 0x00002000, 0x00000004,
 110         0x01000004, 0x00002080, 0x01000084, 0x01002004, 0x01002080,
 111         0x00000000, 0x00002080, 0x01000000, 0x00002004, 0x00000084,
 112         0x01000080, 0x00002084, 0x00000000, 0x01000004, 0x00000004,
 113         0x01000084, 0x01002084, 0x00002004, 0x01002000, 0x00000080,
 114         0x00000084, 0x01002080, 0x01002080, 0x01000084, 0x00002004,
 115         0x01002000, 0x00002000, 0x00000004, 0x01000004, 0x01000080,
 116         0x01000000, 0x00002080, 0x01002084, 0x00000000, 0x00002084,
 117         0x01000000, 0x00000080, 0x00002004, 0x01000084, 0x00000080,
 118         0x00000000, 0x01002084, 0x01002004, 0x01002080, 0x00000084,
 119         0x00002000, 0x00002080, 0x01002004, 0x01000080, 0x00000084,
 120         0x00000004, 0x00002084, 0x01002000, 0x01000004,
 121     };
 122 
 123     private static final int[] s5p = {
 124         0x10000008, 0x00040008, 0x00000000, 0x10040400, 0x00040008,
 125         0x00000400, 0x10000408, 0x00040000, 0x00000408, 0x10040408,
 126         0x00040400, 0x10000000, 0x10000400, 0x10000008, 0x10040000,
 127         0x00040408, 0x00040000, 0x10000408, 0x10040008, 0x00000000,
 128         0x00000400, 0x00000008, 0x10040400, 0x10040008, 0x10040408,
 129         0x10040000, 0x10000000, 0x00000408, 0x00000008, 0x00040400,
 130         0x00040408, 0x10000400, 0x00000408, 0x10000000, 0x10000400,
 131         0x00040408, 0x10040400, 0x00040008, 0x00000000, 0x10000400,
 132         0x10000000, 0x00000400, 0x10040008, 0x00040000, 0x00040008,
 133         0x10040408, 0x00040400, 0x00000008, 0x10040408, 0x00040400,
 134         0x00040000, 0x10000408, 0x10000008, 0x10040000, 0x00040408,
 135         0x00000000, 0x00000400, 0x10000008, 0x10000408, 0x10040400,
 136         0x10040000, 0x00000408, 0x00000008, 0x10040008,
 137     };
 138 
 139     private static final int[] s6p = {
 140         0x00000800, 0x00000040, 0x00200040, 0x80200000, 0x80200840,
 141         0x80000800, 0x00000840, 0x00000000, 0x00200000, 0x80200040,
 142         0x80000040, 0x00200800, 0x80000000, 0x00200840, 0x00200800,
 143         0x80000040, 0x80200040, 0x00000800, 0x80000800, 0x80200840,
 144         0x00000000, 0x00200040, 0x80200000, 0x00000840, 0x80200800,
 145         0x80000840, 0x00200840, 0x80000000, 0x80000840, 0x80200800,
 146         0x00000040, 0x00200000, 0x80000840, 0x00200800, 0x80200800,
 147         0x80000040, 0x00000800, 0x00000040, 0x00200000, 0x80200800,
 148         0x80200040, 0x80000840, 0x00000840, 0x00000000, 0x00000040,
 149         0x80200000, 0x80000000, 0x00200040, 0x00000000, 0x80200040,
 150         0x00200040, 0x00000840, 0x80000040, 0x00000800, 0x80200840,
 151         0x00200000, 0x00200840, 0x80000000, 0x80000800, 0x80200840,
 152         0x80200000, 0x00200840, 0x00200800, 0x80000800,
 153     };
 154 
 155     private static final int[] s7p = {
 156         0x04100010, 0x04104000, 0x00004010, 0x00000000, 0x04004000,
 157         0x00100010, 0x04100000, 0x04104010, 0x00000010, 0x04000000,
 158         0x00104000, 0x00004010, 0x00104010, 0x04004010, 0x04000010,
 159         0x04100000, 0x00004000, 0x00104010, 0x00100010, 0x04004000,
 160         0x04104010, 0x04000010, 0x00000000, 0x00104000, 0x04000000,
 161         0x00100000, 0x04004010, 0x04100010, 0x00100000, 0x00004000,
 162         0x04104000, 0x00000010, 0x00100000, 0x00004000, 0x04000010,
 163         0x04104010, 0x00004010, 0x04000000, 0x00000000, 0x00104000,
 164         0x04100010, 0x04004010, 0x04004000, 0x00100010, 0x04104000,
 165         0x00000010, 0x00100010, 0x04004000, 0x04104010, 0x00100000,
 166         0x04100000, 0x04000010, 0x00104000, 0x00004010, 0x04004010,
 167         0x04100000, 0x00000010, 0x04104000, 0x00104010, 0x00000000,
 168         0x04000000, 0x04100010, 0x00004000, 0x00104010,
 169     };
 170 
 171     private static final int[] permRight0 = {
 172         0x00000000, 0x40000000, 0x00400000, 0x40400000, 0x00004000,
 173         0x40004000, 0x00404000, 0x40404000, 0x00000040, 0x40000040,
 174         0x00400040, 0x40400040, 0x00004040, 0x40004040, 0x00404040,
 175         0x40404040,
 176     };
 177 
 178     private static final int[] permLeft1 = {
 179         0x00000000, 0x40000000, 0x00400000, 0x40400000, 0x00004000,
 180         0x40004000, 0x00404000, 0x40404000, 0x00000040, 0x40000040,
 181         0x00400040, 0x40400040, 0x00004040, 0x40004040, 0x00404040,
 182         0x40404040,
 183     };
 184 
 185     private static final int[] permRight2 = {
 186         0x00000000, 0x10000000, 0x00100000, 0x10100000, 0x00001000,
 187         0x10001000, 0x00101000, 0x10101000, 0x00000010, 0x10000010,
 188         0x00100010, 0x10100010, 0x00001010, 0x10001010, 0x00101010,
 189         0x10101010,
 190     };
 191 
 192     private static final int[] permLeft3 = {
 193         0x00000000, 0x10000000, 0x00100000, 0x10100000, 0x00001000,
 194         0x10001000, 0x00101000, 0x10101000, 0x00000010, 0x10000010,
 195         0x00100010, 0x10100010, 0x00001010, 0x10001010, 0x00101010,
 196         0x10101010,
 197     };
 198 
 199     private static final int[] permRight4 = {
 200         0x00000000, 0x04000000, 0x00040000, 0x04040000, 0x00000400,
 201         0x04000400, 0x00040400, 0x04040400, 0x00000004, 0x04000004,
 202         0x00040004, 0x04040004, 0x00000404, 0x04000404, 0x00040404,
 203         0x04040404,
 204     };
 205 
 206     private static final int[] permLeft5 = {
 207         0x00000000, 0x04000000, 0x00040000, 0x04040000, 0x00000400,
 208         0x04000400, 0x00040400, 0x04040400, 0x00000004, 0x04000004,
 209         0x00040004, 0x04040004, 0x00000404, 0x04000404, 0x00040404,
 210         0x04040404,
 211     };
 212 
 213     private static final int[] permRight6 = {
 214         0x00000000, 0x01000000, 0x00010000, 0x01010000, 0x00000100,
 215         0x01000100, 0x00010100, 0x01010100, 0x00000001, 0x01000001,
 216         0x00010001, 0x01010001, 0x00000101, 0x01000101, 0x00010101,
 217         0x01010101,
 218     };
 219 
 220     private static final int[] permLeft7 = {
 221         0x00000000, 0x01000000, 0x00010000, 0x01010000, 0x00000100,
 222         0x01000100, 0x00010100, 0x01010100, 0x00000001, 0x01000001,
 223         0x00010001, 0x01010001, 0x00000101, 0x01000101, 0x00010101,
 224         0x01010101,
 225     };
 226 
 227     private static final int[] permRight8 = {
 228         0x00000000, 0x80000000, 0x00800000, 0x80800000, 0x00008000,
 229         0x80008000, 0x00808000, 0x80808000, 0x00000080, 0x80000080,
 230         0x00800080, 0x80800080, 0x00008080, 0x80008080, 0x00808080,
 231         0x80808080,
 232     };
 233 
 234     private static final int[] permLeft9 = {
 235         0x00000000, 0x80000000, 0x00800000, 0x80800000, 0x00008000,
 236         0x80008000, 0x00808000, 0x80808000, 0x00000080, 0x80000080,
 237         0x00800080, 0x80800080, 0x00008080, 0x80008080, 0x00808080,
 238         0x80808080,
 239     };
 240 
 241     private static final int[] permRightA = {
 242         0x00000000, 0x20000000, 0x00200000, 0x20200000, 0x00002000,
 243         0x20002000, 0x00202000, 0x20202000, 0x00000020, 0x20000020,
 244         0x00200020, 0x20200020, 0x00002020, 0x20002020, 0x00202020,
 245         0x20202020,
 246     };
 247 
 248     private static final int[] permLeftB = {
 249         0x00000000, 0x20000000, 0x00200000, 0x20200000, 0x00002000,
 250         0x20002000, 0x00202000, 0x20202000, 0x00000020, 0x20000020,
 251         0x00200020, 0x20200020, 0x00002020, 0x20002020, 0x00202020,
 252         0x20202020,
 253     };
 254 
 255     private static final int[] permRightC = {
 256         0x00000000, 0x08000000, 0x00080000, 0x08080000, 0x00000800,
 257         0x08000800, 0x00080800, 0x08080800, 0x00000008, 0x08000008,
 258         0x00080008, 0x08080008, 0x00000808, 0x08000808, 0x00080808,
 259         0x08080808,
 260     };
 261 
 262     private static final int[] permLeftD = {
 263         0x00000000, 0x08000000, 0x00080000, 0x08080000, 0x00000800,
 264         0x08000800, 0x00080800, 0x08080800, 0x00000008, 0x08000008,
 265         0x00080008, 0x08080008, 0x00000808, 0x08000808, 0x00080808,
 266         0x08080808,
 267     };
 268 
 269     private static final int[] permRightE = {
 270         0x00000000, 0x02000000, 0x00020000, 0x02020000, 0x00000200,
 271         0x02000200, 0x00020200, 0x02020200, 0x00000002, 0x02000002,
 272         0x00020002, 0x02020002, 0x00000202, 0x02000202, 0x00020202,
 273         0x02020202,
 274     };
 275 
 276     private static final int[] permLeftF = {
 277         0x00000000, 0x02000000, 0x00020000, 0x02020000, 0x00000200,
 278         0x02000200, 0x00020200, 0x02020200, 0x00000002, 0x02000002,
 279         0x00020002, 0x02020002, 0x00000202, 0x02000202, 0x00020202,
 280         0x02020202,
 281     };
 282 
 283     /*
 284      *        Initial Permutation
 285      */
 286     private static final int[] initPermLeft0 = {
 287        0x00000000, 0x00008000, 0x00000000, 0x00008000, 0x00000080,
 288        0x00008080, 0x00000080, 0x00008080, 0x00000000, 0x00008000,
 289        0x00000000, 0x00008000, 0x00000080, 0x00008080, 0x00000080,
 290        0x00008080,
 291     };
 292 
 293     private static final int[] initPermRight0 = {
 294        0x00000000, 0x00000000, 0x00008000, 0x00008000, 0x00000000,
 295        0x00000000, 0x00008000, 0x00008000, 0x00000080, 0x00000080,
 296        0x00008080, 0x00008080, 0x00000080, 0x00000080, 0x00008080,
 297        0x00008080,
 298     };
 299 
 300     private static final int[] initPermLeft1 = {
 301        0x00000000, 0x80000000, 0x00000000, 0x80000000, 0x00800000,
 302        0x80800000, 0x00800000, 0x80800000, 0x00000000, 0x80000000,
 303        0x00000000, 0x80000000, 0x00800000, 0x80800000, 0x00800000,
 304        0x80800000,
 305     };
 306 
 307     private static final int[] initPermRight1 = {
 308        0x00000000, 0x00000000, 0x80000000, 0x80000000, 0x00000000,
 309        0x00000000, 0x80000000, 0x80000000, 0x00800000, 0x00800000,
 310        0x80800000, 0x80800000, 0x00800000, 0x00800000, 0x80800000,
 311        0x80800000,
 312     };
 313 
 314     private static final int[] initPermLeft2 = {
 315        0x00000000, 0x00004000, 0x00000000, 0x00004000, 0x00000040,
 316        0x00004040, 0x00000040, 0x00004040, 0x00000000, 0x00004000,
 317        0x00000000, 0x00004000, 0x00000040, 0x00004040, 0x00000040,
 318        0x00004040,
 319     };
 320 
 321     private static final int[] initPermRight2 = {
 322        0x00000000, 0x00000000, 0x00004000, 0x00004000, 0x00000000,
 323        0x00000000, 0x00004000, 0x00004000, 0x00000040, 0x00000040,
 324        0x00004040, 0x00004040, 0x00000040, 0x00000040, 0x00004040,
 325        0x00004040,
 326     };
 327 
 328     private static final int[] initPermLeft3 = {
 329        0x00000000, 0x40000000, 0x00000000, 0x40000000, 0x00400000,
 330        0x40400000, 0x00400000, 0x40400000, 0x00000000, 0x40000000,
 331        0x00000000, 0x40000000, 0x00400000, 0x40400000, 0x00400000,
 332        0x40400000,
 333     };
 334 
 335     private static final int[] initPermRight3 = {
 336        0x00000000, 0x00000000, 0x40000000, 0x40000000, 0x00000000,
 337        0x00000000, 0x40000000, 0x40000000, 0x00400000, 0x00400000,
 338        0x40400000, 0x40400000, 0x00400000, 0x00400000, 0x40400000,
 339        0x40400000,
 340     };
 341 
 342     private static final int[] initPermLeft4 = {
 343        0x00000000, 0x00002000, 0x00000000, 0x00002000, 0x00000020,
 344        0x00002020, 0x00000020, 0x00002020, 0x00000000, 0x00002000,
 345        0x00000000, 0x00002000, 0x00000020, 0x00002020, 0x00000020,
 346        0x00002020,
 347     };
 348 
 349     private static final int[] initPermRight4 = {
 350        0x00000000, 0x00000000, 0x00002000, 0x00002000, 0x00000000,
 351        0x00000000, 0x00002000, 0x00002000, 0x00000020, 0x00000020,
 352        0x00002020, 0x00002020, 0x00000020, 0x00000020, 0x00002020,
 353        0x00002020,
 354     };
 355 
 356     private static final int[] initPermLeft5 = {
 357        0x00000000, 0x20000000, 0x00000000, 0x20000000, 0x00200000,
 358        0x20200000, 0x00200000, 0x20200000, 0x00000000, 0x20000000,
 359        0x00000000, 0x20000000, 0x00200000, 0x20200000, 0x00200000,
 360        0x20200000,
 361     };
 362 
 363     private static final int[] initPermRight5 = {
 364        0x00000000, 0x00000000, 0x20000000, 0x20000000, 0x00000000,
 365        0x00000000, 0x20000000, 0x20000000, 0x00200000, 0x00200000,
 366        0x20200000, 0x20200000, 0x00200000, 0x00200000, 0x20200000,
 367        0x20200000,
 368     };
 369 
 370     private static final int[] initPermLeft6 = {
 371        0x00000000, 0x00001000, 0x00000000, 0x00001000, 0x00000010,
 372        0x00001010, 0x00000010, 0x00001010, 0x00000000, 0x00001000,
 373        0x00000000, 0x00001000, 0x00000010, 0x00001010, 0x00000010,
 374        0x00001010,
 375     };
 376 
 377     private static final int[] initPermRight6 = {
 378        0x00000000, 0x00000000, 0x00001000, 0x00001000, 0x00000000,
 379        0x00000000, 0x00001000, 0x00001000, 0x00000010, 0x00000010,
 380        0x00001010, 0x00001010, 0x00000010, 0x00000010, 0x00001010,
 381        0x00001010,
 382     };
 383 
 384     private static final int[] initPermLeft7 = {
 385        0x00000000, 0x10000000, 0x00000000, 0x10000000, 0x00100000,
 386        0x10100000, 0x00100000, 0x10100000, 0x00000000, 0x10000000,
 387        0x00000000, 0x10000000, 0x00100000, 0x10100000, 0x00100000,
 388        0x10100000,
 389     };
 390 
 391     private static final int[] initPermRight7 = {
 392        0x00000000, 0x00000000, 0x10000000, 0x10000000, 0x00000000,
 393        0x00000000, 0x10000000, 0x10000000, 0x00100000, 0x00100000,
 394        0x10100000, 0x10100000, 0x00100000, 0x00100000, 0x10100000,
 395        0x10100000,
 396     };
 397 
 398     private static final int[] initPermLeft8 = {
 399        0x00000000, 0x00000800, 0x00000000, 0x00000800, 0x00000008,
 400        0x00000808, 0x00000008, 0x00000808, 0x00000000, 0x00000800,
 401        0x00000000, 0x00000800, 0x00000008, 0x00000808, 0x00000008,
 402        0x00000808,
 403     };
 404 
 405     private static final int[] initPermRight8 = {
 406        0x00000000, 0x00000000, 0x00000800, 0x00000800, 0x00000000,
 407        0x00000000, 0x00000800, 0x00000800, 0x00000008, 0x00000008,
 408        0x00000808, 0x00000808, 0x00000008, 0x00000008, 0x00000808,
 409        0x00000808,
 410     };
 411 
 412     private static final int[] initPermLeft9 = {
 413        0x00000000, 0x08000000, 0x00000000, 0x08000000, 0x00080000,
 414        0x08080000, 0x00080000, 0x08080000, 0x00000000, 0x08000000,
 415        0x00000000, 0x08000000, 0x00080000, 0x08080000, 0x00080000,
 416        0x08080000,
 417     };
 418 
 419     private static final int[] initPermRight9 = {
 420        0x00000000, 0x00000000, 0x08000000, 0x08000000, 0x00000000,
 421        0x00000000, 0x08000000, 0x08000000, 0x00080000, 0x00080000,
 422        0x08080000, 0x08080000, 0x00080000, 0x00080000, 0x08080000,
 423        0x08080000,
 424     };
 425 
 426     private static final int[] initPermLeftA = {
 427        0x00000000, 0x00000400, 0x00000000, 0x00000400, 0x00000004,
 428        0x00000404, 0x00000004, 0x00000404, 0x00000000, 0x00000400,
 429        0x00000000, 0x00000400, 0x00000004, 0x00000404, 0x00000004,
 430        0x00000404,
 431     };
 432 
 433     private static final int[] initPermRightA = {
 434        0x00000000, 0x00000000, 0x00000400, 0x00000400, 0x00000000,
 435        0x00000000, 0x00000400, 0x00000400, 0x00000004, 0x00000004,
 436        0x00000404, 0x00000404, 0x00000004, 0x00000004, 0x00000404,
 437        0x00000404,
 438     };
 439 
 440     private static final int[] initPermLeftB = {
 441        0x00000000, 0x04000000, 0x00000000, 0x04000000, 0x00040000,
 442        0x04040000, 0x00040000, 0x04040000, 0x00000000, 0x04000000,
 443        0x00000000, 0x04000000, 0x00040000, 0x04040000, 0x00040000,
 444        0x04040000,
 445     };
 446 
 447     private static final int[] initPermRightB = {
 448        0x00000000, 0x00000000, 0x04000000, 0x04000000, 0x00000000,
 449        0x00000000, 0x04000000, 0x04000000, 0x00040000, 0x00040000,
 450        0x04040000, 0x04040000, 0x00040000, 0x00040000, 0x04040000,
 451        0x04040000,
 452     };
 453 
 454     private static final int[] initPermLeftC = {
 455        0x00000000, 0x00000200, 0x00000000, 0x00000200, 0x00000002,
 456        0x00000202, 0x00000002, 0x00000202, 0x00000000, 0x00000200,
 457        0x00000000, 0x00000200, 0x00000002, 0x00000202, 0x00000002,
 458        0x00000202,
 459     };
 460 
 461     private static final int[] initPermRightC = {
 462        0x00000000, 0x00000000, 0x00000200, 0x00000200, 0x00000000,
 463        0x00000000, 0x00000200, 0x00000200, 0x00000002, 0x00000002,
 464        0x00000202, 0x00000202, 0x00000002, 0x00000002, 0x00000202,
 465        0x00000202,
 466     };
 467 
 468     private static final int[] initPermLeftD = {
 469        0x00000000, 0x02000000, 0x00000000, 0x02000000, 0x00020000,
 470        0x02020000, 0x00020000, 0x02020000, 0x00000000, 0x02000000,
 471        0x00000000, 0x02000000, 0x00020000, 0x02020000, 0x00020000,
 472        0x02020000,
 473     };
 474 
 475     private static final int[] initPermRightD = {
 476        0x00000000, 0x00000000, 0x02000000, 0x02000000, 0x00000000,
 477        0x00000000, 0x02000000, 0x02000000, 0x00020000, 0x00020000,
 478        0x02020000, 0x02020000, 0x00020000, 0x00020000, 0x02020000,
 479        0x02020000,
 480     };
 481 
 482     private static final int[] initPermLeftE = {
 483        0x00000000, 0x00000100, 0x00000000, 0x00000100, 0x00000001,
 484        0x00000101, 0x00000001, 0x00000101, 0x00000000, 0x00000100,
 485        0x00000000, 0x00000100, 0x00000001, 0x00000101, 0x00000001,
 486        0x00000101,
 487     };
 488 
 489     private static final int[] initPermRightE = {
 490        0x00000000, 0x00000000, 0x00000100, 0x00000100, 0x00000000,
 491        0x00000000, 0x00000100, 0x00000100, 0x00000001, 0x00000001,
 492        0x00000101, 0x00000101, 0x00000001, 0x00000001, 0x00000101,
 493        0x00000101,
 494     };
 495 
 496     private static final int[] initPermLeftF = {
 497        0x00000000, 0x01000000, 0x00000000, 0x01000000, 0x00010000,
 498        0x01010000, 0x00010000, 0x01010000, 0x00000000, 0x01000000,
 499        0x00000000, 0x01000000, 0x00010000, 0x01010000, 0x00010000,
 500        0x01010000,
 501     };
 502 
 503     private static final int[] initPermRightF = {
 504        0x00000000, 0x00000000, 0x01000000, 0x01000000, 0x00000000,
 505        0x00000000, 0x01000000, 0x01000000, 0x00010000, 0x00010000,
 506        0x01010000, 0x01010000, 0x00010000, 0x00010000, 0x01010000,
 507        0x01010000,
 508     };
 509 
 510     /*
 511      * the encryption key array after expansion and permutation
 512      */
 513     byte[] expandedKey = null;
 514 
 515     /*
 516      * Are we encrypting or decrypting?
 517      */
 518     boolean decrypting = false;
 519 
 520     /**
 521      * Returns this cipher's block size.
 522      *
 523      * @return this cipher's block size
 524      */
 525     int getBlockSize() {
 526         return DES_BLOCK_SIZE;
 527     }
 528 
 529     void init(boolean decrypting, String algorithm, byte[] rawKey)
 530             throws InvalidKeyException {
 531         this.decrypting = decrypting;
 532         if (!algorithm.equalsIgnoreCase("DES")) {
 533             throw new InvalidKeyException("Wrong algorithm: DES required");
 534         }
 535         if (rawKey.length != DES_BLOCK_SIZE) {
 536             throw new InvalidKeyException("Wrong key size");
 537         }
 538         expandKey(rawKey);
 539     }
 540 
 541     /**
 542      * Performs encryption operation.
 543      *
 544      * <p>The input plain text <code>plain</code>, starting at
 545      * <code>plainOffset</code> and ending at
 546      * <code>(plainOffset + len - 1)</code>, is encrypted.
 547      * The result is stored in <code>cipher</code>, starting at
 548      * <code>cipherOffset</code>.
 549      *
 550      * <p>The subclass that implements Cipher should ensure that
 551      * <code>init</code> has been called before this method is called.
 552      *
 553      * @param plain the buffer with the input data to be encrypted
 554      * @param plainOffset the offset in <code>plain</code>
 555      * @param plainLen the length of the input data
 556      * @param cipher the buffer for the result
 557      * @param cipherOffset the offset in <code>cipher</code>
 558      *
 559      * @exception IllegalBlockSizeException if the input length is different
 560      * from the cipher's block size
 561      */
 562     void encryptBlock(byte[] plain, int plainOffset,
 563                  byte[] cipher, int cipherOffset)
 564     {
 565         cipherBlock(plain, plainOffset, cipher, cipherOffset);
 566     }
 567 
 568     /**
 569      * Performs decryption operation.
 570      *
 571      * <p>The input cipher text <code>cipher</code>, starting at
 572      * <code>cipherOffset</code> and ending at
 573      * <code>(cipherOffset + len - 1)</code>, is decrypted.
 574      * The result is stored in <code>plain</code>, starting at
 575      * <code>plainOffset</code>.
 576      *
 577      * <p>The subclass that implements Cipher should ensure that
 578      * <code>init</code> has been called before this method is called.
 579      *
 580      * @param cipher the buffer with the input data to be decrypted
 581      * @param cipherOffset the offset in <code>cipherOffset</code>
 582      * @param cipherLen the length of the input data
 583      * @param plain the buffer for the result
 584      * @param plainOffset the offset in <code>plain</code>
 585      *
 586      * @exception IllegalBlockSizeException if the input length is different
 587      * from the cipher's block size
 588      */
 589     void decryptBlock(byte[] cipher, int cipherOffset,
 590                  byte[] plain, int plainOffset)
 591     {
 592         cipherBlock(cipher, cipherOffset, plain, plainOffset);
 593     }
 594 
 595 
 596     void cipherBlock(byte[] in, int inOffset, byte[] out, int outOffset) {
 597         byte[] key;
 598         int temp;
 599         int i, j;
 600         int offset;
 601         int left, right;
 602 
 603         left = initialPermutationLeft(in, inOffset);
 604         right = initialPermutationRight(in, inOffset);
 605 
 606         key = expandedKey;
 607 
 608         if (decrypting) {
 609             offset = 16 - DES_BLOCK_SIZE;
 610             j = 128 - DES_BLOCK_SIZE;
 611 
 612         } else {
 613             offset = 0 - DES_BLOCK_SIZE;
 614             j = 0;
 615         }
 616 
 617         for (i = 0; i < 16; i++) {
 618             // make the first and last bit adjacent
 619             // move the first bit to the last
 620             temp = (right << 1) | ((right >> 31) & 1);
 621 
 622             // mangler function:
 623             // every 6 bit is fed into the sbox, which
 624             // produces 4-bit output
 625             left ^= s0p[(temp & 0x3f) ^ key[j+0]]
 626                 ^ s1p[((temp >>  4) & 0x3f) ^ key[j+1]]
 627                 ^ s2p[((temp >>  8) & 0x3f) ^ key[j+2]]
 628                 ^ s3p[((temp >> 12) & 0x3f) ^ key[j+3]]
 629                 ^ s4p[((temp >> 16) & 0x3f) ^ key[j+4]]
 630                 ^ s5p[((temp >> 20) & 0x3f) ^ key[j+5]]
 631                 ^ s6p[((temp >> 24) & 0x3f) ^ key[j+6]];
 632 
 633             // make the last sbox input the last bit from right[0]
 634             temp = ((right & 1) << 5) | ((right >> 27) & 0x1f);
 635             left ^= s7p[temp ^ key[j+7]];
 636             temp = left;
 637             left = right;
 638             right = temp;
 639             j -= offset;
 640         }
 641 
 642         temp = left;
 643         left = right;
 644         right = temp;
 645         perm(left, right, out, outOffset);
 646     }
 647 
 648     private static void perm(int left, int right,
 649                              byte[] out, int offset) {
 650         int low, high, temp;
 651 
 652         temp = left;
 653         high = permRight0[temp & 0x0000000f];
 654         temp >>= 4;
 655         low  = permLeft1[temp & 0x0000000f];
 656         temp >>= 4;
 657         high |= permRight2[temp & 0x0000000f];
 658         temp >>= 4;
 659         low  |= permLeft3[temp & 0x0000000f];
 660         temp >>= 4;
 661         high |= permRight4[temp & 0x0000000f];
 662         temp >>= 4;
 663         low  |= permLeft5[temp & 0x0000000f];
 664         temp >>= 4;
 665         high |= permRight6[temp & 0x0000000f];
 666         temp >>= 4;
 667         low  |= permLeft7[temp & 0x0000000f];
 668 
 669         temp = right;
 670         high |= permRight8[temp & 0x0000000f];
 671         temp >>= 4;
 672         low  |= permLeft9[temp & 0x0000000f];
 673         temp >>= 4;
 674         high |= permRightA[temp & 0x0000000f];
 675         temp >>= 4;
 676         low  |= permLeftB[temp & 0x0000000f];
 677         temp >>= 4;
 678         high |= permRightC[temp & 0x0000000f];
 679         temp >>= 4;
 680         low  |= permLeftD[temp & 0x0000000f];
 681         temp >>= 4;
 682         high |= permRightE[temp & 0x0000000f];
 683         temp >>= 4;
 684         low  |= permLeftF[temp & 0x0000000f];
 685 
 686 
 687         out[offset + 0] = (byte)low;
 688         out[offset + 1] = (byte)(low >> 8);
 689         out[offset + 2] = (byte)(low >> 16);
 690         out[offset + 3] = (byte)(low >> 24);
 691         out[offset + 4] = (byte)high;
 692         out[offset + 5] = (byte)(high >> 8);
 693         out[offset + 6] = (byte)(high >> 16);
 694         out[offset + 7] = (byte)(high >> 24);
 695 
 696     }
 697 
 698     private static int initialPermutationLeft(byte[] block, int offset) {
 699         int l;
 700 
 701         l  = initPermLeft1[block[offset] & 0xf];
 702         l |= initPermLeft0[(block[offset] >> 4) & 0xf];
 703         l |= initPermLeft3[block[offset + 1] & 0xf];
 704         l |= initPermLeft2[(block[offset + 1] >> 4) & 0xf];
 705         l |= initPermLeft5[block[offset + 2] & 0xf];
 706         l |= initPermLeft4[(block[offset + 2] >> 4) & 0xf];
 707         l |= initPermLeft7[block[offset + 3] & 0xf];
 708         l |= initPermLeft6[(block[offset + 3] >> 4) & 0xf];
 709         l |= initPermLeft9[block[offset + 4] & 0xf];
 710         l |= initPermLeft8[(block[offset + 4] >> 4) & 0xf];
 711         l |= initPermLeftB[block[offset + 5] & 0xf];
 712         l |= initPermLeftA[(block[offset + 5] >> 4) & 0xf];
 713         l |= initPermLeftD[block[offset + 6] & 0xf];
 714         l |= initPermLeftC[(block[offset + 6] >> 4) & 0xf];
 715         l |= initPermLeftF[block[offset + 7] & 0xf];
 716         l |= initPermLeftE[(block[offset + 7] >> 4) & 0xf];
 717         return l;
 718     }
 719 
 720     private static int initialPermutationRight(byte[] block, int offset) {
 721         int l;
 722 
 723         l  = initPermRight1[block[offset] & 0xf];
 724         l |= initPermRight0[(block[offset] >> 4) & 0xf];
 725         l |= initPermRight3[block[offset + 1] & 0xf];
 726         l |= initPermRight2[(block[offset + 1] >> 4) & 0xf];
 727         l |= initPermRight5[block[offset + 2] & 0xf];
 728         l |= initPermRight4[(block[offset + 2] >> 4) & 0xf];
 729         l |= initPermRight7[block[offset + 3] & 0xf];
 730         l |= initPermRight6[(block[offset + 3] >> 4) & 0xf];
 731         l |= initPermRight9[block[offset + 4] & 0xf];
 732         l |= initPermRight8[(block[offset + 4] >> 4) & 0xf];
 733         l |= initPermRightB[block[offset + 5] & 0xf];
 734         l |= initPermRightA[(block[offset + 5] >> 4) & 0xf];
 735         l |= initPermRightD[block[offset + 6] & 0xf];
 736         l |= initPermRightC[(block[offset + 6] >> 4) & 0xf];
 737         l |= initPermRightF[block[offset + 7] & 0xf];
 738         l |= initPermRightE[(block[offset + 7] >> 4) & 0xf];
 739         return l;
 740     }
 741 
 742     void expandKey(byte[] key) {
 743         int octet;
 744         byte[] ek = new byte[128];
 745 
 746         octet = key[0];
 747         if ((octet & 0x80) != 0) {
 748             ek[  3] |=  2; ek[  9] |=  8; ek[ 18] |=  8;
 749             ek[ 27] |= 32; ek[ 33] |=  2; ek[ 42] |= 16;
 750             ek[ 48] |=  8; ek[ 65] |= 16; ek[ 74] |=  2;
 751             ek[ 80] |=  2; ek[ 89] |=  4; ek[ 99] |= 16;
 752             ek[104] |=  4; ek[122] |= 32;
 753         }
 754         if ((octet & 0x40) != 0) {
 755             ek[  1] |=  4; ek[  8] |=  1; ek[ 18] |=  4;
 756             ek[ 25] |= 32; ek[ 34] |= 32; ek[ 41] |=  8;
 757             ek[ 50] |=  8; ek[ 59] |= 32; ek[ 64] |= 16;
 758             ek[ 75] |=  4; ek[ 90] |=  1; ek[ 97] |= 16;
 759             ek[106] |=  2; ek[112] |=  2; ek[123] |=  1;
 760         }
 761         if ((octet & 0x20) != 0) {
 762             ek[  2] |=  1; ek[ 19] |=  8; ek[ 35] |=  1;
 763             ek[ 40] |=  1; ek[ 50] |=  4; ek[ 57] |= 32;
 764             ek[ 75] |=  2; ek[ 80] |= 32; ek[ 89] |=  1;
 765             ek[ 96] |= 16; ek[107] |=  4; ek[120] |=  8;
 766         }
 767         if ((octet & 0x10) != 0) {
 768             ek[  4] |= 32; ek[ 20] |=  2; ek[ 31] |=  4;
 769             ek[ 37] |= 32; ek[ 47] |=  1; ek[ 54] |=  1;
 770             ek[ 63] |=  2; ek[ 68] |=  1; ek[ 78] |=  4;
 771             ek[ 84] |=  8; ek[101] |= 16; ek[108] |=  4;
 772             ek[119] |= 16; ek[126] |=  8;
 773         }
 774         if ((octet & 0x8) != 0) {
 775             ek[  5] |=  4; ek[ 15] |=  4; ek[ 21] |= 32;
 776             ek[ 31] |=  1; ek[ 38] |=  1; ek[ 47] |=  2;
 777             ek[ 53] |=  2; ek[ 68] |=  8; ek[ 85] |= 16;
 778             ek[ 92] |=  4; ek[103] |= 16; ek[108] |= 32;
 779             ek[118] |= 32; ek[124] |=  2;
 780         }
 781         if ((octet & 0x4) != 0) {
 782             ek[ 15] |=  2; ek[ 21] |=  2; ek[ 39] |=  8;
 783             ek[ 46] |= 16; ek[ 55] |= 32; ek[ 61] |=  1;
 784             ek[ 71] |= 16; ek[ 76] |= 32; ek[ 86] |= 32;
 785             ek[ 93] |=  4; ek[102] |=  2; ek[108] |= 16;
 786             ek[117] |=  8; ek[126] |=  1;
 787         }
 788         if ((octet & 0x2) != 0) {
 789             ek[ 14] |= 16; ek[ 23] |= 32; ek[ 29] |=  1;
 790             ek[ 38] |=  8; ek[ 52] |=  2; ek[ 63] |=  4;
 791             ek[ 70] |=  2; ek[ 76] |= 16; ek[ 85] |=  8;
 792             ek[100] |=  1; ek[110] |=  4; ek[116] |=  8;
 793             ek[127] |=  8;
 794         }
 795         octet = key[1];
 796         if ((octet & 0x80) != 0) {
 797             ek[  1] |=  8; ek[  8] |= 32; ek[ 17] |=  1;
 798             ek[ 24] |= 16; ek[ 35] |=  4; ek[ 50] |=  1;
 799             ek[ 57] |= 16; ek[ 67] |=  8; ek[ 83] |=  1;
 800             ek[ 88] |=  1; ek[ 98] |=  4; ek[105] |= 32;
 801             ek[114] |= 32; ek[123] |=  2;
 802         }
 803         if ((octet & 0x40) != 0) {
 804             ek[  0] |=  1; ek[ 11] |= 16; ek[ 16] |=  4;
 805             ek[ 35] |=  2; ek[ 40] |= 32; ek[ 49] |=  1;
 806             ek[ 56] |= 16; ek[ 65] |=  2; ek[ 74] |= 16;
 807             ek[ 80] |=  8; ek[ 99] |=  8; ek[115] |=  1;
 808             ek[121] |=  4;
 809         }
 810         if ((octet & 0x20) != 0) {
 811             ek[  9] |= 16; ek[ 18] |=  2; ek[ 24] |=  2;
 812             ek[ 33] |=  4; ek[ 43] |= 16; ek[ 48] |=  4;
 813             ek[ 66] |= 32; ek[ 73] |=  8; ek[ 82] |=  8;
 814             ek[ 91] |= 32; ek[ 97] |=  2; ek[106] |= 16;
 815             ek[112] |=  8; ek[122] |=  1;
 816         }
 817         if ((octet & 0x10) != 0) {
 818             ek[ 14] |= 32; ek[ 21] |=  4; ek[ 30] |=  2;
 819             ek[ 36] |= 16; ek[ 45] |=  8; ek[ 60] |=  1;
 820             ek[ 69] |=  2; ek[ 87] |=  8; ek[ 94] |= 16;
 821             ek[103] |= 32; ek[109] |=  1; ek[118] |=  8;
 822             ek[124] |= 32;
 823         }
 824         if ((octet & 0x8) != 0) {
 825             ek[  7] |=  4; ek[ 14] |=  2; ek[ 20] |= 16;
 826             ek[ 29] |=  8; ek[ 44] |=  1; ek[ 54] |=  4;
 827             ek[ 60] |=  8; ek[ 71] |=  8; ek[ 78] |= 16;
 828             ek[ 87] |= 32; ek[ 93] |=  1; ek[102] |=  8;
 829             ek[116] |=  2; ek[125] |=  4;
 830         }
 831         if ((octet & 0x4) != 0) {
 832             ek[  7] |=  2; ek[ 12] |=  1; ek[ 22] |=  4;
 833             ek[ 28] |=  8; ek[ 45] |= 16; ek[ 52] |=  4;
 834             ek[ 63] |= 16; ek[ 70] |=  8; ek[ 84] |=  2;
 835             ek[ 95] |=  4; ek[101] |= 32; ek[111] |=  1;
 836             ek[118] |=  1;
 837         }
 838         if ((octet & 0x2) != 0) {
 839             ek[  6] |= 16; ek[ 13] |= 16; ek[ 20] |=  4;
 840             ek[ 31] |= 16; ek[ 36] |= 32; ek[ 46] |= 32;
 841             ek[ 53] |=  4; ek[ 62] |=  2; ek[ 69] |= 32;
 842             ek[ 79] |=  1; ek[ 86] |=  1; ek[ 95] |=  2;
 843             ek[101] |=  2; ek[119] |=  8;
 844         }
 845         octet = key[2];
 846         if ((octet & 0x80) != 0) {
 847             ek[  0] |= 32; ek[ 10] |=  8; ek[ 19] |= 32;
 848             ek[ 25] |=  2; ek[ 34] |= 16; ek[ 40] |=  8;
 849             ek[ 59] |=  8; ek[ 66] |=  2; ek[ 72] |=  2;
 850             ek[ 81] |=  4; ek[ 91] |= 16; ek[ 96] |=  4;
 851             ek[115] |=  2; ek[121] |=  8;
 852         }
 853         if ((octet & 0x40) != 0) {
 854             ek[  3] |= 16; ek[ 10] |=  4; ek[ 17] |= 32;
 855             ek[ 26] |= 32; ek[ 33] |=  8; ek[ 42] |=  8;
 856             ek[ 51] |= 32; ek[ 57] |=  2; ek[ 67] |=  4;
 857             ek[ 82] |=  1; ek[ 89] |= 16; ek[ 98] |=  2;
 858             ek[104] |=  2; ek[113] |=  4; ek[120] |=  1;
 859         }
 860         if ((octet & 0x20) != 0) {
 861             ek[  1] |= 16; ek[ 11] |=  8; ek[ 27] |=  1;
 862             ek[ 32] |=  1; ek[ 42] |=  4; ek[ 49] |= 32;
 863             ek[ 58] |= 32; ek[ 67] |=  2; ek[ 72] |= 32;
 864             ek[ 81] |=  1; ek[ 88] |= 16; ek[ 99] |=  4;
 865             ek[114] |=  1;
 866         }
 867         if ((octet & 0x10) != 0) {
 868             ek[  6] |= 32; ek[ 12] |=  2; ek[ 23] |=  4;
 869             ek[ 29] |= 32; ek[ 39] |=  1; ek[ 46] |=  1;
 870             ek[ 55] |=  2; ek[ 61] |=  2; ek[ 70] |=  4;
 871             ek[ 76] |=  8; ek[ 93] |= 16; ek[100] |=  4;
 872             ek[111] |= 16; ek[116] |= 32;
 873         }
 874         if ((octet & 0x8) != 0) {
 875             ek[  6] |=  2; ek[ 13] |= 32; ek[ 23] |=  1;
 876             ek[ 30] |=  1; ek[ 39] |=  2; ek[ 45] |=  2;
 877             ek[ 63] |=  8; ek[ 77] |= 16; ek[ 84] |=  4;
 878             ek[ 95] |= 16; ek[100] |= 32; ek[110] |= 32;
 879             ek[117] |=  4; ek[127] |=  4;
 880         }
 881         if ((octet & 0x4) != 0) {
 882             ek[  4] |=  1; ek[ 13] |=  2; ek[ 31] |=  8;
 883             ek[ 38] |= 16; ek[ 47] |= 32; ek[ 53] |=  1;
 884             ek[ 62] |=  8; ek[ 68] |= 32; ek[ 78] |= 32;
 885             ek[ 85] |=  4; ek[ 94] |=  2; ek[100] |= 16;
 886             ek[109] |=  8; ek[127] |=  2;
 887         }
 888         if ((octet & 0x2) != 0) {
 889             ek[  5] |= 16; ek[ 15] |= 32; ek[ 21] |=  1;
 890             ek[ 30] |=  8; ek[ 44] |=  2; ek[ 55] |=  4;
 891             ek[ 61] |= 32; ek[ 68] |= 16; ek[ 77] |=  8;
 892             ek[ 92] |=  1; ek[102] |=  4; ek[108] |=  8;
 893             ek[126] |= 16;
 894         }
 895         octet = key[3];
 896         if ((octet & 0x80) != 0) {
 897             ek[  2] |=  8; ek[  9] |=  1; ek[ 16] |= 16;
 898             ek[ 27] |=  4; ek[ 42] |=  1; ek[ 49] |= 16;
 899             ek[ 58] |=  2; ek[ 75] |=  1; ek[ 80] |=  1;
 900             ek[ 90] |=  4; ek[ 97] |= 32; ek[106] |= 32;
 901             ek[113] |=  8; ek[120] |= 32;
 902         }
 903         if ((octet & 0x40) != 0) {
 904             ek[  2] |=  4; ek[  8] |=  4; ek[ 27] |=  2;
 905             ek[ 32] |= 32; ek[ 41] |=  1; ek[ 48] |= 16;
 906             ek[ 59] |=  4; ek[ 66] |= 16; ek[ 72] |=  8;
 907             ek[ 91] |=  8; ek[107] |=  1; ek[112] |=  1;
 908             ek[123] |= 16;
 909         }
 910         if ((octet & 0x20) != 0) {
 911             ek[  3] |=  8; ek[ 10] |=  2; ek[ 16] |=  2;
 912             ek[ 25] |=  4; ek[ 35] |= 16; ek[ 40] |=  4;
 913             ek[ 59] |=  2; ek[ 65] |=  8; ek[ 74] |=  8;
 914             ek[ 83] |= 32; ek[ 89] |=  2; ek[ 98] |= 16;
 915             ek[104] |=  8; ek[121] |= 16;
 916         }
 917         if ((octet & 0x10) != 0) {
 918             ek[  4] |=  2; ek[ 13] |=  4; ek[ 22] |=  2;
 919             ek[ 28] |= 16; ek[ 37] |=  8; ek[ 52] |=  1;
 920             ek[ 62] |=  4; ek[ 79] |=  8; ek[ 86] |= 16;
 921             ek[ 95] |= 32; ek[101] |=  1; ek[110] |=  8;
 922             ek[126] |= 32;
 923         }
 924         if ((octet & 0x8) != 0) {
 925             ek[  5] |= 32; ek[ 12] |= 16; ek[ 21] |=  8;
 926             ek[ 36] |=  1; ek[ 46] |=  4; ek[ 52] |=  8;
 927             ek[ 70] |= 16; ek[ 79] |= 32; ek[ 85] |=  1;
 928             ek[ 94] |=  8; ek[108] |=  2; ek[119] |=  4;
 929             ek[126] |=  2;
 930         }
 931         if ((octet & 0x4) != 0) {
 932             ek[  5] |=  2; ek[ 14] |=  4; ek[ 20] |=  8;
 933             ek[ 37] |= 16; ek[ 44] |=  4; ek[ 55] |= 16;
 934             ek[ 60] |= 32; ek[ 76] |=  2; ek[ 87] |=  4;
 935             ek[ 93] |= 32; ek[103] |=  1; ek[110] |=  1;
 936             ek[119] |=  2; ek[124] |=  1;
 937         }
 938         if ((octet & 0x2) != 0) {
 939             ek[  7] |= 32; ek[ 12] |=  4; ek[ 23] |= 16;
 940             ek[ 28] |= 32; ek[ 38] |= 32; ek[ 45] |=  4;
 941             ek[ 54] |=  2; ek[ 60] |= 16; ek[ 71] |=  1;
 942             ek[ 78] |=  1; ek[ 87] |=  2; ek[ 93] |=  2;
 943             ek[111] |=  8; ek[118] |= 16; ek[125] |= 16;
 944         }
 945         octet = key[4];
 946         if ((octet & 0x80) != 0) {
 947             ek[  1] |=  1; ek[ 11] |= 32; ek[ 17] |=  2;
 948             ek[ 26] |= 16; ek[ 32] |=  8; ek[ 51] |=  8;
 949             ek[ 64] |=  2; ek[ 73] |=  4; ek[ 83] |= 16;
 950             ek[ 88] |=  4; ek[107] |=  2; ek[112] |= 32;
 951             ek[122] |=  8;
 952         }
 953         if ((octet & 0x40) != 0) {
 954             ek[  0] |=  4; ek[  9] |= 32; ek[ 18] |= 32;
 955             ek[ 25] |=  8; ek[ 34] |=  8; ek[ 43] |= 32;
 956             ek[ 49] |=  2; ek[ 58] |= 16; ek[ 74] |=  1;
 957             ek[ 81] |= 16; ek[ 90] |=  2; ek[ 96] |=  2;
 958             ek[105] |=  4; ek[115] |= 16; ek[122] |=  4;
 959         }
 960         if ((octet & 0x20) != 0) {
 961             ek[  2] |=  2; ek[ 19] |=  1; ek[ 24] |=  1;
 962             ek[ 34] |=  4; ek[ 41] |= 32; ek[ 50] |= 32;
 963             ek[ 57] |=  8; ek[ 64] |= 32; ek[ 73] |=  1;
 964             ek[ 80] |= 16; ek[ 91] |=  4; ek[106] |=  1;
 965             ek[113] |= 16; ek[123] |=  8;
 966         }
 967         if ((octet & 0x10) != 0) {
 968             ek[  3] |=  4; ek[ 10] |= 16; ek[ 16] |=  8;
 969             ek[ 35] |=  8; ek[ 51] |=  1; ek[ 56] |=  1;
 970             ek[ 67] |= 16; ek[ 72] |=  4; ek[ 91] |=  2;
 971             ek[ 96] |= 32; ek[105] |=  1; ek[112] |= 16;
 972             ek[121] |=  2;
 973         }
 974         if ((octet & 0x8) != 0) {
 975             ek[  4] |= 16; ek[ 15] |=  1; ek[ 22] |=  1;
 976             ek[ 31] |=  2; ek[ 37] |=  2; ek[ 55] |=  8;
 977             ek[ 62] |= 16; ek[ 69] |= 16; ek[ 76] |=  4;
 978             ek[ 87] |= 16; ek[ 92] |= 32; ek[102] |= 32;
 979             ek[109] |=  4; ek[118] |=  2; ek[125] |= 32;
 980         }
 981         if ((octet & 0x4) != 0) {
 982             ek[  6] |=  4; ek[ 23] |=  8; ek[ 30] |= 16;
 983             ek[ 39] |= 32; ek[ 45] |=  1; ek[ 54] |=  8;
 984             ek[ 70] |= 32; ek[ 77] |=  4; ek[ 86] |=  2;
 985             ek[ 92] |= 16; ek[101] |=  8; ek[116] |=  1;
 986             ek[125] |=  2;
 987         }
 988         if ((octet & 0x2) != 0) {
 989             ek[  4] |=  4; ek[ 13] |=  1; ek[ 22] |=  8;
 990             ek[ 36] |=  2; ek[ 47] |=  4; ek[ 53] |= 32;
 991             ek[ 63] |=  1; ek[ 69] |=  8; ek[ 84] |=  1;
 992             ek[ 94] |=  4; ek[100] |=  8; ek[117] |= 16;
 993             ek[127] |= 32;
 994         }
 995         octet = key[5];
 996         if ((octet & 0x80) != 0) {
 997             ek[  3] |= 32; ek[  8] |= 16; ek[ 19] |=  4;
 998             ek[ 34] |=  1; ek[ 41] |= 16; ek[ 50] |=  2;
 999             ek[ 56] |=  2; ek[ 67] |=  1; ek[ 72] |=  1;
1000             ek[ 82] |=  4; ek[ 89] |= 32; ek[ 98] |= 32;
1001             ek[105] |=  8; ek[114] |=  8; ek[121] |=  1;
1002         }
1003         if ((octet & 0x40) != 0) {
1004             ek[  1] |= 32; ek[ 19] |=  2; ek[ 24] |= 32;
1005             ek[ 33] |=  1; ek[ 40] |= 16; ek[ 51] |=  4;
1006             ek[ 64] |=  8; ek[ 83] |=  8; ek[ 99] |=  1;
1007             ek[104] |=  1; ek[114] |=  4; ek[120] |=  4;
1008         }
1009         if ((octet & 0x20) != 0) {
1010             ek[  8] |=  2; ek[ 17] |=  4; ek[ 27] |= 16;
1011             ek[ 32] |=  4; ek[ 51] |=  2; ek[ 56] |= 32;
1012             ek[ 66] |=  8; ek[ 75] |= 32; ek[ 81] |=  2;
1013             ek[ 90] |= 16; ek[ 96] |=  8; ek[115] |=  8;
1014             ek[122] |=  2;
1015         }
1016         if ((octet & 0x10) != 0) {
1017             ek[  2] |= 16; ek[ 18] |=  1; ek[ 25] |= 16;
1018             ek[ 34] |=  2; ek[ 40] |=  2; ek[ 49] |=  4;
1019             ek[ 59] |= 16; ek[ 66] |=  4; ek[ 73] |= 32;
1020             ek[ 82] |= 32; ek[ 89] |=  8; ek[ 98] |=  8;
1021             ek[107] |= 32; ek[113] |=  2; ek[123] |=  4;
1022         }
1023         if ((octet & 0x8) != 0) {
1024             ek[  7] |=  1; ek[ 13] |=  8; ek[ 28] |=  1;
1025             ek[ 38] |=  4; ek[ 44] |=  8; ek[ 61] |= 16;
1026             ek[ 71] |= 32; ek[ 77] |=  1; ek[ 86] |=  8;
1027             ek[100] |=  2; ek[111] |=  4; ek[117] |= 32;
1028             ek[124] |= 16;
1029         }
1030         if ((octet & 0x4) != 0) {
1031             ek[ 12] |=  8; ek[ 29] |= 16; ek[ 36] |=  4;
1032             ek[ 47] |= 16; ek[ 52] |= 32; ek[ 62] |= 32;
1033             ek[ 68] |=  2; ek[ 79] |=  4; ek[ 85] |= 32;
1034             ek[ 95] |=  1; ek[102] |=  1; ek[111] |=  2;
1035             ek[117] |=  2; ek[126] |=  4;
1036         }
1037         if ((octet & 0x2) != 0) {
1038             ek[  5] |=  1; ek[ 15] |= 16; ek[ 20] |= 32;
1039             ek[ 30] |= 32; ek[ 37] |=  4; ek[ 46] |=  2;
1040             ek[ 52] |= 16; ek[ 61] |=  8; ek[ 70] |=  1;
1041             ek[ 79] |=  2; ek[ 85] |=  2; ek[103] |=  8;
1042             ek[110] |= 16; ek[119] |= 32; ek[124] |=  4;
1043         }
1044         octet = key[6];
1045         if ((octet & 0x80) != 0) {
1046             ek[  0] |= 16; ek[  9] |=  2; ek[ 18] |= 16;
1047             ek[ 24] |=  8; ek[ 43] |=  8; ek[ 59] |=  1;
1048             ek[ 65] |=  4; ek[ 75] |= 16; ek[ 80] |=  4;
1049             ek[ 99] |=  2; ek[104] |= 32; ek[113] |=  1;
1050             ek[123] |= 32;
1051         }
1052         if ((octet & 0x40) != 0) {
1053             ek[ 10] |= 32; ek[ 17] |=  8; ek[ 26] |=  8;
1054             ek[ 35] |= 32; ek[ 41] |=  2; ek[ 50] |= 16;
1055             ek[ 56] |=  8; ek[ 66] |=  1; ek[ 73] |= 16;
1056             ek[ 82] |=  2; ek[ 88] |=  2; ek[ 97] |=  4;
1057             ek[107] |= 16; ek[112] |=  4; ek[121] |= 32;
1058         }
1059         if ((octet & 0x20) != 0) {
1060             ek[  0] |=  2; ek[ 11] |=  1; ek[ 16] |=  1;
1061             ek[ 26] |=  4; ek[ 33] |= 32; ek[ 42] |= 32;
1062             ek[ 49] |=  8; ek[ 58] |=  8; ek[ 65] |=  1;
1063             ek[ 72] |= 16; ek[ 83] |=  4; ek[ 98] |=  1;
1064             ek[105] |= 16; ek[114] |=  2;
1065         }
1066         if ((octet & 0x10) != 0) {
1067             ek[  8] |=  8; ek[ 27] |=  8; ek[ 43] |=  1;
1068             ek[ 48] |=  1; ek[ 58] |=  4; ek[ 64] |=  4;
1069             ek[ 83] |=  2; ek[ 88] |= 32; ek[ 97] |=  1;
1070             ek[104] |= 16; ek[115] |=  4; ek[122] |= 16;
1071         }
1072         if ((octet & 0x8) != 0) {
1073             ek[  5] |=  8; ek[ 14] |=  1; ek[ 23] |=  2;
1074             ek[ 29] |=  2; ek[ 47] |=  8; ek[ 54] |= 16;
1075             ek[ 63] |= 32; ek[ 68] |=  4; ek[ 79] |= 16;
1076             ek[ 84] |= 32; ek[ 94] |= 32; ek[101] |=  4;
1077             ek[110] |=  2; ek[116] |= 16; ek[127] |=  1;
1078         }
1079         if ((octet & 0x4) != 0) {
1080             ek[  4] |=  8; ek[ 15] |=  8; ek[ 22] |= 16;
1081             ek[ 31] |= 32; ek[ 37] |=  1; ek[ 46] |=  8;
1082             ek[ 60] |=  2; ek[ 69] |=  4; ek[ 78] |=  2;
1083             ek[ 84] |= 16; ek[ 93] |=  8; ek[108] |=  1;
1084             ek[118] |=  4;
1085         }
1086         if ((octet & 0x2) != 0) {
1087             ek[  7] |= 16; ek[ 14] |=  8; ek[ 28] |=  2;
1088             ek[ 39] |=  4; ek[ 45] |= 32; ek[ 55] |=  1;
1089             ek[ 62] |=  1; ek[ 76] |=  1; ek[ 86] |=  4;
1090             ek[ 92] |=  8; ek[109] |= 16; ek[116] |=  4;
1091             ek[125] |=  1;
1092         }
1093         octet = key[7];
1094         if ((octet & 0x80) != 0) {
1095             ek[  1] |=  2; ek[ 11] |=  4; ek[ 26] |=  1;
1096             ek[ 33] |= 16; ek[ 42] |=  2; ek[ 48] |=  2;
1097             ek[ 57] |=  4; ek[ 64] |=  1; ek[ 74] |=  4;
1098             ek[ 81] |= 32; ek[ 90] |= 32; ek[ 97] |=  8;
1099             ek[106] |=  8; ek[115] |= 32; ek[120] |= 16;
1100         }
1101         if ((octet & 0x40) != 0) {
1102             ek[  2] |= 32; ek[ 11] |=  2; ek[ 16] |= 32;
1103             ek[ 25] |=  1; ek[ 32] |= 16; ek[ 43] |=  4;
1104             ek[ 58] |=  1; ek[ 75] |=  8; ek[ 91] |=  1;
1105             ek[ 96] |=  1; ek[106] |=  4; ek[113] |= 32;
1106         }
1107         if ((octet & 0x20) != 0) {
1108             ek[  3] |=  1; ek[  9] |=  4; ek[ 19] |= 16;
1109             ek[ 24] |=  4; ek[ 43] |=  2; ek[ 48] |= 32;
1110             ek[ 57] |=  1; ek[ 67] |= 32; ek[ 73] |=  2;
1111             ek[ 82] |= 16; ek[ 88] |=  8; ek[107] |=  8;
1112             ek[120] |=  2;
1113         }
1114         if ((octet & 0x10) != 0) {
1115             ek[  0] |=  8; ek[ 10] |=  1; ek[ 17] |= 16;
1116             ek[ 26] |=  2; ek[ 32] |=  2; ek[ 41] |=  4;
1117             ek[ 51] |= 16; ek[ 56] |=  4; ek[ 65] |= 32;
1118             ek[ 74] |= 32; ek[ 81] |=  8; ek[ 90] |=  8;
1119             ek[ 99] |= 32; ek[105] |=  2; ek[114] |= 16;
1120         }
1121         if ((octet & 0x8) != 0) {
1122             ek[  6] |=  1; ek[ 20] |=  1; ek[ 30] |=  4;
1123             ek[ 36] |=  8; ek[ 53] |= 16; ek[ 60] |=  4;
1124             ek[ 69] |=  1; ek[ 78] |=  8; ek[ 92] |=  2;
1125             ek[103] |=  4; ek[109] |= 32; ek[119] |=  1;
1126             ek[125] |=  8;
1127         }
1128         if ((octet & 0x4) != 0) {
1129             ek[  7] |=  8; ek[ 21] |= 16; ek[ 28] |=  4;
1130             ek[ 39] |= 16; ek[ 44] |= 32; ek[ 54] |= 32;
1131             ek[ 61] |=  4; ek[ 71] |=  4; ek[ 77] |= 32;
1132             ek[ 87] |=  1; ek[ 94] |=  1; ek[103] |=  2;
1133             ek[109] |=  2; ek[124] |=  8;
1134         }
1135         if ((octet & 0x2) != 0) {
1136             ek[  6] |=  8; ek[ 12] |= 32; ek[ 22] |= 32;
1137             ek[ 29] |=  4; ek[ 38] |=  2; ek[ 44] |= 16;
1138             ek[ 53] |=  8; ek[ 71] |=  2; ek[ 77] |=  2;
1139             ek[ 95] |=  8; ek[102] |= 16; ek[111] |= 32;
1140             ek[117] |=  1; ek[127] |= 16;
1141         }
1142 
1143         expandedKey = ek;
1144     }
1145 }