⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 rijndael.java

📁 linux下建立JAVA虚拟机的源码KAFFE
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
    int ROUNDS = Ke.length - 1;    int SC = BC == 4 ? 0 : (BC == 6 ? 1 : 2);    int s1 = shifts[SC][1][0];    int s2 = shifts[SC][2][0];    int s3 = shifts[SC][3][0];    int[] a = new int[BC];    int[] t = new int[BC]; // temporary work array    int i, tt;    for (i = 0; i < BC; i++)      { // plaintext to ints + key        t[i] = (in[inOffset++] << 24 | (in[inOffset++] & 0xFF) << 16                | (in[inOffset++] & 0xFF) << 8 | (in[inOffset++] & 0xFF))               ^ Ke[0][i];      }    for (int r = 1; r < ROUNDS; r++)      { // apply round transforms        for (i = 0; i < BC; i++)          {            a[i] = (T1[(t[i] >>> 24)] ^ T2[(t[(i + s1) % BC] >>> 16) & 0xFF]                    ^ T3[(t[(i + s2) % BC] >>> 8) & 0xFF] ^ T4[t[(i + s3) % BC] & 0xFF])                   ^ Ke[r][i];          }        System.arraycopy(a, 0, t, 0, BC);        if (DEBUG && debuglevel > 6)          {            System.out.println("CT" + r + "=" + Util.toString(t));          }      }    for (i = 0; i < BC; i++)      { // last round is special        tt = Ke[ROUNDS][i];        out[outOffset++] = (byte) (S[(t[i] >>> 24)] ^ (tt >>> 24));        out[outOffset++] = (byte) (S[(t[(i + s1) % BC] >>> 16) & 0xFF] ^ (tt >>> 16));        out[outOffset++] = (byte) (S[(t[(i + s2) % BC] >>> 8) & 0xFF] ^ (tt >>> 8));        out[outOffset++] = (byte) (S[t[(i + s3) % BC] & 0xFF] ^ tt);      }    if (DEBUG && debuglevel > 6)      {        System.out.println("CT=" + Util.toString(out, outOffset - bs + 1, bs));        System.out.println();      }  }  private static void rijndaelDecrypt(byte[] in, int inOffset, byte[] out,                                      int outOffset, Object sessionKey, int bs)  {    Object[] sKey = (Object[]) sessionKey; // extract decryption round keys    int[][] Kd = (int[][]) sKey[1];    int BC = bs / 4;    int ROUNDS = Kd.length - 1;    int SC = BC == 4 ? 0 : (BC == 6 ? 1 : 2);    int s1 = shifts[SC][1][1];    int s2 = shifts[SC][2][1];    int s3 = shifts[SC][3][1];    int[] a = new int[BC];    int[] t = new int[BC]; // temporary work array    int i, tt;    for (i = 0; i < BC; i++)      { // ciphertext to ints + key        t[i] = (in[inOffset++] << 24 | (in[inOffset++] & 0xFF) << 16                | (in[inOffset++] & 0xFF) << 8 | (in[inOffset++] & 0xFF))               ^ Kd[0][i];      }    for (int r = 1; r < ROUNDS; r++)      { // apply round transforms        for (i = 0; i < BC; i++)          {            a[i] = (T5[(t[i] >>> 24)] ^ T6[(t[(i + s1) % BC] >>> 16) & 0xFF]                    ^ T7[(t[(i + s2) % BC] >>> 8) & 0xFF] ^ T8[t[(i + s3) % BC] & 0xFF])                   ^ Kd[r][i];          }        System.arraycopy(a, 0, t, 0, BC);        if (DEBUG && debuglevel > 6)          {            System.out.println("PT" + r + "=" + Util.toString(t));          }      }    for (i = 0; i < BC; i++)      { // last round is special        tt = Kd[ROUNDS][i];        out[outOffset++] = (byte) (Si[(t[i] >>> 24)] ^ (tt >>> 24));        out[outOffset++] = (byte) (Si[(t[(i + s1) % BC] >>> 16) & 0xFF] ^ (tt >>> 16));        out[outOffset++] = (byte) (Si[(t[(i + s2) % BC] >>> 8) & 0xFF] ^ (tt >>> 8));        out[outOffset++] = (byte) (Si[t[(i + s3) % BC] & 0xFF] ^ tt);      }    if (DEBUG && debuglevel > 6)      {        System.out.println("PT=" + Util.toString(out, outOffset - bs + 1, bs));        System.out.println();      }  }  private static void aesEncrypt(byte[] in, int i, byte[] out, int j, Object key)  {    int[][] Ke = (int[][]) ((Object[]) key)[0]; // extract encryption round keys    int ROUNDS = Ke.length - 1;    int[] Ker = Ke[0];    // plaintext to ints + key    int t0 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Ker[0];    int t1 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Ker[1];    int t2 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Ker[2];    int t3 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Ker[3];    int a0, a1, a2, a3;    for (int r = 1; r < ROUNDS; r++)      { // apply round transforms        Ker = Ke[r];        a0 = (T1[(t0 >>> 24)] ^ T2[(t1 >>> 16) & 0xFF] ^ T3[(t2 >>> 8) & 0xFF] ^ T4[t3 & 0xFF])             ^ Ker[0];        a1 = (T1[(t1 >>> 24)] ^ T2[(t2 >>> 16) & 0xFF] ^ T3[(t3 >>> 8) & 0xFF] ^ T4[t0 & 0xFF])             ^ Ker[1];        a2 = (T1[(t2 >>> 24)] ^ T2[(t3 >>> 16) & 0xFF] ^ T3[(t0 >>> 8) & 0xFF] ^ T4[t1 & 0xFF])             ^ Ker[2];        a3 = (T1[(t3 >>> 24)] ^ T2[(t0 >>> 16) & 0xFF] ^ T3[(t1 >>> 8) & 0xFF] ^ T4[t2 & 0xFF])             ^ Ker[3];        t0 = a0;        t1 = a1;        t2 = a2;        t3 = a3;        if (DEBUG && debuglevel > 6)          {            System.out.println("CT" + r + "=" + Util.toString(t0)                               + Util.toString(t1) + Util.toString(t2)                               + Util.toString(t3));          }      }    // last round is special    Ker = Ke[ROUNDS];    int tt = Ker[0];    out[j++] = (byte) (S[(t0 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (S[(t1 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (S[(t2 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (S[t3 & 0xFF] ^ tt);    tt = Ker[1];    out[j++] = (byte) (S[(t1 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (S[(t2 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (S[(t3 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (S[t0 & 0xFF] ^ tt);    tt = Ker[2];    out[j++] = (byte) (S[(t2 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (S[(t3 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (S[(t0 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (S[t1 & 0xFF] ^ tt);    tt = Ker[3];    out[j++] = (byte) (S[(t3 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (S[(t0 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (S[(t1 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (S[t2 & 0xFF] ^ tt);    if (DEBUG && debuglevel > 6)      {        System.out.println("CT=" + Util.toString(out, j - 15, 16));        System.out.println();      }  }  private static void aesDecrypt(byte[] in, int i, byte[] out, int j, Object key)  {    int[][] Kd = (int[][]) ((Object[]) key)[1]; // extract decryption round keys    int ROUNDS = Kd.length - 1;    int[] Kdr = Kd[0];    // ciphertext to ints + key    int t0 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Kdr[0];    int t1 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Kdr[1];    int t2 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Kdr[2];    int t3 = (in[i++] << 24 | (in[i++] & 0xFF) << 16 | (in[i++] & 0xFF) << 8 | (in[i++] & 0xFF))             ^ Kdr[3];    int a0, a1, a2, a3;    for (int r = 1; r < ROUNDS; r++)      { // apply round transforms        Kdr = Kd[r];        a0 = (T5[(t0 >>> 24)] ^ T6[(t3 >>> 16) & 0xFF] ^ T7[(t2 >>> 8) & 0xFF] ^ T8[t1 & 0xFF])             ^ Kdr[0];        a1 = (T5[(t1 >>> 24)] ^ T6[(t0 >>> 16) & 0xFF] ^ T7[(t3 >>> 8) & 0xFF] ^ T8[t2 & 0xFF])             ^ Kdr[1];        a2 = (T5[(t2 >>> 24)] ^ T6[(t1 >>> 16) & 0xFF] ^ T7[(t0 >>> 8) & 0xFF] ^ T8[t3 & 0xFF])             ^ Kdr[2];        a3 = (T5[(t3 >>> 24)] ^ T6[(t2 >>> 16) & 0xFF] ^ T7[(t1 >>> 8) & 0xFF] ^ T8[t0 & 0xFF])             ^ Kdr[3];        t0 = a0;        t1 = a1;        t2 = a2;        t3 = a3;        if (DEBUG && debuglevel > 6)          {            System.out.println("PT" + r + "=" + Util.toString(t0)                               + Util.toString(t1) + Util.toString(t2)                               + Util.toString(t3));          }      }    // last round is special    Kdr = Kd[ROUNDS];    int tt = Kdr[0];    out[j++] = (byte) (Si[(t0 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (Si[(t3 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (Si[(t2 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (Si[t1 & 0xFF] ^ tt);    tt = Kdr[1];    out[j++] = (byte) (Si[(t1 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (Si[(t0 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (Si[(t3 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (Si[t2 & 0xFF] ^ tt);    tt = Kdr[2];    out[j++] = (byte) (Si[(t2 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (Si[(t1 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (Si[(t0 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (Si[t3 & 0xFF] ^ tt);    tt = Kdr[3];    out[j++] = (byte) (Si[(t3 >>> 24)] ^ (tt >>> 24));    out[j++] = (byte) (Si[(t2 >>> 16) & 0xFF] ^ (tt >>> 16));    out[j++] = (byte) (Si[(t1 >>> 8) & 0xFF] ^ (tt >>> 8));    out[j++] = (byte) (Si[t0 & 0xFF] ^ tt);    if (DEBUG && debuglevel > 6)      {        System.out.println("PT=" + Util.toString(out, j - 15, 16));        System.out.println();      }  }  // Instance methods  // -------------------------------------------------------------------------  // java.lang.Cloneable interface implementation ----------------------------  public Object clone()  {    Rijndael result = new Rijndael();    result.currentBlockSize = this.currentBlockSize;    return result;  }  // IBlockCipherSpi interface implementation --------------------------------  public Iterator blockSizes()  {    ArrayList al = new ArrayList();    al.add(new Integer(128 / 8));    al.add(new Integer(192 / 8));    al.add(new Integer(256 / 8));    return Collections.unmodifiableList(al).iterator();  }  public Iterator keySizes()  {    ArrayList al = new ArrayList();    al.add(new Integer(128 / 8));    al.add(new Integer(192 / 8));    al.add(new Integer(256 / 8));    return Collections.unmodifiableList(al).iterator();  }  /**   * Expands a user-supplied key material into a session key for a designated   * <i>block size</i>.   *   * @param k the 128/192/256-bit user-key to use.   * @param bs the block size in bytes of this Rijndael.   * @return an Object encapsulating the session key.   * @exception IllegalArgumentException if the block size is not 16, 24 or 32.   * @exception InvalidKeyException if the key data is invalid.   */  public Object makeKey(byte[] k, int bs) throws InvalidKeyException  {    if (k == null)      {        throw new InvalidKeyException("Empty key");      }    if (!(k.length == 16 || k.length == 24 || k.length == 32))      {        throw new InvalidKeyException("Incorrect key length");      }    if (!(bs == 16 || bs == 24 || bs == 32))      {        throw new IllegalArgumentException();      }    int ROUNDS = getRounds(k.length, bs);    int BC = bs / 4;    int[][] Ke = new int[ROUNDS + 1][BC]; // encryption round keys    int[][] Kd = new int[ROUNDS + 1][BC]; // decryption round keys    int ROUND_KEY_COUNT = (ROUNDS + 1) * BC;    int KC = k.length / 4;    int[] tk = new int[KC];    int i, j;    // copy user material bytes into temporary ints    for (i = 0, j = 0; i < KC;)      {        tk[i++] = k[j++] << 24 | (k[j++] & 0xFF) << 16 | (k[j++] & 0xFF) << 8                  | (k[j++] & 0xFF);      }    // copy values into round key arrays    int t = 0;    for (j = 0; (j < KC) && (t < ROUND_KEY_COUNT); j++, t++)      {        Ke[t / BC][t % BC] = tk[j];        Kd[ROUNDS - (t / BC)][t % BC] = tk[j];      }    int tt, rconpointer = 0;    while (t < ROUND_KEY_COUNT)      {        // extrapolate using phi (the round key evolution function)        tt = tk[KC - 1];        tk[0] ^= (S[(tt >>> 16) & 0xFF] & 0xFF) << 24                 ^ (S[(tt >>> 8) & 0xFF] & 0xFF) << 16                 ^ (S[tt & 0xFF] & 0xFF) << 8 ^ (S[(tt >>> 24)] & 0xFF)                 ^ rcon[rconpointer++] << 24;        if (KC != 8)          {            for (i = 1, j = 0; i < KC;)              {                tk[i++] ^= tk[j++];              }          }        else          {            for (i = 1, j = 0; i < KC / 2;)              {                tk[i++] ^= tk[j++];              }            tt = tk[KC / 2 - 1];            tk[KC / 2] ^= (S[tt & 0xFF] & 0xFF)                          ^ (S[(tt >>> 8) & 0xFF] & 0xFF) << 8                          ^ (S[(tt >>> 16) & 0xFF] & 0xFF) << 16                          ^ S[(tt >>> 24) & 0xFF] << 24;            for (j = KC / 2, i = j + 1; i < KC;)              {                tk[i++] ^= tk[j++];              }          }        // copy values into round key arrays        for (j = 0; (j < KC) && (t < ROUND_KEY_COUNT); j++, t++)          {            Ke[t / BC][t % BC] = tk[j];            Kd[ROUNDS - (t / BC)][t % BC] = tk[j];          }      }    for (int r = 1; r < ROUNDS; r++)      { // inverse MixColumn where needed        for (j = 0; j < BC; j++)          {            tt = Kd[r][j];            Kd[r][j] = U1[(tt >>> 24)] ^ U2[(tt >>> 16) & 0xFF]                       ^ U3[(tt >>> 8) & 0xFF] ^ U4[tt & 0xFF];          }      }    return new Object[] { Ke, Kd };  }  public void encrypt(byte[] in, int i, byte[] out, int j, Object k, int bs)  {    if (!(bs == 16 || bs == 24 || bs == 32))      {        throw new IllegalArgumentException();      }    if (bs == DEFAULT_BLOCK_SIZE)      {        aesEncrypt(in, i, out, j, k);      }    else      {        rijndaelEncrypt(in, i, out, j, k, bs);      }  }  public void decrypt(byte[] in, int i, byte[] out, int j, Object k, int bs)  {    if (!(bs == 16 || bs == 24 || bs == 32))      {        throw new IllegalArgumentException();      }    if (bs == DEFAULT_BLOCK_SIZE)      {        aesDecrypt(in, i, out, j, k);      }    else      {        rijndaelDecrypt(in, i, out, j, k, bs);      }  }  public boolean selfTest()  {    if (valid == null)      {        boolean result = super.selfTest(); // do symmetry tests        if (result)          {            result = testKat(KAT_KEY, KAT_CT);          }        valid = new Boolean(result);      }    return valid.booleanValue();  }}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -