public byte[] unwrap(byte[] in, int inoff, int inlen) throws invalidciphertextexception { if (forwrapping) { throw new illegalstateexception("not set for unwrapping"); } int n = inlen / 8; if ((n * 8) != inlen) { throw new invalidciphertextexception("unwrap data must be a multiple of 8 bytes"); } byte[] block = new byte[inlen - iv.length]; byte[] a = new byte[iv.length]; byte[] buf = new byte[8 + iv.length]; system.arraycopy(in, 0, a, 0, iv.length); system.arraycopy(in, iv.length, block, 0, inlen - iv.length); engine.init(false, param); n = n - 1; for (int j = 5; j >= 0; j--) { for (int i = n; i >= 1; i--) { system.arraycopy(a, 0, buf, 0, iv.length); system.arraycopy(block, 8 * (i - 1), buf, iv.length, 8); int t = n * j + i; for (int k = 1; t != 0; k++) { byte v = (byte) t; buf[iv.length - k] ^= v; t >>>= 8; } engine.processblock(buf, 0, buf, 0); system.arraycopy(buf, 0, a, 0, 8); system.arraycopy(buf, 8, block, 8 * (i - 1), 8); } } if (!arrays.constanttimeareequal(a, iv)) { throw new invalidciphertextexception("checksum failed"); } return block; }
public byte[] wrap(byte[] in, int inoff, int inlen) { if (!forwrapping) { throw new illegalstateexception("not set for wrapping"); } int n = inlen / 8; if ((n * 8) != inlen) { throw new datalengthexception("wrap data must be a multiple of 8 bytes"); } byte[] block = new byte[inlen + iv.length]; byte[] buf = new byte[8 + iv.length]; system.arraycopy(iv, 0, block, 0, iv.length); system.arraycopy(in, 0, block, iv.length, inlen); engine.init(true, param); for (int j = 0; j != 6; j++) { for (int i = 1; i <= n; i++) { system.arraycopy(block, 0, buf, 0, iv.length); system.arraycopy(block, 8 * i, buf, iv.length, 8); engine.processblock(buf, 0, buf, 0); int t = n * j + i; for (int k = 1; t != 0; k++) { byte v = (byte) t; buf[iv.length - k] ^= v; t >>>= 8; } system.arraycopy(buf, 0, block, 0, 8); system.arraycopy(buf, 8, block, 8 * i, 8); } } return block; }