jobb

16:37:57.755 INFO  jd.cli.Main - Decompiling jobb.jar
package Twofish;

import java.io.InputStream;
import java.io.PrintStream;
import java.io.PrintWriter;
import java.util.Enumeration;
import java.util.Properties;

public class Twofish_Properties
{
  static final boolean GLOBAL_DEBUG = false;
  static final String ALGORITHM = "Twofish";
  static final double VERSION = 0.2D;
  static final String FULL_NAME = "Twofish ver. 0.2";
  static final String NAME = "Twofish_Properties";
  static final Properties properties = new Properties();
  private static final String[][] DEFAULT_PROPERTIES = { { "Trace.Twofish_Algorithm", "true" }, { "Debug.Level.*", "1" }, { "Debug.Level.Twofish_Algorithm", "9" } };
  
  static
  {
    String it = "Twofish.properties";
    InputStream is = Twofish_Properties.class.getResourceAsStream(it);
    boolean ok = is != null;
    if (ok) {
      try
      {
        properties.load(is);
        is.close();
      }
      catch (Exception x)
      {
        ok = false;
      }
    }
    if (!ok)
    {
      int n = DEFAULT_PROPERTIES.length;
      for (int i = 0; i < n; i++) {
        properties.put(DEFAULT_PROPERTIES[i][0], DEFAULT_PROPERTIES[i][1]);
      }
    }
  }
  
  public static String getProperty(String key)
  {
    return properties.getProperty(key);
  }
  
  public static String getProperty(String key, String value)
  {
    return properties.getProperty(key, value);
  }
  
  public static void list(PrintStream out)
  {
    list(new PrintWriter(out, true));
  }
  
  public static void list(PrintWriter out)
  {
    out.println("#");
    out.println("# ----- Begin Twofish properties -----");
    out.println("#");
    
    Enumeration en = properties.propertyNames();
    while (en.hasMoreElements())
    {
      String key = (String)en.nextElement();
      String value = getProperty(key);
      out.println(key + " = " + value);
    }
    out.println("#");
    out.println("# ----- End Twofish properties -----");
  }
  
  public static Enumeration propertyNames()
  {
    return properties.propertyNames();
  }
  
  static boolean isTraceable(String label)
  {
    String s = getProperty("Trace." + label);
    if (s == null) {
      return false;
    }
    return new Boolean(s).booleanValue();
  }
  
  static int getLevel(String label)
  {
    String s = getProperty("Debug.Level." + label);
    if (s == null)
    {
      s = getProperty("Debug.Level.*");
      if (s == null) {
        return 0;
      }
    }
    try
    {
      return Integer.parseInt(s);
    }
    catch (NumberFormatException e) {}
    return 0;
  }
  
  static PrintWriter getOutput()
  {
    String name = getProperty("Output");
    PrintWriter pw;
    PrintWriter pw;
    if ((name != null) && (name.equals("out"))) {
      pw = new PrintWriter(System.out, true);
    } else {
      pw = new PrintWriter(System.err, true);
    }
    return pw;
  }
}

