001: /*
002: *
003: *
004: * Copyright 1990-2007 Sun Microsystems, Inc. All Rights Reserved.
005: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER
006: *
007: * This program is free software; you can redistribute it and/or
008: * modify it under the terms of the GNU General Public License version
009: * 2 only, as published by the Free Software Foundation.
010: *
011: * This program is distributed in the hope that it will be useful, but
012: * WITHOUT ANY WARRANTY; without even the implied warranty of
013: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
014: * General Public License version 2 for more details (a copy is
015: * included at /legal/license.txt).
016: *
017: * You should have received a copy of the GNU General Public License
018: * version 2 along with this work; if not, write to the Free Software
019: * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020: * 02110-1301 USA
021: *
022: * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
023: * Clara, CA 95054 or visit www.sun.com if you need additional
024: * information or have any questions.
025: */
026:
027: package com.sun.midp.crypto;
028:
029: /**
030: * AES CBC Cipher.
031: */
032: public class AES_CBC extends AES_ECB {
033:
034: /** Internal buffer. */
035: private byte[] scratchPad;
036:
037: /** Saved internal buffer. */
038: private byte[] savedState;
039:
040: /**
041: * Constructor.
042: */
043: public AES_CBC() {
044: super ();
045: scratchPad = new byte[BLOCK_SIZE];
046: }
047:
048: /**
049: * Initializes this cipher with a key and a set of algorithm
050: * parameters.
051: * @param mode the operation mode of this cipher
052: * @param key the encryption key
053: * @param params the algorithm parameters
054: * @exception java.security.InvalidKeyException if the given key
055: * is inappropriate for initializing this cipher
056: * @exception java.security.InvalidAlgorithmParameterException
057: * if the given algorithm parameters are inappropriate for this cipher
058: */
059: public void init(int mode, Key key, CryptoParameter params)
060: throws InvalidKeyException,
061: InvalidAlgorithmParameterException {
062: doInit(mode, "AES", key, true, params);
063: System.arraycopy(IV, 0, state, 0, BLOCK_SIZE);
064: }
065:
066: /**
067: * Encrypts or decrypts data in a single-part operation, or finishes a
068: * multiple-part operation. The data is encrypted or decrypted,
069: * depending on how this cipher was initialized.
070: *
071: * @param inBuff the input buffer
072: * @param inOffset the offset in <code>input</code> where the input
073: * starts
074: * @param inLength the input length
075: * @param outBuff the buffer for the result
076: * @param outOffset the offset in <code>output</code> where the result
077: * is stored
078: *
079: * @return the number of bytes stored in <code>output</code>
080: *
081: * @exception IllegalStateException if this cipher is in a wrong state
082: * (e.g., has not been initialized)
083: * @exception javax.crypto.IllegalBlockSizeException if this cipher is a
084: * block cipher,
085: * no padding has been requested (only in encryption mode), and the total
086: * input length of the data processed by this cipher is not a multiple of
087: * block size
088: * @exception javax.crypto.ShortBufferException if the given output buffer
089: * is too small to hold the result
090: * @exception javax.crypto.BadPaddingException if this cipher is in
091: * decryption mode,
092: * and (un)padding has been requested, but the decrypted data is not
093: * bounded by the appropriate padding bytes
094: */
095: public int doFinal(byte inBuff[], int inOffset, int inLength,
096: byte outBuff[], int outOffset)
097: throws IllegalStateException, IllegalBlockSizeException,
098: ShortBufferException, BadPaddingException {
099: int result = super .doFinal(inBuff, inOffset, inLength, outBuff,
100: outOffset);
101: System.arraycopy(IV, 0, state, 0, BLOCK_SIZE);
102: return result;
103: }
104:
105: /**
106: * Depending on the mode, either encrypts or decrypts one block.
107: * @param out will contain the result of encryption
108: * or decryption operation
109: * @param offset is the offset in out
110: */
111: protected void processBlock(byte[] out, int offset) {
112:
113: if (mode == Cipher.ENCRYPT_MODE) {
114: Util.xorArrays(holdData, state);
115: cipherBlock();
116: System.arraycopy(state, 0, out, offset, BLOCK_SIZE);
117: } else {
118: System.arraycopy(state, 0, scratchPad, 0, BLOCK_SIZE);
119: decipherBlock();
120: Util.xorArrays(state, scratchPad);
121: System.arraycopy(state, 0, out, offset, BLOCK_SIZE);
122: System.arraycopy(holdData, 0, state, 0, BLOCK_SIZE);
123: }
124: holdCount = 0;
125: }
126:
127: /**
128: * Saves internal state.
129: */
130: protected void saveState() {
131: super .saveState();
132: savedState = Util.cloneArray(state);
133: }
134:
135: /**
136: * Restores internal state.
137: */
138: protected void restoreState() {
139: super.restoreState();
140: state = savedState;
141: }
142: }
|