/* Location:
 * Qualified Name:     Twofish.Twofish_Properties
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package Twofish;

import java.io.PrintWriter;
import java.security.InvalidKeyException;

public final class Twofish_Algorithm
{
  static final String NAME = "Twofish_Algorithm";
  static final boolean IN = true;
  static final boolean OUT = false;
  static final boolean DEBUG = false;
  static final int debuglevel = 0;
  static final PrintWriter err = (PrintWriter)null;
  static final boolean TRACE = Twofish_Properties.isTraceable("Twofish_Algorithm");
  static final int BLOCK_SIZE = 16;
  private static final int ROUNDS = 16;
  private static final int MAX_ROUNDS = 16;
  private static final int INPUT_WHITEN = 0;
  private static final int OUTPUT_WHITEN = 4;
  private static final int ROUND_SUBKEYS = 8;
  private static final int TOTAL_SUBKEYS = 40;
  private static final int SK_STEP = 33686018;
  private static final int SK_BUMP = 16843009;
  private static final int SK_ROTL = 9;
  
  static void debug(String s)
  {
    err.println(">>> Twofish_Algorithm: " + s);
  }
  
  static void trace(boolean in, String s)
  {
    if (TRACE) {
      err.println((in ? "==> " : "<== ") + "Twofish_Algorithm" + "." + s);
    }
  }
  
  static void trace(String s)
  {
    if (TRACE) {
      err.println("<=> Twofish_Algorithm." + s);
    }
  }
  
  private static final byte[][] P = { { -87, 103, -77, -24, 4, -3, -93, 118, -102, -110, Byte.MIN_VALUE, 120, -28, -35, -47, 56, 13, -58, 53, -104, 24, -9, -20, 108, 67, 117, 55, 38, -6, 19, -108, 72, -14, -48, -117, 48, -124, 84, -33, 35, 25, 91, 61, 89, -13, -82, -94, -126, 99, 1, -125, 46, -39, 81, -101, 124, -90, -21, -91, -66, 22, 12, -29, 97, -64, -116, 58, -11, 115, 44, 37, 11, -69, 78, -119, 107, 83, 106, -76, -15, -31, -26, -67, 69, -30, -12, -74, 102, -52, -107, 3, 86, -44, 28, 30, -41, -5, -61, -114, -75, -23, -49, -65, -70, -22, 119, 57, -81, 51, -55, 98, 113, -127, 121, 9, -83, 36, -51, -7, -40, -27, -59, -71, 77, 68, 8, -122, -25, -95, 29, -86, -19, 6, 112, -78, -46, 65, 123, -96, 17, 49, -62, 39, -112, 32, -10, 96, -1, -106, 92, -79, -85, -98, -100, 82, 27, 95, -109, 10, -17, -111, -123, 73, -18, 45, 79, -113, 59, 71, -121, 109, 70, -42, 62, 105, 100, 42, -50, -53, 47, -4, -105, 5, 122, -84, Byte.MAX_VALUE, -43, 26, 75, 14, -89, 90, 40, 20, 63, 41, -120, 60, 76, 2, -72, -38, -80, 23, 85, 31, -118, 125, 87, -57, -115, 116, -73, -60, -97, 114, 126, 21, 34, 18, 88, 7, -103, 52, 110, 80, -34, 104, 101, -68, -37, -8, -56, -88, 43, 64, -36, -2, 50, -92, -54, 16, 33, -16, -45, 93, 15, 0, 111, -99, 54, 66, 74, 94, -63, -32 }, { 117, -13, -58, -12, -37, 123, -5, -56, 74, -45, -26, 107, 69, 125, -24, 75, -42, 50, -40, -3, 55, 113, -15, -31, 48, 15, -8, 27, -121, -6, 6, 63, 94, -70, -82, 91, -118, 0, -68, -99, 109, -63, -79, 14, Byte.MIN_VALUE, 93, -46, -43, -96, -124, 7, 20, -75, -112, 44, -93, -78, 115, 76, 84, -110, 116, 54, 81, 56, -80, -67, 90, -4, 96, 98, -106, 108, 66, -9, 16, 124, 40, 39, -116, 19, -107, -100, -57, 36, 70, 59, 112, -54, -29, -123, -53, 17, -48, -109, -72, -90, -125, 32, -1, -97, 119, -61, -52, 3, 111, 8, -65, 64, -25, 43, -30, 121, 12, -86, -126, 65, 58, -22, -71, -28, -102, -92, -105, 126, -38, 122, 23, 102, -108, -95, 29, 61, -16, -34, -77, 11, 114, -89, 28, -17, -47, 83, 62, -113, 51, 38, 95, -20, 118, 42, 73, -127, -120, -18, 33, -60, 26, -21, -39, -59, 57, -103, -51, -83, 49, -117, 1, 24, 35, -35, 31, 78, 45, -7, 72, 79, -14, 101, -114, 120, 92, 88, 25, -115, -27, -104, 87, 103, Byte.MAX_VALUE, 5, 100, -81, 99, -74, -2, -11, -73, 60, -91, -50, -23, 104, 68, -32, 77, 67, 105, 41, 46, -84, 21, 89, -88, 10, -98, 110, 71, -33, 52, 53, 106, -49, -36, 34, -55, -64, -101, -119, -44, -19, -85, 18, -94, 13, 82, -69, 2, 47, -87, -41, 97, 30, -76, 80, 4, -10, -62, 22, 37, -122, 86, 85, 9, -66, -111 } };
  private static final int P_00 = 1;
  private static final int P_01 = 0;
  private static final int P_02 = 0;
  private static final int P_03 = 1;
  private static final int P_04 = 1;
  private static final int P_10 = 0;
  private static final int P_11 = 0;
  private static final int P_12 = 1;
  private static final int P_13 = 1;
  private static final int P_14 = 0;
  private static final int P_20 = 1;
  private static final int P_21 = 1;
  private static final int P_22 = 0;
  private static final int P_23 = 0;
  private static final int P_24 = 0;
  private static final int P_30 = 0;
  private static final int P_31 = 1;
  private static final int P_32 = 1;
  private static final int P_33 = 0;
  private static final int P_34 = 1;
  private static final int GF256_FDBK = 361;
  private static final int GF256_FDBK_2 = 180;
  private static final int GF256_FDBK_4 = 90;
  private static final int[][] MDS = new int[4]['?'];
  private static final int RS_GF_FDBK = 333;
  private static final char[] HEX_DIGITS = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
  
  static
  {
    long time = System.currentTimeMillis();
    
    int[] m1 = new int[2];
    int[] mX = new int[2];
    int[] mY = new int[2];
    for (int i = 0; i < 256; i++)
    {
      int j = P[0][i] & 0xFF;
      m1[0] = j;
      mX[0] = (Mx_X(j) & 0xFF);
      mY[0] = (Mx_Y(j) & 0xFF);
      
      j = P[1][i] & 0xFF;
      m1[1] = j;
      mX[1] = (Mx_X(j) & 0xFF);
      mY[1] = (Mx_Y(j) & 0xFF);
      
      MDS[0][i] = (m1[1] << 0 | mX[1] << 8 | mY[1] << 16 | mY[1] << 24);
      
      MDS[1][i] = (mY[0] << 0 | mY[0] << 8 | mX[0] << 16 | m1[0] << 24);
      
      MDS[2][i] = (mX[1] << 0 | mY[1] << 8 | m1[1] << 16 | mY[1] << 24);
      
      MDS[3][i] = (mX[0] << 0 | m1[0] << 8 | mY[0] << 16 | mX[0] << 24);
    }
    time = System.currentTimeMillis() - time;
  }
  
  private static final int LFSR1(int x)
  {
    return x >> 1 ^ ((x & 0x1) != 0 ? 180 : 0);
  }
  
  private static final int LFSR2(int x)
  {
    return x >> 2 ^ ((x & 0x2) != 0 ? 180 : 0) ^ ((x & 0x1) != 0 ? 90 : 0);
  }
  
  private static final int Mx_1(int x)
  {
    return x;
  }
  
  private static final int Mx_X(int x)
  {
    return x ^ LFSR2(x);
  }
  
  private static final int Mx_Y(int x)
  {
    return x ^ LFSR1(x) ^ LFSR2(x);
  }
  
  public static synchronized Object makeKey(byte[] k)
    throws InvalidKeyException
  {
    if (k == null) {
      throw new InvalidKeyException("Empty key");
    }
    int length = k.length;
    if ((length != 8) && (length != 16) && (length != 24) && (length != 32)) {
      throw new InvalidKeyException("Incorrect key length");
    }
    int k64Cnt = length / 8;
    int subkeyCnt = 40;
    int[] k32e = new int[4];
    int[] k32o = new int[4];
    int[] sBoxKey = new int[4];
    
    int offset = 0;
    int i = 0;
    for (int j = k64Cnt - 1; (i < 4) && (offset < length); j--)
    {
      k32e[i] = (k[(offset++)] & 0xFF | (k[(offset++)] & 0xFF) << 8 | (k[(offset++)] & 0xFF) << 16 | (k[(offset++)] & 0xFF) << 24);
      
      k32o[i] = (k[(offset++)] & 0xFF | (k[(offset++)] & 0xFF) << 8 | (k[(offset++)] & 0xFF) << 16 | (k[(offset++)] & 0xFF) << 24);
      
      sBoxKey[j] = RS_MDS_Encode(k32e[i], k32o[i]);i++;
    }
    int[] subKeys = new int[subkeyCnt];
    int q;
    for (i = q = 0; i < subkeyCnt / 2; q += 33686018)
    {
      int A = F32(k64Cnt, q, k32e);
      int B = F32(k64Cnt, q + 16843009, k32o);
      B = B << 8 | B >>> 24;
      A += B;
      subKeys[(2 * i)] = A;
      A += B;
      subKeys[(2 * i + 1)] = (A << 9 | A >>> 23);i++;
    }
    int k0 = sBoxKey[0];
    int k1 = sBoxKey[1];
    int k2 = sBoxKey[2];
    int k3 = sBoxKey[3];
    
    int[] sBox = new int['?'];
    for (i = 0; i < 256; i++)
    {
      int b3;
      int b2;
      int b1;
      int b0 = b1 = b2 = b3 = i;
      switch (k64Cnt & 0x3)
      {
      case 1: 
        sBox[(2 * i)] = MDS[0][(P[0][b0] & 0xFF ^ b0(k0))];
        sBox[(2 * i + 1)] = MDS[1][(P[0][b1] & 0xFF ^ b1(k0))];
        sBox[(512 + 2 * i)] = MDS[2][(P[1][b2] & 0xFF ^ b2(k0))];
        sBox[(512 + 2 * i + 1)] = MDS[3][(P[1][b3] & 0xFF ^ b3(k0))];
        break;
      case 0: 
        b0 = P[1][b0] & 0xFF ^ b0(k3);
        b1 = P[0][b1] & 0xFF ^ b1(k3);
        b2 = P[0][b2] & 0xFF ^ b2(k3);
        b3 = P[1][b3] & 0xFF ^ b3(k3);
      case 3: 
        b0 = P[1][b0] & 0xFF ^ b0(k2);
        b1 = P[1][b1] & 0xFF ^ b1(k2);
        b2 = P[0][b2] & 0xFF ^ b2(k2);
        b3 = P[0][b3] & 0xFF ^ b3(k2);
      case 2: 
        sBox[(2 * i)] = MDS[0][(P[0][(P[0][b0] & 0xFF ^ b0(k1))] & 0xFF ^ b0(k0))];
        sBox[(2 * i + 1)] = MDS[1][(P[0][(P[1][b1] & 0xFF ^ b1(k1))] & 0xFF ^ b1(k0))];
        sBox[(512 + 2 * i)] = MDS[2][(P[1][(P[0][b2] & 0xFF ^ b2(k1))] & 0xFF ^ b2(k0))];
        sBox[(512 + 2 * i + 1)] = MDS[3][(P[1][(P[1][b3] & 0xFF ^ b3(k1))] & 0xFF ^ b3(k0))];
      }
    }
    Object sessionKey = { sBox, subKeys };
    
    return sessionKey;
  }
  
  public static byte[] blockEncrypt(byte[] in, int inOffset, Object sessionKey)
  {
    Object[] sk = (Object[])sessionKey;
    int[] sBox = (int[])sk[0];
    int[] sKey = (int[])sk[1];
    
    int x0 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    int x1 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    int x2 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    int x3 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    x0 ^= sKey[0];
    x1 ^= sKey[1];
    x2 ^= sKey[2];
    x3 ^= sKey[3];
    
    int k = 8;
    for (int R = 0; R < 16; R += 2)
    {
      int t0 = Fe32(sBox, x0, 0);
      int t1 = Fe32(sBox, x1, 3);
      x2 ^= t0 + t1 + sKey[(k++)];
      x2 = x2 >>> 1 | x2 << 31;
      x3 = x3 << 1 | x3 >>> 31;
      x3 ^= t0 + 2 * t1 + sKey[(k++)];
      
      t0 = Fe32(sBox, x2, 0);
      t1 = Fe32(sBox, x3, 3);
      x0 ^= t0 + t1 + sKey[(k++)];
      x0 = x0 >>> 1 | x0 << 31;
      x1 = x1 << 1 | x1 >>> 31;
      x1 ^= t0 + 2 * t1 + sKey[(k++)];
    }
    x2 ^= sKey[4];
    x3 ^= sKey[5];
    x0 ^= sKey[6];
    x1 ^= sKey[7];
    
    byte[] result = { (byte)x2, (byte)(x2 >>> 8), (byte)(x2 >>> 16), (byte)(x2 >>> 24), (byte)x3, (byte)(x3 >>> 8), (byte)(x3 >>> 16), (byte)(x3 >>> 24), (byte)x0, (byte)(x0 >>> 8), (byte)(x0 >>> 16), (byte)(x0 >>> 24), (byte)x1, (byte)(x1 >>> 8), (byte)(x1 >>> 16), (byte)(x1 >>> 24) };
    
    return result;
  }
  
  public static byte[] blockDecrypt(byte[] in, int inOffset, Object sessionKey)
  {
    Object[] sk = (Object[])sessionKey;
    int[] sBox = (int[])sk[0];
    int[] sKey = (int[])sk[1];
    
    int x2 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    int x3 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    int x0 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    int x1 = in[(inOffset++)] & 0xFF | (in[(inOffset++)] & 0xFF) << 8 | (in[(inOffset++)] & 0xFF) << 16 | (in[(inOffset++)] & 0xFF) << 24;
    
    x2 ^= sKey[4];
    x3 ^= sKey[5];
    x0 ^= sKey[6];
    x1 ^= sKey[7];
    
    int k = 39;
    for (int R = 0; R < 16; R += 2)
    {
      int t0 = Fe32(sBox, x2, 0);
      int t1 = Fe32(sBox, x3, 3);
      x1 ^= t0 + 2 * t1 + sKey[(k--)];
      x1 = x1 >>> 1 | x1 << 31;
      x0 = x0 << 1 | x0 >>> 31;
      x0 ^= t0 + t1 + sKey[(k--)];
      
      t0 = Fe32(sBox, x0, 0);
      t1 = Fe32(sBox, x1, 3);
      x3 ^= t0 + 2 * t1 + sKey[(k--)];
      x3 = x3 >>> 1 | x3 << 31;
      x2 = x2 << 1 | x2 >>> 31;
      x2 ^= t0 + t1 + sKey[(k--)];
    }
    x0 ^= sKey[0];
    x1 ^= sKey[1];
    x2 ^= sKey[2];
    x3 ^= sKey[3];
    
    byte[] result = { (byte)x0, (byte)(x0 >>> 8), (byte)(x0 >>> 16), (byte)(x0 >>> 24), (byte)x1, (byte)(x1 >>> 8), (byte)(x1 >>> 16), (byte)(x1 >>> 24), (byte)x2, (byte)(x2 >>> 8), (byte)(x2 >>> 16), (byte)(x2 >>> 24), (byte)x3, (byte)(x3 >>> 8), (byte)(x3 >>> 16), (byte)(x3 >>> 24) };
    
    return result;
  }
  
  public static boolean self_test()
  {
    return self_test(16);
  }
  
  private static final int b0(int x)
  {
    return x & 0xFF;
  }
  
  private static final int b1(int x)
  {
    return x >>> 8 & 0xFF;
  }
  
  private static final int b2(int x)
  {
    return x >>> 16 & 0xFF;
  }
  
  private static final int b3(int x)
  {
    return x >>> 24 & 0xFF;
  }
  
  private static final int RS_MDS_Encode(int k0, int k1)
  {
    int r = k1;
    for (int i = 0; i < 4; i++) {
      r = RS_rem(r);
    }
    r ^= k0;
    for (int i = 0; i < 4; i++) {
      r = RS_rem(r);
    }
    return r;
  }
  
  private static final int RS_rem(int x)
  {
    int b = x >>> 24 & 0xFF;
    int g2 = (b << 1 ^ ((b & 0x80) != 0 ? 333 : 0)) & 0xFF;
    int g3 = b >>> 1 ^ ((b & 0x1) != 0 ? 166 : 0) ^ g2;
    int result = x << 8 ^ g3 << 24 ^ g2 << 16 ^ g3 << 8 ^ b;
    return result;
  }
  
  private static final int F32(int k64Cnt, int x, int[] k32)
  {
    int b0 = b0(x);
    int b1 = b1(x);
    int b2 = b2(x);
    int b3 = b3(x);
    int k0 = k32[0];
    int k1 = k32[1];
    int k2 = k32[2];
    int k3 = k32[3];
    
    int result = 0;
    switch (k64Cnt & 0x3)
    {
    case 1: 
      result = MDS[0][(P[0][b0] & 0xFF ^ b0(k0))] ^ MDS[1][(P[0][b1] & 0xFF ^ b1(k0))] ^ MDS[2][(P[1][b2] & 0xFF ^ b2(k0))] ^ MDS[3][(P[1][b3] & 0xFF ^ b3(k0))];
      
      break;
    case 0: 
      b0 = P[1][b0] & 0xFF ^ b0(k3);
      b1 = P[0][b1] & 0xFF ^ b1(k3);
      b2 = P[0][b2] & 0xFF ^ b2(k3);
      b3 = P[1][b3] & 0xFF ^ b3(k3);
    case 3: 
      b0 = P[1][b0] & 0xFF ^ b0(k2);
      b1 = P[1][b1] & 0xFF ^ b1(k2);
      b2 = P[0][b2] & 0xFF ^ b2(k2);
      b3 = P[0][b3] & 0xFF ^ b3(k2);
    case 2: 
      result = MDS[0][(P[0][(P[0][b0] & 0xFF ^ b0(k1))] & 0xFF ^ b0(k0))] ^ MDS[1][(P[0][(P[1][b1] & 0xFF ^ b1(k1))] & 0xFF ^ b1(k0))] ^ MDS[2][(P[1][(P[0][b2] & 0xFF ^ b2(k1))] & 0xFF ^ b2(k0))] ^ MDS[3][(P[1][(P[1][b3] & 0xFF ^ b3(k1))] & 0xFF ^ b3(k0))];
    }
    return result;
  }
  
  private static final int Fe32(int[] sBox, int x, int R)
  {
    return sBox[(2 * _b(x, R))] ^ sBox[(2 * _b(x, R + 1) + 1)] ^ sBox[(512 + 2 * _b(x, R + 2))] ^ sBox[(512 + 2 * _b(x, R + 3) + 1)];
  }
  
  private static final int _b(int x, int N)
  {
    int result = 0;
    switch (N % 4)
    {
    case 0: 
      result = b0(x); break;
    case 1: 
      result = b1(x); break;
    case 2: 
      result = b2(x); break;
    case 3: 
      result = b3(x);
    }
    return result;
  }
  
  public static int blockSize()
  {
    return 16;
  }
  
  private static boolean self_test(int keysize)
  {
    boolean ok = false;
    try
    {
      byte[] kb = new byte[keysize];
      byte[] pt = new byte[16];
      for (int i = 0; i < keysize; i++) {
        kb[i] = ((byte)i);
      }
      for (i = 0; i < 16; i++) {
        pt[i] = ((byte)i);
      }
      Object key = makeKey(kb);
      
      byte[] ct = blockEncrypt(pt, 0, key);
      
      byte[] cpt = blockDecrypt(ct, 0, key);
      
      ok = areEqual(pt, cpt);
      if (!ok) {
        throw new RuntimeException("Symmetric operation failed");
      }
    }
    catch (Exception x) {}
    return ok;
  }
  
  private static boolean areEqual(byte[] a, byte[] b)
  {
    int aLength = a.length;
    if (aLength != b.length) {
      return false;
    }
    for (int i = 0; i < aLength; i++) {
      if (a[i] != b[i]) {
        return false;
      }
    }
    return true;
  }
  
  private static String intToString(int n)
  {
    char[] buf = new char[8];
    for (int i = 7; i >= 0; i--)
    {
      buf[i] = HEX_DIGITS[(n & 0xF)];
      n >>>= 4;
    }
    return new String(buf);
  }
  
  private static String toString(byte[] ba)
  {
    return toString(ba, 0, ba.length);
  }
  
  private static String toString(byte[] ba, int offset, int length)
  {
    char[] buf = new char[length * 2];
    int i = offset;
    for (int j = 0; i < offset + length;)
    {
      int k = ba[(i++)];
      buf[(j++)] = HEX_DIGITS[(k >>> 4 & 0xF)];
      buf[(j++)] = HEX_DIGITS[(k & 0xF)];
    }
    return new String(buf);
  }
  
  public static void main(String[] args)
  {
    self_test(16);
    self_test(24);
    self_test(32);
  }
}

/* Location:
 * Qualified Name:     Twofish.Twofish_Algorithm
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package com.android.jobb;

public class Base64
{
  private static final byte[] encodingTable = { 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47 };
  
  public static byte[] encode(byte[] data)
  {
    int modulus = data.length % 3;
    byte[] bytes;
    byte[] bytes;
    if (modulus == 0) {
      bytes = new byte[4 * data.length / 3];
    } else {
      bytes = new byte[4 * (data.length / 3 + 1)];
    }
    int dataLength = data.length - modulus;
    
    int i = 0;
    for (int j = 0; i < dataLength; j += 4)
    {
      int a1 = data[i] & 0xFF;
      int a2 = data[(i + 1)] & 0xFF;
      int a3 = data[(i + 2)] & 0xFF;
      
      bytes[j] = encodingTable[(a1 >>> 2 & 0x3F)];
      bytes[(j + 1)] = encodingTable[((a1 << 4 | a2 >>> 4) & 0x3F)];
      bytes[(j + 2)] = encodingTable[((a2 << 2 | a3 >>> 6) & 0x3F)];
      bytes[(j + 3)] = encodingTable[(a3 & 0x3F)];i += 3;
    }
    int d1;
    int b1;
    int b2;
    switch (modulus)
    {
    case 0: 
      break;
    case 1: 
      d1 = data[(data.length - 1)] & 0xFF;
      b1 = d1 >>> 2 & 0x3F;
      b2 = d1 << 4 & 0x3F;
      
      bytes[(bytes.length - 4)] = encodingTable[b1];
      bytes[(bytes.length - 3)] = encodingTable[b2];
      bytes[(bytes.length - 2)] = 61;
      bytes[(bytes.length - 1)] = 61;
      break;
    case 2: 
      d1 = data[(data.length - 2)] & 0xFF;
      int d2 = data[(data.length - 1)] & 0xFF;
      
      b1 = d1 >>> 2 & 0x3F;
      b2 = (d1 << 4 | d2 >>> 4) & 0x3F;
      int b3 = d2 << 2 & 0x3F;
      
      bytes[(bytes.length - 4)] = encodingTable[b1];
      bytes[(bytes.length - 3)] = encodingTable[b2];
      bytes[(bytes.length - 2)] = encodingTable[b3];
      bytes[(bytes.length - 1)] = 61;
    }
    return bytes;
  }
  
  private static final byte[] decodingTable = new byte['?'];
  
  static
  {
    for (int i = 65; i <= 90; i++) {
      decodingTable[i] = ((byte)(i - 65));
    }
    for (int i = 97; i <= 122; i++) {
      decodingTable[i] = ((byte)(i - 97 + 26));
    }
    for (int i = 48; i <= 57; i++) {
      decodingTable[i] = ((byte)(i - 48 + 52));
    }
    decodingTable[43] = 62;
    decodingTable[47] = 63;
  }
  
  public static byte[] decode(byte[] data)
  {
    byte[] bytes;
    byte[] bytes;
    if (data[(data.length - 2)] == 61)
    {
      bytes = new byte[(data.length / 4 - 1) * 3 + 1];
    }
    else
    {
      byte[] bytes;
      if (data[(data.length - 1)] == 61) {
        bytes = new byte[(data.length / 4 - 1) * 3 + 2];
      } else {
        bytes = new byte[data.length / 4 * 3];
      }
    }
    int i = 0;
    for (int j = 0; i < data.length - 4; j += 3)
    {
      byte b1 = decodingTable[data[i]];
      byte b2 = decodingTable[data[(i + 1)]];
      byte b3 = decodingTable[data[(i + 2)]];
      byte b4 = decodingTable[data[(i + 3)]];
      
      bytes[j] = ((byte)(b1 << 2 | b2 >> 4));
      bytes[(j + 1)] = ((byte)(b2 << 4 | b3 >> 2));
      bytes[(j + 2)] = ((byte)(b3 << 6 | b4));i += 4;
    }
    if (data[(data.length - 2)] == 61)
    {
      byte b1 = decodingTable[data[(data.length - 4)]];
      byte b2 = decodingTable[data[(data.length - 3)]];
      
      bytes[(bytes.length - 1)] = ((byte)(b1 << 2 | b2 >> 4));
    }
    else if (data[(data.length - 1)] == 61)
    {
      byte b1 = decodingTable[data[(data.length - 4)]];
      byte b2 = decodingTable[data[(data.length - 3)]];
      byte b3 = decodingTable[data[(data.length - 2)]];
      
      bytes[(bytes.length - 2)] = ((byte)(b1 << 2 | b2 >> 4));
      bytes[(bytes.length - 1)] = ((byte)(b2 << 4 | b3 >> 2));
    }
    else
    {
      byte b1 = decodingTable[data[(data.length - 4)]];
      byte b2 = decodingTable[data[(data.length - 3)]];
      byte b3 = decodingTable[data[(data.length - 2)]];
      byte b4 = decodingTable[data[(data.length - 1)]];
      
      bytes[(bytes.length - 3)] = ((byte)(b1 << 2 | b2 >> 4));
      bytes[(bytes.length - 2)] = ((byte)(b2 << 4 | b3 >> 2));
      bytes[(bytes.length - 1)] = ((byte)(b3 << 6 | b4));
    }
    return bytes;
  }
  
  public static byte[] decode(String data)
  {
    byte[] bytes;
    byte[] bytes;
    if (data.charAt(data.length() - 2) == '=')
    {
      bytes = new byte[(data.length() / 4 - 1) * 3 + 1];
    }
    else
    {
      byte[] bytes;
      if (data.charAt(data.length() - 1) == '=') {
        bytes = new byte[(data.length() / 4 - 1) * 3 + 2];
      } else {
        bytes = new byte[data.length() / 4 * 3];
      }
    }
    int i = 0;
    for (int j = 0; i < data.length() - 4; j += 3)
    {
      byte b1 = decodingTable[data.charAt(i)];
      byte b2 = decodingTable[data.charAt(i + 1)];
      byte b3 = decodingTable[data.charAt(i + 2)];
      byte b4 = decodingTable[data.charAt(i + 3)];
      
      bytes[j] = ((byte)(b1 << 2 | b2 >> 4));
      bytes[(j + 1)] = ((byte)(b2 << 4 | b3 >> 2));
      bytes[(j + 2)] = ((byte)(b3 << 6 | b4));i += 4;
    }
    if (data.charAt(data.length() - 2) == '=')
    {
      byte b1 = decodingTable[data.charAt(data.length() - 4)];
      byte b2 = decodingTable[data.charAt(data.length() - 3)];
      
      bytes[(bytes.length - 1)] = ((byte)(b1 << 2 | b2 >> 4));
    }
    else if (data.charAt(data.length() - 1) == '=')
    {
      byte b1 = decodingTable[data.charAt(data.length() - 4)];
      byte b2 = decodingTable[data.charAt(data.length() - 3)];
      byte b3 = decodingTable[data.charAt(data.length() - 2)];
      
      bytes[(bytes.length - 2)] = ((byte)(b1 << 2 | b2 >> 4));
      bytes[(bytes.length - 1)] = ((byte)(b2 << 4 | b3 >> 2));
    }
    else
    {
      byte b1 = decodingTable[data.charAt(data.length() - 4)];
      byte b2 = decodingTable[data.charAt(data.length() - 3)];
      byte b3 = decodingTable[data.charAt(data.length() - 2)];
      byte b4 = decodingTable[data.charAt(data.length() - 1)];
      
      bytes[(bytes.length - 3)] = ((byte)(b1 << 2 | b2 >> 4));
      bytes[(bytes.length - 2)] = ((byte)(b2 << 4 | b3 >> 2));
      bytes[(bytes.length - 1)] = ((byte)(b3 << 6 | b4));
    }
    return bytes;
  }
}

/* Location:
 * Qualified Name:     com.android.jobb.Base64
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package com.android.jobb;

import java.io.IOException;
import java.io.OutputStream;

public abstract interface Encoder
{
  public abstract int encode(byte[] paramArrayOfByte, int paramInt1, int paramInt2, OutputStream paramOutputStream)
    throws IOException;
  
  public abstract int decode(byte[] paramArrayOfByte, int paramInt1, int paramInt2, OutputStream paramOutputStream)
    throws IOException;
  
  public abstract int decode(String paramString, OutputStream paramOutputStream)
    throws IOException;
}

/* Location:
 * Qualified Name:     com.android.jobb.Encoder
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package com.android.jobb;

import java.io.UnsupportedEncodingException;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.security.SecureRandom;
import java.security.spec.InvalidKeySpecException;
import javax.crypto.SecretKeyFactory;
import javax.crypto.interfaces.PBEKey;
import javax.crypto.spec.PBEKeySpec;

public class PBKDF
{
  public static final int SALT_LEN = 8;
  private static final int ROUNDS = 1024;
  private static final int KEY_BITS = 128;
  
  public static byte[] getKey(String password, byte[] saltBytes)
    throws InvalidKeyException, NoSuchAlgorithmException, UnsupportedEncodingException
  {
    PBEKeySpec pwKey = new PBEKeySpec(password.toCharArray(), saltBytes, 1024, 128);
    SecretKeyFactory factory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
    try
    {
      PBEKey pbeKey = (PBEKey)factory.generateSecret(pwKey);
      return pbeKey.getEncoded();
    }
    catch (InvalidKeySpecException e)
    {
      e.printStackTrace();
    }
    return null;
  }
  
  public static byte[] getRandomSalt()
  {
    SecureRandom random = new SecureRandom();
    byte[] saltBytes = new byte[8];
    random.nextBytes(saltBytes);
    return saltBytes;
  }
}

/* Location:
 * Qualified Name:     com.android.jobb.PBKDF
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package com.android.jobb;

import java.io.File;
import java.io.PrintStream;
import java.util.Stack;

final class Main$2
  implements Main.FileProcessor
{
  Stack<int[]> mDirLen = new Stack();
  
  Main$2(boolean paramBoolean, int paramInt, long[] paramArrayOfLong) {}
  
  public void processFile(File f)
  {
    if (Main.sVerboseMode) {
      System.out.println("Adding size for file: " + f.getAbsolutePath());
    }
    long length = f.length();
    if ((val$calculateSlop) && (length > 0L))
    {
      int[] dirLen = (int[])mDirLen.peek();
      long realLength = (val$clusterSize - 1 + length) / val$clusterSize * val$clusterSize;
      long slop = realLength - length;
      length += slop;
      val$mSize[0] += length;
      val$mSize[1] += slop;
      dirLen[0] += f.getName().length() / 13 + 3;
    }
    else
    {
      val$mSize[0] += length;
    }
  }
  
  public void processDirectory(File f)
  {
    if (val$calculateSlop)
    {
      int[] dirLen = new int[1];
      dirLen[0] += f.getName().length() / 13 + 4;
      mDirLen.push(dirLen);
    }
  }
  
  public void endDirectory(File dir)
  {
    if (val$calculateSlop)
    {
      int[] dirLen = (int[])mDirLen.pop();
      long lastDirLen = dirLen[0] * 32;
      if (lastDirLen != 0L)
      {
        long realLength = (val$clusterSize - 1 + lastDirLen) / val$clusterSize * val$clusterSize;
        long slop = realLength - lastDirLen;
        val$mSize[0] += lastDirLen + slop;
        val$mSize[1] += slop;
        val$mSize[2] += lastDirLen;
      }
    }
  }
}

/* Location:
 * Qualified Name:     com.android.jobb.Main.2
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package com.android.jobb;

import de.waldheinz.fs.fat.Fat;
import de.waldheinz.fs.fat.FatFile;
import de.waldheinz.fs.fat.FatFileSystem;
import de.waldheinz.fs.fat.FatLfnDirectory;
import de.waldheinz.fs.fat.FatLfnDirectoryEntry;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.PrintStream;
import java.nio.ByteBuffer;
import java.nio.channels.ReadableByteChannel;
import java.util.Stack;

final class Main$1
  implements Main.FileProcessor
{
  Stack<FatLfnDirectory> mCurDir = new Stack();
  
  Main$1(String paramString, FatFileSystem paramFatFileSystem) {}
  
  public void processDirectory(File curFile)
  {
    String directory = curFile.getAbsolutePath().substring(val$rootPath.length());
    if (Main.sVerboseMode) {
      System.out.println("Processing Directory: " + directory + " at cluster " + val$fs.getFat().getLastFreeCluster());
    }
    FatLfnDirectory curDir = val$fs.getRoot();
    if (directory.length() > 0)
    {
      File tempFile = new File(directory);
      Stack<String> pathStack = new Stack();
      do
      {
        pathStack.push(tempFile.getName());
      } while (null != (tempFile = tempFile.getParentFile()));
      while (!pathStack.empty())
      {
        String name = (String)pathStack.pop();
        if (0 != name.length())
        {
          FatLfnDirectoryEntry entry = curDir.getEntry(name);
          if (null != entry)
          {
            if (!entry.isDirectory()) {
              throw new RuntimeException("File path not FAT compatible - naming conflict!");
            }
          }
          else {
            try
            {
              if (Main.sVerboseMode) {
                System.out.println("Adding Directory: " + name);
              }
              entry = curDir.addDirectory(name);
            }
            catch (IOException e)
            {
              e.printStackTrace();
              throw new RuntimeException("Error adding directory!");
            }
          }
          try
          {
            curDir = entry.getDirectory();
          }
          catch (IOException e)
          {
            e.printStackTrace();
            throw new RuntimeException("Error getting directory");
          }
        }
      }
    }
    mCurDir.push(curDir);
  }
  
  public void processFile(File curFile)
  {
    FatLfnDirectory curDir = (FatLfnDirectory)mCurDir.peek();
    FatLfnDirectoryEntry entry;
    try
    {
      if (Main.sVerboseMode) {
        System.out.println("Adding file: " + curFile.getAbsolutePath().substring(val$rootPath.length()) + " with length " + curFile.length() + " at cluster " + val$fs.getFat().getLastFreeCluster());
      }
      entry = curDir.addFile(curFile.getName());
    }
    catch (IOException e)
    {
      e.printStackTrace();
      throw new RuntimeException("Error adding file with name: " + curFile.getName());
    }
    ReadableByteChannel channel = null;
    try
    {
      FatFile f = entry.getFile();
      channel = new FileInputStream(curFile).getChannel();
      ByteBuffer buf = ByteBuffer.allocateDirect(524288);
      int numRead = 0;
      long offset = 0L;
      for (;;)
      {
        buf.clear();
        numRead = channel.read(buf);
        if (numRead < 0) {
          break;
        }
        buf.rewind();
        buf.limit(numRead);
        f.write(offset, buf);
        offset += numRead;
      }
      f.flush(); return;
    }
    catch (IOException e)
    {
      e.printStackTrace();
      throw new RuntimeException("Error getting/writing file with name: " + curFile.getName());
    }
    finally
    {
      if (null != channel) {
        try
        {
          channel.close();
        }
        catch (IOException e)
        {
          e.printStackTrace();
        }
      }
    }
  }
  
  public void endDirectory(File dir)
  {
    mCurDir.pop();
  }
}

/* Location:
 * Qualified Name:     com.android.jobb.Main.1
 * Java Class Version: 6 (50.0)
 * JD-Core Version:    0.7.1
 */
package com.android.jobb;

import Twofish.Twofish_Algorithm;
import java.io.IOException;
import java.io.PrintStream;
import java.nio.ByteBuffer;
import java.nio.MappedByteBuffer;
import java.nio.channels.FileChannel;
import java.nio.channels.FileChannel.MapMode;
import java.nio.channels.FileLock;
import java.nio.channels.ReadableByteChannel;
import java.nio.channels.WritableByteChannel;
import java.util.Arrays;

final class EncryptedBlockFile$EncryptedBlockFileChannel
  extends FileChannel
{
  final FileChannel mFC;
  
  protected EncryptedBlockFile$EncryptedBlockFileChannel(EncryptedBlockFile paramEncryptedBlockFile, FileChannel wrappedFC)
  {
    mFC = wrappedFC;
  }
  
  public void force(boolean metaData)
    throws IOException
  {
    mFC.force(metaData);
  }
  
  public FileLock lock(long position, long size, boolean shared)
    throws IOException
  {
    throw new RuntimeException("Lock not implemented");
  }
  
  public MappedByteBuffer map(FileChannel.MapMode mode, long position, long size)
    throws IOException
  {
    throw new RuntimeException("MappedByteBuffer not implemented");
  }
  
  public long position()
    throws IOException
  {
    return mFC.position();
  }
  
  public FileChannel position(long newPosition)
    throws IOException
  {
    mFC.position(newPosition);
    return this;
  }
  
  public int read(ByteBuffer dst)
    throws IOException
  {
    long position = position();
    int read = read(dst, position);
    if (read >= 0)
    {
      position += read;
      position(position);
    }
    return read;
  }
  
  public int read(ByteBuffer dest, long position)
    throws IOException
  {
    int toRead = dest.remaining();
    int targetRead = toRead;
    int numSectors = toRead / 512;
    if (position + toRead > this$0.length()) {
      throw new IOException("reading past end of device");
    }
    int firstSector = (int)position / 512;
    int alignmentOff;
    boolean isMisaligned;
    boolean doubleBuffer;
    if (0 != (alignmentOff = (int)(position % 512L)))
    {
      toRead += alignmentOff;
      numSectors = toRead / 512;
      boolean isMisaligned = true;
      boolean doubleBuffer = true;
      System.out.println("Alignment off reading from sector: " + firstSector);
    }
    else
    {
      isMisaligned = false;
      doubleBuffer = false;
      alignmentOff = 0;
    }
    int partialReadSize;
    boolean isPartial;
    if (0 != (partialReadSize = toRead % 512))
    {
      boolean isPartial = true;
      doubleBuffer = true;
      numSectors = toRead / 512 + 1;
      System.out.println("Partial read from sector: " + firstSector);
    }
    else
    {
      isPartial = false;
    }
    ByteBuffer tempDest;
    ByteBuffer tempDest;
    if (doubleBuffer) {
      tempDest = ByteBuffer.allocate(512);
    } else {
      tempDest = null;
    }
    int lastSector = firstSector + numSectors;
    if (isMisaligned)
    {
      readDecryptedSector(firstSector++, tempDest);
      tempDest.position(alignmentOff);
      if ((firstSector == lastSector) && (isPartial)) {
        tempDest.limit(partialReadSize);
      }
      dest.put(tempDest);
    }
    for (int i = firstSector; i < lastSector; i++) {
      if ((firstSector + 1 == lastSector) && (isPartial))
      {
        readDecryptedSector(i, tempDest);
        tempDest.rewind();
        tempDest.limit(partialReadSize);
        dest.put(tempDest);
      }
      else
      {
        readDecryptedSector(i, dest);
      }
    }
    return targetRead;
  }
  
  public long read(ByteBuffer[] dsts, int offset, int length)
    throws IOException
  {
    throw new RuntimeException("Scattering Channel Read not implemented");
  }
  
  public long size()
    throws IOException
  {
    return mFC.size();
  }
  
  public long transferFrom(ReadableByteChannel src, long position, long count)
    throws IOException
  {
    throw new RuntimeException("File Channel transfer not implemented");
  }
  
  public long transferTo(long position, long count, WritableByteChannel target)
    throws IOException
  {
    throw new RuntimeException("File Channel transfer to not implemented");
  }
  
  public FileChannel truncate(long size)
    throws IOException
  {
    mFC.truncate(size);
    return this;
  }
  
  public FileLock tryLock(long position, long size, boolean shared)
    throws IOException
  {
    return mFC.tryLock(position, size, shared);
  }
  
  public int write(ByteBuffer src)
    throws IOException
  {
    long position = position();
    int write = write(src, position);
    if (write >= 0)
    {
      position += write;
      position(position);
    }
    return write;
  }
  
  public int write(ByteBuffer src, long position)
    throws IOException
  {
    int toWrite = src.remaining();
    int targetWrite = toWrite;
    int firstSector = (int)position / 512;
    int numSectors = toWrite / 512;
    
    boolean fixAccess = false;
    long readOffset;
    if (0L != position % 512L)
    {
      long alignmentOff = position % 512L;
      long readOffset = position - alignmentOff;
      toWrite = (int)(toWrite + alignmentOff);
      numSectors = toWrite / 512;
      fixAccess = true;
      System.out.println("Alignment off writing to sector: " + firstSector);
    }
    else
    {
      readOffset = position;
    }
    if (0 != toWrite % 512)
    {
      numSectors = toWrite / 512 + 1;
      fixAccess = true;
      System.out.println("Partial Sector [" + toWrite % 512 + "] writing to sector: " + firstSector);
    }
    if (fixAccess)
    {
      ByteBuffer dest = ByteBuffer.allocate(numSectors * 512);
      read(dest, readOffset);
      int bufOffset = (int)(position - readOffset);
      dest.position(bufOffset);
      dest.put(src);
      
      src = dest;
      src.rewind();
    }
    int lastSector = firstSector + numSectors;
    for (int i = firstSector; i < lastSector; i++) {
      writeEncryptedSector(i, src);
    }
    return targetWrite;
  }
  
  public long write(ByteBuffer[] srcs, int offset, int length)
    throws IOException
  {
    throw new RuntimeException("Scattering Channel Write not implemented");
  }
  
  protected void implCloseChannel()
    throws IOException
  {}
  
  private void cryptIVPlainGen(int sector, byte[] out)
  {
    Arrays.fill(out, (byte)0);
    out[0] = ((byte)(sector & 0xFF));
    out[1] = ((byte)(sector >> 8 & 0xFF));
    out[2] = ((byte)(sector >> 16 & 0xFF));
    out[3] = ((byte)(sector >>> 24));
  }
  
  private void readDecryptedSector(int sector, ByteBuffer dest)
    throws IOException
  {
    By
1 2 3

Further reading...

For more information on Java 1.5 Tiger, you may find Java 1.5 Tiger, A developer's Notebook by D. Flanagan and B. McLaughlin from O'Reilly of interest.

New!JAR listings


Copyright 2006-2017. Infinite Loop Ltd