Home | History | Annotate | Download | only in crypto
      1 /*
      2  * Copyright (C) 2014 The Android Open Source Project
      3  * Copyright (c) 1997, 2012, Oracle and/or its affiliates. All rights reserved.
      4  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
      5  *
      6  * This code is free software; you can redistribute it and/or modify it
      7  * under the terms of the GNU General Public License version 2 only, as
      8  * published by the Free Software Foundation.  Oracle designates this
      9  * particular file as subject to the "Classpath" exception as provided
     10  * by Oracle in the LICENSE file that accompanied this code.
     11  *
     12  * This code is distributed in the hope that it will be useful, but WITHOUT
     13  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
     14  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
     15  * version 2 for more details (a copy is included in the LICENSE file that
     16  * accompanied this code).
     17  *
     18  * You should have received a copy of the GNU General Public License version
     19  * 2 along with this work; if not, write to the Free Software Foundation,
     20  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
     21  *
     22  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
     23  * or visit www.oracle.com if you need additional information or have any
     24  * questions.
     25  */
     26 
     27 package javax.crypto;
     28 
     29 import java.util.*;
     30 import java.util.concurrent.ConcurrentHashMap;
     31 import java.util.concurrent.ConcurrentMap;
     32 import java.util.regex.*;
     33 
     34 import static java.util.Locale.ENGLISH;
     35 
     36 import java.security.*;
     37 import java.security.Provider.Service;
     38 import java.security.spec.AlgorithmParameterSpec;
     39 import java.security.spec.InvalidParameterSpecException;
     40 import java.security.cert.Certificate;
     41 import java.security.cert.X509Certificate;
     42 
     43 import javax.crypto.spec.*;
     44 
     45 import java.nio.ByteBuffer;
     46 import java.nio.ReadOnlyBufferException;
     47 import sun.security.jca.*;
     48 
     49 /**
     50  * This class provides the functionality of a cryptographic cipher for
     51  * encryption and decryption. It forms the core of the Java Cryptographic
     52  * Extension (JCE) framework.
     53  *
     54  * <p>In order to create a Cipher object, the application calls the
     55  * Cipher's <code>getInstance</code> method, and passes the name of the
     56  * requested <i>transformation</i> to it. Optionally, the name of a provider
     57  * may be specified.
     58  *
     59  * <p>A <i>transformation</i> is a string that describes the operation (or
     60  * set of operations) to be performed on the given input, to produce some
     61  * output. A transformation always includes the name of a cryptographic
     62  * algorithm (e.g., <i>DES</i>), and may be followed by a feedback mode and
     63  * padding scheme.
     64  *
     65  * <p> A transformation is of the form:
     66  *
     67  * <ul>
     68  * <li>"<i>algorithm/mode/padding</i>" or
     69  *
     70  * <li>"<i>algorithm</i>"
     71  * </ul>
     72  *
     73  * <P> (in the latter case,
     74  * provider-specific default values for the mode and padding scheme are used).
     75  * For example, the following is a valid transformation:
     76  *
     77  * <pre>
     78  *     Cipher c = Cipher.getInstance("<i>DES/CBC/PKCS5Padding</i>");
     79  * </pre>
     80  *
     81  * Using modes such as <code>CFB</code> and <code>OFB</code>, block
     82  * ciphers can encrypt data in units smaller than the cipher's actual
     83  * block size.  When requesting such a mode, you may optionally specify
     84  * the number of bits to be processed at a time by appending this number
     85  * to the mode name as shown in the "<code>DES/CFB8/NoPadding</code>" and
     86  * "<code>DES/OFB32/PKCS5Padding</code>" transformations. If no such
     87  * number is specified, a provider-specific default is used. (For
     88  * example, the SunJCE provider uses a default of 64 bits for DES.)
     89  * Thus, block ciphers can be turned into byte-oriented stream ciphers by
     90  * using an 8 bit mode such as CFB8 or OFB8.
     91  * <p>
     92  * Modes such as Authenticated Encryption with Associated Data (AEAD)
     93  * provide authenticity assurances for both confidential data and
     94  * Additional Associated Data (AAD) that is not encrypted.  (Please see
     95  * <a href="http://www.ietf.org/rfc/rfc5116.txt"> RFC 5116 </a> for more
     96  * information on AEAD and AEAD algorithms such as GCM/CCM.) Both
     97  * confidential and AAD data can be used when calculating the
     98  * authentication tag (similar to a {@link Mac}).  This tag is appended
     99  * to the ciphertext during encryption, and is verified on decryption.
    100  * <p>
    101  * AEAD modes such as GCM/CCM perform all AAD authenticity calculations
    102  * before starting the ciphertext authenticity calculations.  To avoid
    103  * implementations having to internally buffer ciphertext, all AAD data
    104  * must be supplied to GCM/CCM implementations (via the {@code
    105  * updateAAD} methods) <b>before</b> the ciphertext is processed (via
    106  * the {@code update} and {@code doFinal} methods).
    107  * <p>
    108  * Note that GCM mode has a uniqueness requirement on IVs used in
    109  * encryption with a given key. When IVs are repeated for GCM
    110  * encryption, such usages are subject to forgery attacks. Thus, after
    111  * each encryption operation using GCM mode, callers should re-initialize
    112  * the cipher objects with GCM parameters which has a different IV value.
    113  * <pre>
    114  *     GCMParameterSpec s = ...;
    115  *     cipher.init(..., s);
    116  *
    117  *     // If the GCM parameters were generated by the provider, it can
    118  *     // be retrieved by:
    119  *     // cipher.getParameters().getParameterSpec(GCMParameterSpec.class);
    120  *
    121  *     cipher.updateAAD(...);  // AAD
    122  *     cipher.update(...);     // Multi-part update
    123  *     cipher.doFinal(...);    // conclusion of operation
    124  *
    125  *     // Use a different IV value for every encryption
    126  *     byte[] newIv = ...;
    127  *     s = new GCMParameterSpec(s.getTLen(), newIv);
    128  *     cipher.init(..., s);
    129  *     ...
    130  *
    131  * </pre>
    132  * <p> Android provides the following <code>Cipher</code> transformations:
    133  * <table>
    134  *   <thead>
    135  *     <tr>
    136  *       <th>Algorithm</th>
    137  *       <th>Modes</th>
    138  *       <th>Paddings</th>
    139  *       <th>Supported API Levels</th>
    140  *     </tr>
    141  *   </thead>
    142  *   <tbody>
    143  *     <tr>
    144  *       <td rowspan="2">AES</td>
    145  *       <td>CBC<br>CFB<br>CTR<br>CTS<br>ECB<br>OFB</td>
    146  *       <td>ISO10126Padding<br>NoPadding<br>PKCS5Padding</td>
    147  *       <td>1+</td>
    148  *     </tr>
    149  *     <tr>
    150  *       <td>GCM</td>
    151  *       <td>NOPADDING</td>
    152  *       <td>10+</td>
    153  *     </tr>
    154  *     <tr>
    155  *       <td rowspan="2">AES_128</td>
    156  *       <td>CBC<br>ECB</td>
    157  *       <td>NoPadding<br>PKCS5Padding</td>
    158  *       <td>26+</td>
    159  *     </tr>
    160  *     <tr>
    161  *       <td>GCM</td>
    162  *       <td>NoPadding</td>
    163  *       <td>26+</td>
    164  *     </tr>
    165  *     <tr>
    166  *       <td rowspan="2">AES_256</td>
    167  *       <td>CBC<br>ECB</td>
    168  *       <td>NoPadding<br>PKCS5Padding</td>
    169  *       <td>26+</td>
    170  *     </tr>
    171  *     <tr>
    172  *       <td>GCM</td>
    173  *       <td>NoPadding</td>
    174  *       <td>26+</td>
    175  *     </tr>
    176  *     <tr>
    177  *       <td>ARC4</td>
    178  *       <td>ECB</td>
    179  *       <td>NoPadding</td>
    180  *       <td>10+</td>
    181  *     </tr>
    182  *     <tr>
    183  *       <td>BLOWFISH</td>
    184  *       <td>CBC<br>CFB<br>CTR<br>CTS<br>ECB<br>OFB</td>
    185  *       <td>ISO10126Padding<br>NoPadding<br>PKCS5Padding</td>
    186  *       <td>10+</td>
    187  *     </tr>
    188  *     <tr>
    189  *       <td>DES</td>
    190  *       <td>CBC<br>CFB<br>CTR<br>CTS<br>ECB<br>OFB</td>
    191  *       <td>ISO10126Padding<br>NoPadding<br>PKCS5Padding</td>
    192  *       <td>1+</td>
    193  *     </tr>
    194  *     <tr>
    195  *       <td>DESede</td>
    196  *       <td>CBC<br>CFB<br>CTR<br>CTS<br>ECB<br>OFB</td>
    197  *       <td>ISO10126Padding<br>NoPadding<br>PKCS5Padding</td>
    198  *       <td>1+</td>
    199  *     </tr>
    200  *     <tr>
    201  *       <td rowspan="3">RSA</td>
    202  *       <td rowspan="3">ECB<br>NONE</td>
    203  *       <td>NoPadding<br>OAEPPadding<br>PKCS1Padding</td>
    204  *       <td>1+</td>
    205  *     </tr>
    206  *     <tr>
    207  *       <td>OAEPwithSHA-1andMGF1Padding<br>OAEPwithSHA-256andMGF1Padding</td>
    208  *       <td>10+</td>
    209  *     </tr>
    210  *     <tr>
    211  *       <td>OAEPwithSHA-224andMGF1Padding<br>OAEPwithSHA-384andMGF1Padding<br>OAEPwithSHA-512andMGF1Padding</td>
    212  *       <td>23+</td>
    213  *     </tr>
    214  *   </tbody>
    215  * </table>
    216  *
    217  * These transformations are described in the
    218  * <a href="{@docRoot}openjdk-redirect.html?v=8&path=/technotes/guides/security/StandardNames.html#Cipher">
    219  * Cipher section</a> of the
    220  * Java Cryptography Architecture Standard Algorithm Name Documentation.
    221  *
    222  * @author Jan Luehe
    223  * @see KeyGenerator
    224  * @see SecretKey
    225  * @since 1.4
    226  */
    227 
    228 public class Cipher {
    229 
    230     // Android-removed: this debugging mechanism is not used in Android.
    231     /*
    232     private static final Debug debug =
    233                         Debug.getInstance("jca", "Cipher");
    234 
    235     private static final Debug pdebug =
    236                         Debug.getInstance("provider", "Provider");
    237     private static final boolean skipDebug =
    238         Debug.isOn("engine=") && !Debug.isOn("cipher");
    239     */
    240 
    241     /**
    242      * Constant used to initialize cipher to encryption mode.
    243      */
    244     public static final int ENCRYPT_MODE = 1;
    245 
    246     /**
    247      * Constant used to initialize cipher to decryption mode.
    248      */
    249     public static final int DECRYPT_MODE = 2;
    250 
    251     /**
    252      * Constant used to initialize cipher to key-wrapping mode.
    253      */
    254     public static final int WRAP_MODE = 3;
    255 
    256     /**
    257      * Constant used to initialize cipher to key-unwrapping mode.
    258      */
    259     public static final int UNWRAP_MODE = 4;
    260 
    261     /**
    262      * Constant used to indicate the to-be-unwrapped key is a "public key".
    263      */
    264     public static final int PUBLIC_KEY = 1;
    265 
    266     /**
    267      * Constant used to indicate the to-be-unwrapped key is a "private key".
    268      */
    269     public static final int PRIVATE_KEY = 2;
    270 
    271     /**
    272      * Constant used to indicate the to-be-unwrapped key is a "secret key".
    273      */
    274     public static final int SECRET_KEY = 3;
    275 
    276     // The provider
    277     private Provider provider;
    278 
    279     // The provider implementation (delegate)
    280     private CipherSpi spi;
    281 
    282     // The transformation
    283     final private String transformation;
    284 
    285     // The tokenized version of transformation
    286     final private String[] tokenizedTransformation;
    287 
    288     // The exemption mechanism that needs to be enforced
    289     private ExemptionMechanism exmech;
    290 
    291     // Flag which indicates whether or not this cipher has been initialized
    292     private boolean initialized = false;
    293 
    294     // The operation mode - store the operation mode after the
    295     // cipher has been initialized.
    296     private int opmode = 0;
    297 
    298     // The OID for the KeyUsage extension in an X.509 v3 certificate
    299     private static final String KEY_USAGE_EXTENSION_OID = "2.5.29.15";
    300 
    301     private final SpiAndProviderUpdater spiAndProviderUpdater;
    302 
    303 
    304     /**
    305      * Creates a Cipher object.
    306      *
    307      * @param cipherSpi the delegate
    308      * @param provider the provider
    309      * @param transformation the transformation
    310      */
    311     protected Cipher(CipherSpi cipherSpi,
    312                      Provider provider,
    313                      String transformation) {
    314         if (cipherSpi == null) {
    315             throw new NullPointerException("cipherSpi == null");
    316         }
    317         if (!(cipherSpi instanceof NullCipherSpi) && provider == null) {
    318             throw new NullPointerException("provider == null");
    319         }
    320 
    321         this.spi = cipherSpi;
    322         this.provider = provider;
    323         this.transformation = transformation;
    324         this.tokenizedTransformation = null;
    325 
    326         this.spiAndProviderUpdater =
    327             new SpiAndProviderUpdater(provider, cipherSpi);
    328     }
    329 
    330     private Cipher(CipherSpi cipherSpi,
    331                    Provider provider,
    332                    String transformation,
    333                    String[] tokenizedTransformation) {
    334         this.spi = cipherSpi;
    335         this.provider = provider;
    336         this.transformation = transformation;
    337         this.tokenizedTransformation = tokenizedTransformation;
    338 
    339         this.spiAndProviderUpdater =
    340             new SpiAndProviderUpdater(provider, cipherSpi);
    341     }
    342 
    343     private static String[] tokenizeTransformation(String transformation)
    344             throws NoSuchAlgorithmException {
    345         if (transformation == null || transformation.isEmpty()) {
    346             throw new NoSuchAlgorithmException("No transformation given");
    347         }
    348         /*
    349          * array containing the components of a Cipher transformation:
    350          *
    351          * index 0: algorithm component (e.g., DES)
    352          * index 1: feedback component (e.g., CFB)
    353          * index 2: padding component (e.g., PKCS5Padding)
    354          */
    355         String[] parts = new String[3];
    356         int count = 0;
    357         StringTokenizer parser = new StringTokenizer(transformation, "/");
    358         try {
    359             while (parser.hasMoreTokens() && count < 3) {
    360                 parts[count++] = parser.nextToken().trim();
    361             }
    362             if (count == 0 || count == 2 || parser.hasMoreTokens()) {
    363                 throw new NoSuchAlgorithmException("Invalid transformation"
    364                                                + " format:" +
    365                                                transformation);
    366             }
    367         } catch (NoSuchElementException e) {
    368             throw new NoSuchAlgorithmException("Invalid transformation " +
    369                                            "format:" + transformation);
    370         }
    371         if ((parts[0] == null) || (parts[0].length() == 0)) {
    372             throw new NoSuchAlgorithmException("Invalid transformation:" +
    373                                    "algorithm not specified-"
    374                                    + transformation);
    375         }
    376         return parts;
    377     }
    378 
    379     /**
    380      * Returns a <code>Cipher</code> object that implements the specified
    381      * transformation.
    382      *
    383      * <p> This method traverses the list of registered security Providers,
    384      * starting with the most preferred Provider.
    385      * A new Cipher object encapsulating the
    386      * CipherSpi implementation from the first
    387      * Provider that supports the specified algorithm is returned.
    388      *
    389      * <p> Note that the list of registered providers may be retrieved via
    390      * the {@link Security#getProviders() Security.getProviders()} method.
    391      *
    392      * @param transformation the name of the transformation, e.g.,
    393      * <i>DES/CBC/PKCS5Padding</i>.
    394      * See the Cipher section in the <a href=
    395      *   "{@docRoot}openjdk-redirect.html?v=8&path=/technotes/guides/security/StandardNames.html#Cipher">
    396      * Java Cryptography Architecture Standard Algorithm Name Documentation</a>
    397      * for information about standard transformation names.
    398      *
    399      * @return a cipher that implements the requested transformation.
    400      *
    401      * @exception NoSuchAlgorithmException if <code>transformation</code>
    402      *          is null, empty, in an invalid format,
    403      *          or if no Provider supports a CipherSpi implementation for the
    404      *          specified algorithm.
    405      *
    406      * @exception NoSuchPaddingException if <code>transformation</code>
    407      *          contains a padding scheme that is not available.
    408      *
    409      * @see java.security.Provider
    410      */
    411     public static final Cipher getInstance(String transformation)
    412             throws NoSuchAlgorithmException, NoSuchPaddingException
    413     {
    414         return createCipher(transformation, null);
    415     }
    416 
    417     /**
    418      * Returns a <code>Cipher</code> object that implements the specified
    419      * transformation.
    420      *
    421      * <p> A new Cipher object encapsulating the
    422      * CipherSpi implementation from the specified provider
    423      * is returned.  The specified provider must be registered
    424      * in the security provider list.
    425      *
    426      * <p> Note that the list of registered providers may be retrieved via
    427      * the {@link Security#getProviders() Security.getProviders()} method.
    428      *
    429      * @param transformation the name of the transformation,
    430      * e.g., <i>DES/CBC/PKCS5Padding</i>.
    431      * See the Cipher section in the <a href=
    432      *   "{@docRoot}openjdk-redirect.html?v=8&path=/technotes/guides/security/StandardNames.html#Cipher">
    433      * Java Cryptography Architecture Standard Algorithm Name Documentation</a>
    434      * for information about standard transformation names.
    435      *
    436      * @param provider the name of the provider.
    437      *
    438      * @return a cipher that implements the requested transformation.
    439      *
    440      * @exception NoSuchAlgorithmException if <code>transformation</code>
    441      *          is null, empty, in an invalid format,
    442      *          or if a CipherSpi implementation for the specified algorithm
    443      *          is not available from the specified provider.
    444      *
    445      * @exception NoSuchProviderException if the specified provider is not
    446      *          registered in the security provider list.
    447      *
    448      * @exception NoSuchPaddingException if <code>transformation</code>
    449      *          contains a padding scheme that is not available.
    450      *
    451      * @exception IllegalArgumentException if the <code>provider</code>
    452      *          is null or empty.
    453      *
    454      * @see java.security.Provider
    455      */
    456     public static final Cipher getInstance(String transformation,
    457                                            String provider)
    458             throws NoSuchAlgorithmException, NoSuchProviderException,
    459             NoSuchPaddingException
    460     {
    461         if ((provider == null) || (provider.length() == 0)) {
    462             throw new IllegalArgumentException("Missing provider");
    463         }
    464         Provider p = Security.getProvider(provider);
    465         if (p == null) {
    466             throw new NoSuchProviderException("No such provider: " +
    467                                               provider);
    468         }
    469         return createCipher(transformation, p);
    470     }
    471 
    472     /**
    473      * Returns a <code>Cipher</code> object that implements the specified
    474      * transformation.
    475      *
    476      * <p> A new Cipher object encapsulating the
    477      * CipherSpi implementation from the specified Provider
    478      * object is returned.  Note that the specified Provider object
    479      * does not have to be registered in the provider list.
    480      *
    481      * @param transformation the name of the transformation,
    482      * e.g., <i>DES/CBC/PKCS5Padding</i>.
    483      * See the Cipher section in the <a href=
    484      *   "{@docRoot}openjdk-redirect.html?v=8&path=/technotes/guides/security/StandardNames.html#Cipher">
    485      * Java Cryptography Architecture Standard Algorithm Name Documentation</a>
    486      * for information about standard transformation names.
    487      *
    488      * @param provider the provider.
    489      *
    490      * @return a cipher that implements the requested transformation.
    491      *
    492      * @exception NoSuchAlgorithmException if <code>transformation</code>
    493      *          is null, empty, in an invalid format,
    494      *          or if a CipherSpi implementation for the specified algorithm
    495      *          is not available from the specified Provider object.
    496      *
    497      * @exception NoSuchPaddingException if <code>transformation</code>
    498      *          contains a padding scheme that is not available.
    499      *
    500      * @exception IllegalArgumentException if the <code>provider</code>
    501      *          is null.
    502      *
    503      * @see java.security.Provider
    504      */
    505     public static final Cipher getInstance(String transformation,
    506                                            Provider provider)
    507             throws NoSuchAlgorithmException, NoSuchPaddingException
    508     {
    509         if (provider == null) {
    510             throw new IllegalArgumentException("Missing provider");
    511         }
    512         return createCipher(transformation, provider);
    513     }
    514 
    515     static final Cipher createCipher(String transformation, Provider provider)
    516         throws NoSuchAlgorithmException, NoSuchPaddingException {
    517         String[] tokenizedTransformation = tokenizeTransformation(transformation);
    518 
    519         CipherSpiAndProvider cipherSpiAndProvider = null;
    520         try {
    521             cipherSpiAndProvider =
    522                 tryCombinations(null /*params*/, provider, tokenizedTransformation);
    523         } catch (InvalidKeyException | InvalidAlgorithmParameterException e) {
    524             // Shouldn't happen.
    525             throw new IllegalStateException("Key/Algorithm excepton despite not passing one", e);
    526         }
    527 
    528         if (cipherSpiAndProvider == null) {
    529             if (provider == null) {
    530                 throw new NoSuchAlgorithmException("No provider found for " + transformation);
    531             } else {
    532                 throw new NoSuchAlgorithmException("Provider " + provider.getName()
    533                         + " does not provide " + transformation);
    534             }
    535         }
    536 
    537         // exceptions and stuff
    538         return new Cipher(null, provider, transformation, tokenizedTransformation);
    539     }
    540 
    541     /**
    542      * Choose the Spi from the first provider available. Used if
    543      * delayed provider selection is not possible because init()
    544      * is not the first method called.
    545      */
    546     void updateProviderIfNeeded() {
    547         try {
    548             spiAndProviderUpdater.updateAndGetSpiAndProvider(null, spi, provider);
    549         } catch (Exception lastException) {
    550             ProviderException e = new ProviderException
    551                     ("Could not construct CipherSpi instance");
    552             if (lastException != null) {
    553                 e.initCause(lastException);
    554             }
    555             throw e;
    556         }
    557     }
    558 
    559     private void chooseProvider(InitType initType, int opmode, Key key,
    560             AlgorithmParameterSpec paramSpec,
    561             AlgorithmParameters params, SecureRandom random)
    562             throws InvalidKeyException, InvalidAlgorithmParameterException {
    563 
    564         try {
    565             final InitParams initParams = new InitParams(initType, opmode, key, random,
    566                                                          paramSpec, params);
    567             spiAndProviderUpdater.updateAndGetSpiAndProvider(initParams, spi, provider);
    568         } catch (Exception lastException) {
    569             // no working provider found, fail
    570             if (lastException instanceof InvalidKeyException) {
    571                 throw (InvalidKeyException)lastException;
    572             }
    573             if (lastException instanceof InvalidAlgorithmParameterException) {
    574                 throw (InvalidAlgorithmParameterException)lastException;
    575             }
    576             if (lastException instanceof RuntimeException) {
    577                 throw (RuntimeException)lastException;
    578             }
    579             String kName = (key != null) ? key.getClass().getName() : "(null)";
    580             throw new InvalidKeyException
    581                 ("No installed provider supports this key: "
    582                 + kName, lastException);
    583         }
    584     }
    585 
    586     /**
    587      * Returns the provider of this <code>Cipher</code> object.
    588      *
    589      * @return the provider of this <code>Cipher</code> object
    590      */
    591     public final Provider getProvider() {
    592         updateProviderIfNeeded();
    593         return this.provider;
    594     }
    595 
    596     /**
    597      * Returns the algorithm name of this <code>Cipher</code> object.
    598      *
    599      * <p>This is the same name that was specified in one of the
    600      * <code>getInstance</code> calls that created this <code>Cipher</code>
    601      * object..
    602      *
    603      * @return the algorithm name of this <code>Cipher</code> object.
    604      */
    605     public final String getAlgorithm() {
    606         return this.transformation;
    607     }
    608 
    609     /**
    610      * Returns the block size (in bytes).
    611      *
    612      * @return the block size (in bytes), or 0 if the underlying algorithm is
    613      * not a block cipher
    614      */
    615     public final int getBlockSize() {
    616         updateProviderIfNeeded();
    617         return spi.engineGetBlockSize();
    618     }
    619 
    620     /**
    621      * Returns the length in bytes that an output buffer would need to be in
    622      * order to hold the result of the next <code>update</code> or
    623      * <code>doFinal</code> operation, given the input length
    624      * <code>inputLen</code> (in bytes).
    625      *
    626      * <p>This call takes into account any unprocessed (buffered) data from a
    627      * previous <code>update</code> call, padding, and AEAD tagging.
    628      *
    629      * <p>The actual output length of the next <code>update</code> or
    630      * <code>doFinal</code> call may be smaller than the length returned by
    631      * this method.
    632      *
    633      * @param inputLen the input length (in bytes)
    634      *
    635      * @return the required output buffer size (in bytes)
    636      *
    637      * @exception IllegalStateException if this cipher is in a wrong state
    638      * (e.g., has not yet been initialized)
    639      */
    640     public final int getOutputSize(int inputLen) {
    641 
    642         if (!initialized && !(this instanceof NullCipher)) {
    643             throw new IllegalStateException("Cipher not initialized");
    644         }
    645         if (inputLen < 0) {
    646             throw new IllegalArgumentException("Input size must be equal " +
    647                                                "to or greater than zero");
    648         }
    649         updateProviderIfNeeded();
    650         return spi.engineGetOutputSize(inputLen);
    651     }
    652 
    653     /**
    654      * Returns the initialization vector (IV) in a new buffer.
    655      *
    656      * <p>This is useful in the case where a random IV was created,
    657      * or in the context of password-based encryption or
    658      * decryption, where the IV is derived from a user-supplied password.
    659      *
    660      * @return the initialization vector in a new buffer, or null if the
    661      * underlying algorithm does not use an IV, or if the IV has not yet
    662      * been set.
    663      */
    664     public final byte[] getIV() {
    665         updateProviderIfNeeded();
    666         return spi.engineGetIV();
    667     }
    668 
    669     /**
    670      * Returns the parameters used with this cipher.
    671      *
    672      * <p>The returned parameters may be the same that were used to initialize
    673      * this cipher, or may contain a combination of default and random
    674      * parameter values used by the underlying cipher implementation if this
    675      * cipher requires algorithm parameters but was not initialized with any.
    676      *
    677      * @return the parameters used with this cipher, or null if this cipher
    678      * does not use any parameters.
    679      */
    680     public final AlgorithmParameters getParameters() {
    681         updateProviderIfNeeded();
    682         return spi.engineGetParameters();
    683     }
    684 
    685     /**
    686      * Returns the exemption mechanism object used with this cipher.
    687      *
    688      * @return the exemption mechanism object used with this cipher, or
    689      * null if this cipher does not use any exemption mechanism.
    690      */
    691     public final ExemptionMechanism getExemptionMechanism() {
    692         updateProviderIfNeeded();
    693         return exmech;
    694     }
    695 
    696     // check if opmode is one of the defined constants
    697     // throw InvalidParameterExeption if not
    698     private static void checkOpmode(int opmode) {
    699         if ((opmode < ENCRYPT_MODE) || (opmode > UNWRAP_MODE)) {
    700             throw new InvalidParameterException("Invalid operation mode");
    701         }
    702     }
    703 
    704     private static String getOpmodeString(int opmode) {
    705         switch (opmode) {
    706             case ENCRYPT_MODE:
    707                 return "encryption";
    708             case DECRYPT_MODE:
    709                 return "decryption";
    710             case WRAP_MODE:
    711                 return "key wrapping";
    712             case UNWRAP_MODE:
    713                 return "key unwrapping";
    714             default:
    715                 return "";
    716         }
    717     }
    718 
    719     /**
    720      * Initializes this cipher with a key.
    721      *
    722      * <p>The cipher is initialized for one of the following four operations:
    723      * encryption, decryption, key wrapping or key unwrapping, depending
    724      * on the value of <code>opmode</code>.
    725      *
    726      * <p>If this cipher requires any algorithm parameters that cannot be
    727      * derived from the given <code>key</code>, the underlying cipher
    728      * implementation is supposed to generate the required parameters itself
    729      * (using provider-specific default or random values) if it is being
    730      * initialized for encryption or key wrapping, and raise an
    731      * <code>InvalidKeyException</code> if it is being
    732      * initialized for decryption or key unwrapping.
    733      * The generated parameters can be retrieved using
    734      * {@link #getParameters() getParameters} or
    735      * {@link #getIV() getIV} (if the parameter is an IV).
    736      *
    737      * <p>If this cipher requires algorithm parameters that cannot be
    738      * derived from the input parameters, and there are no reasonable
    739      * provider-specific default values, initialization will
    740      * necessarily fail.
    741      *
    742      * <p>If this cipher (including its underlying feedback or padding scheme)
    743      * requires any random bytes (e.g., for parameter generation), it will get
    744      * them using the {@link java.security.SecureRandom}
    745      * implementation of the highest-priority
    746      * installed provider as the source of randomness.
    747      * (If none of the installed providers supply an implementation of
    748      * SecureRandom, a system-provided source of randomness will be used.)
    749      *
    750      * <p>Note that when a Cipher object is initialized, it loses all
    751      * previously-acquired state. In other words, initializing a Cipher is
    752      * equivalent to creating a new instance of that Cipher and initializing
    753      * it.
    754      *
    755      * @param opmode the operation mode of this cipher (this is one of
    756      * the following:
    757      * <code>ENCRYPT_MODE</code>, <code>DECRYPT_MODE</code>,
    758      * <code>WRAP_MODE</code> or <code>UNWRAP_MODE</code>)
    759      * @param key the key
    760      *
    761      * @exception InvalidKeyException if the given key is inappropriate for
    762      * initializing this cipher, or requires
    763      * algorithm parameters that cannot be
    764      * determined from the given key, or if the given key has a keysize that
    765      * exceeds the maximum allowable keysize (as determined from the
    766      * configured jurisdiction policy files).
    767      * @throws UnsupportedOperationException if (@code opmode} is
    768      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
    769      * by the underlying {@code CipherSpi}.
    770      */
    771     public final void init(int opmode, Key key) throws InvalidKeyException {
    772         init(opmode, key, JceSecurity.RANDOM);
    773     }
    774 
    775     /**
    776      * Initializes this cipher with a key and a source of randomness.
    777      *
    778      * <p>The cipher is initialized for one of the following four operations:
    779      * encryption, decryption, key wrapping or  key unwrapping, depending
    780      * on the value of <code>opmode</code>.
    781      *
    782      * <p>If this cipher requires any algorithm parameters that cannot be
    783      * derived from the given <code>key</code>, the underlying cipher
    784      * implementation is supposed to generate the required parameters itself
    785      * (using provider-specific default or random values) if it is being
    786      * initialized for encryption or key wrapping, and raise an
    787      * <code>InvalidKeyException</code> if it is being
    788      * initialized for decryption or key unwrapping.
    789      * The generated parameters can be retrieved using
    790      * {@link #getParameters() getParameters} or
    791      * {@link #getIV() getIV} (if the parameter is an IV).
    792      *
    793      * <p>If this cipher requires algorithm parameters that cannot be
    794      * derived from the input parameters, and there are no reasonable
    795      * provider-specific default values, initialization will
    796      * necessarily fail.
    797      *
    798      * <p>If this cipher (including its underlying feedback or padding scheme)
    799      * requires any random bytes (e.g., for parameter generation), it will get
    800      * them from <code>random</code>.
    801      *
    802      * <p>Note that when a Cipher object is initialized, it loses all
    803      * previously-acquired state. In other words, initializing a Cipher is
    804      * equivalent to creating a new instance of that Cipher and initializing
    805      * it.
    806      *
    807      * @param opmode the operation mode of this cipher (this is one of the
    808      * following:
    809      * <code>ENCRYPT_MODE</code>, <code>DECRYPT_MODE</code>,
    810      * <code>WRAP_MODE</code> or <code>UNWRAP_MODE</code>)
    811      * @param key the encryption key
    812      * @param random the source of randomness
    813      *
    814      * @exception InvalidKeyException if the given key is inappropriate for
    815      * initializing this cipher, or requires
    816      * algorithm parameters that cannot be
    817      * determined from the given key, or if the given key has a keysize that
    818      * exceeds the maximum allowable keysize (as determined from the
    819      * configured jurisdiction policy files).
    820      * @throws UnsupportedOperationException if (@code opmode} is
    821      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
    822      * by the underlying {@code CipherSpi}.
    823      */
    824     public final void init(int opmode, Key key, SecureRandom random)
    825             throws InvalidKeyException
    826     {
    827         initialized = false;
    828         checkOpmode(opmode);
    829 
    830         try {
    831             chooseProvider(InitType.KEY, opmode, key, null, null, random);
    832         } catch (InvalidAlgorithmParameterException e) {
    833             // should never occur
    834             throw new InvalidKeyException(e);
    835         }
    836 
    837         initialized = true;
    838         this.opmode = opmode;
    839         // Android-removed: this debugging mechanism is not used in Android.
    840         /*
    841         if (!skipDebug && pdebug != null) {
    842             pdebug.println("Cipher." + transformation + " " +
    843                 getOpmodeString(opmode) + " algorithm from: " +
    844                 this.provider.getName());
    845         }
    846         */
    847     }
    848 
    849     /**
    850      * Initializes this cipher with a key and a set of algorithm
    851      * parameters.
    852      *
    853      * <p>The cipher is initialized for one of the following four operations:
    854      * encryption, decryption, key wrapping or  key unwrapping, depending
    855      * on the value of <code>opmode</code>.
    856      *
    857      * <p>If this cipher requires any algorithm parameters and
    858      * <code>params</code> is null, the underlying cipher implementation is
    859      * supposed to generate the required parameters itself (using
    860      * provider-specific default or random values) if it is being
    861      * initialized for encryption or key wrapping, and raise an
    862      * <code>InvalidAlgorithmParameterException</code> if it is being
    863      * initialized for decryption or key unwrapping.
    864      * The generated parameters can be retrieved using
    865      * {@link #getParameters() getParameters} or
    866      * {@link #getIV() getIV} (if the parameter is an IV).
    867      *
    868      * <p>If this cipher requires algorithm parameters that cannot be
    869      * derived from the input parameters, and there are no reasonable
    870      * provider-specific default values, initialization will
    871      * necessarily fail.
    872      *
    873      * <p>If this cipher (including its underlying feedback or padding scheme)
    874      * requires any random bytes (e.g., for parameter generation), it will get
    875      * them using the {@link java.security.SecureRandom}
    876      * implementation of the highest-priority
    877      * installed provider as the source of randomness.
    878      * (If none of the installed providers supply an implementation of
    879      * SecureRandom, a system-provided source of randomness will be used.)
    880      *
    881      * <p>Note that when a Cipher object is initialized, it loses all
    882      * previously-acquired state. In other words, initializing a Cipher is
    883      * equivalent to creating a new instance of that Cipher and initializing
    884      * it.
    885      *
    886      * @param opmode the operation mode of this cipher (this is one of the
    887      * following:
    888      * <code>ENCRYPT_MODE</code>, <code>DECRYPT_MODE</code>,
    889      * <code>WRAP_MODE</code> or <code>UNWRAP_MODE</code>)
    890      * @param key the encryption key
    891      * @param params the algorithm parameters
    892      *
    893      * @exception InvalidKeyException if the given key is inappropriate for
    894      * initializing this cipher, or its keysize exceeds the maximum allowable
    895      * keysize (as determined from the configured jurisdiction policy files).
    896      * @exception InvalidAlgorithmParameterException if the given algorithm
    897      * parameters are inappropriate for this cipher,
    898      * or this cipher requires
    899      * algorithm parameters and <code>params</code> is null, or the given
    900      * algorithm parameters imply a cryptographic strength that would exceed
    901      * the legal limits (as determined from the configured jurisdiction
    902      * policy files).
    903      * @throws UnsupportedOperationException if (@code opmode} is
    904      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
    905      * by the underlying {@code CipherSpi}.
    906      */
    907     public final void init(int opmode, Key key, AlgorithmParameterSpec params)
    908             throws InvalidKeyException, InvalidAlgorithmParameterException
    909     {
    910         init(opmode, key, params, JceSecurity.RANDOM);
    911     }
    912 
    913     /**
    914      * Initializes this cipher with a key, a set of algorithm
    915      * parameters, and a source of randomness.
    916      *
    917      * <p>The cipher is initialized for one of the following four operations:
    918      * encryption, decryption, key wrapping or  key unwrapping, depending
    919      * on the value of <code>opmode</code>.
    920      *
    921      * <p>If this cipher requires any algorithm parameters and
    922      * <code>params</code> is null, the underlying cipher implementation is
    923      * supposed to generate the required parameters itself (using
    924      * provider-specific default or random values) if it is being
    925      * initialized for encryption or key wrapping, and raise an
    926      * <code>InvalidAlgorithmParameterException</code> if it is being
    927      * initialized for decryption or key unwrapping.
    928      * The generated parameters can be retrieved using
    929      * {@link #getParameters() getParameters} or
    930      * {@link #getIV() getIV} (if the parameter is an IV).
    931      *
    932      * <p>If this cipher requires algorithm parameters that cannot be
    933      * derived from the input parameters, and there are no reasonable
    934      * provider-specific default values, initialization will
    935      * necessarily fail.
    936      *
    937      * <p>If this cipher (including its underlying feedback or padding scheme)
    938      * requires any random bytes (e.g., for parameter generation), it will get
    939      * them from <code>random</code>.
    940      *
    941      * <p>Note that when a Cipher object is initialized, it loses all
    942      * previously-acquired state. In other words, initializing a Cipher is
    943      * equivalent to creating a new instance of that Cipher and initializing
    944      * it.
    945      *
    946      * @param opmode the operation mode of this cipher (this is one of the
    947      * following:
    948      * <code>ENCRYPT_MODE</code>, <code>DECRYPT_MODE</code>,
    949      * <code>WRAP_MODE</code> or <code>UNWRAP_MODE</code>)
    950      * @param key the encryption key
    951      * @param params the algorithm parameters
    952      * @param random the source of randomness
    953      *
    954      * @exception InvalidKeyException if the given key is inappropriate for
    955      * initializing this cipher, or its keysize exceeds the maximum allowable
    956      * keysize (as determined from the configured jurisdiction policy files).
    957      * @exception InvalidAlgorithmParameterException if the given algorithm
    958      * parameters are inappropriate for this cipher,
    959      * or this cipher requires
    960      * algorithm parameters and <code>params</code> is null, or the given
    961      * algorithm parameters imply a cryptographic strength that would exceed
    962      * the legal limits (as determined from the configured jurisdiction
    963      * policy files).
    964      * @throws UnsupportedOperationException if (@code opmode} is
    965      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
    966      * by the underlying {@code CipherSpi}.
    967      */
    968     public final void init(int opmode, Key key, AlgorithmParameterSpec params,
    969                            SecureRandom random)
    970             throws InvalidKeyException, InvalidAlgorithmParameterException
    971     {
    972         initialized = false;
    973         checkOpmode(opmode);
    974 
    975         chooseProvider(InitType.ALGORITHM_PARAM_SPEC, opmode, key, params, null, random);
    976 
    977         initialized = true;
    978         this.opmode = opmode;
    979 
    980         // Android-removed: this debugging mechanism is not used in Android.
    981         /*
    982         if (!skipDebug && pdebug != null) {
    983             pdebug.println("Cipher." + transformation + " " +
    984                 getOpmodeString(opmode) + " algorithm from: " +
    985                 this.provider.getName());
    986         }
    987         */
    988     }
    989 
    990     /**
    991      * Initializes this cipher with a key and a set of algorithm
    992      * parameters.
    993      *
    994      * <p>The cipher is initialized for one of the following four operations:
    995      * encryption, decryption, key wrapping or  key unwrapping, depending
    996      * on the value of <code>opmode</code>.
    997      *
    998      * <p>If this cipher requires any algorithm parameters and
    999      * <code>params</code> is null, the underlying cipher implementation is
   1000      * supposed to generate the required parameters itself (using
   1001      * provider-specific default or random values) if it is being
   1002      * initialized for encryption or key wrapping, and raise an
   1003      * <code>InvalidAlgorithmParameterException</code> if it is being
   1004      * initialized for decryption or key unwrapping.
   1005      * The generated parameters can be retrieved using
   1006      * {@link #getParameters() getParameters} or
   1007      * {@link #getIV() getIV} (if the parameter is an IV).
   1008      *
   1009      * <p>If this cipher requires algorithm parameters that cannot be
   1010      * derived from the input parameters, and there are no reasonable
   1011      * provider-specific default values, initialization will
   1012      * necessarily fail.
   1013      *
   1014      * <p>If this cipher (including its underlying feedback or padding scheme)
   1015      * requires any random bytes (e.g., for parameter generation), it will get
   1016      * them using the {@link java.security.SecureRandom}
   1017      * implementation of the highest-priority
   1018      * installed provider as the source of randomness.
   1019      * (If none of the installed providers supply an implementation of
   1020      * SecureRandom, a system-provided source of randomness will be used.)
   1021      *
   1022      * <p>Note that when a Cipher object is initialized, it loses all
   1023      * previously-acquired state. In other words, initializing a Cipher is
   1024      * equivalent to creating a new instance of that Cipher and initializing
   1025      * it.
   1026      *
   1027      * @param opmode the operation mode of this cipher (this is one of the
   1028      * following: <code>ENCRYPT_MODE</code>,
   1029      * <code>DECRYPT_MODE</code>, <code>WRAP_MODE</code>
   1030      * or <code>UNWRAP_MODE</code>)
   1031      * @param key the encryption key
   1032      * @param params the algorithm parameters
   1033      *
   1034      * @exception InvalidKeyException if the given key is inappropriate for
   1035      * initializing this cipher, or its keysize exceeds the maximum allowable
   1036      * keysize (as determined from the configured jurisdiction policy files).
   1037      * @exception InvalidAlgorithmParameterException if the given algorithm
   1038      * parameters are inappropriate for this cipher,
   1039      * or this cipher requires
   1040      * algorithm parameters and <code>params</code> is null, or the given
   1041      * algorithm parameters imply a cryptographic strength that would exceed
   1042      * the legal limits (as determined from the configured jurisdiction
   1043      * policy files).
   1044      * @throws UnsupportedOperationException if (@code opmode} is
   1045      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
   1046      * by the underlying {@code CipherSpi}.
   1047      */
   1048     public final void init(int opmode, Key key, AlgorithmParameters params)
   1049             throws InvalidKeyException, InvalidAlgorithmParameterException
   1050     {
   1051         init(opmode, key, params, JceSecurity.RANDOM);
   1052     }
   1053 
   1054     /**
   1055      * Initializes this cipher with a key, a set of algorithm
   1056      * parameters, and a source of randomness.
   1057      *
   1058      * <p>The cipher is initialized for one of the following four operations:
   1059      * encryption, decryption, key wrapping or  key unwrapping, depending
   1060      * on the value of <code>opmode</code>.
   1061      *
   1062      * <p>If this cipher requires any algorithm parameters and
   1063      * <code>params</code> is null, the underlying cipher implementation is
   1064      * supposed to generate the required parameters itself (using
   1065      * provider-specific default or random values) if it is being
   1066      * initialized for encryption or key wrapping, and raise an
   1067      * <code>InvalidAlgorithmParameterException</code> if it is being
   1068      * initialized for decryption or key unwrapping.
   1069      * The generated parameters can be retrieved using
   1070      * {@link #getParameters() getParameters} or
   1071      * {@link #getIV() getIV} (if the parameter is an IV).
   1072      *
   1073      * <p>If this cipher requires algorithm parameters that cannot be
   1074      * derived from the input parameters, and there are no reasonable
   1075      * provider-specific default values, initialization will
   1076      * necessarily fail.
   1077      *
   1078      * <p>If this cipher (including its underlying feedback or padding scheme)
   1079      * requires any random bytes (e.g., for parameter generation), it will get
   1080      * them from <code>random</code>.
   1081      *
   1082      * <p>Note that when a Cipher object is initialized, it loses all
   1083      * previously-acquired state. In other words, initializing a Cipher is
   1084      * equivalent to creating a new instance of that Cipher and initializing
   1085      * it.
   1086      *
   1087      * @param opmode the operation mode of this cipher (this is one of the
   1088      * following: <code>ENCRYPT_MODE</code>,
   1089      * <code>DECRYPT_MODE</code>, <code>WRAP_MODE</code>
   1090      * or <code>UNWRAP_MODE</code>)
   1091      * @param key the encryption key
   1092      * @param params the algorithm parameters
   1093      * @param random the source of randomness
   1094      *
   1095      * @exception InvalidKeyException if the given key is inappropriate for
   1096      * initializing this cipher, or its keysize exceeds the maximum allowable
   1097      * keysize (as determined from the configured jurisdiction policy files).
   1098      * @exception InvalidAlgorithmParameterException if the given algorithm
   1099      * parameters are inappropriate for this cipher,
   1100      * or this cipher requires
   1101      * algorithm parameters and <code>params</code> is null, or the given
   1102      * algorithm parameters imply a cryptographic strength that would exceed
   1103      * the legal limits (as determined from the configured jurisdiction
   1104      * policy files).
   1105      * @throws UnsupportedOperationException if (@code opmode} is
   1106      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
   1107      * by the underlying {@code CipherSpi}.
   1108      */
   1109     public final void init(int opmode, Key key, AlgorithmParameters params,
   1110                            SecureRandom random)
   1111             throws InvalidKeyException, InvalidAlgorithmParameterException
   1112     {
   1113         initialized = false;
   1114         checkOpmode(opmode);
   1115 
   1116         chooseProvider(InitType.ALGORITHM_PARAMS, opmode, key, null, params, random);
   1117 
   1118         initialized = true;
   1119         this.opmode = opmode;
   1120 
   1121         // Android-removed: this debugging mechanism is not used in Android.
   1122         /*
   1123         if (!skipDebug && pdebug != null) {
   1124             pdebug.println("Cipher." + transformation + " " +
   1125                 getOpmodeString(opmode) + " algorithm from: " +
   1126                 this.provider.getName());
   1127         }
   1128         */
   1129     }
   1130 
   1131     /**
   1132      * Initializes this cipher with the public key from the given certificate.
   1133      * <p> The cipher is initialized for one of the following four operations:
   1134      * encryption, decryption, key wrapping or  key unwrapping, depending
   1135      * on the value of <code>opmode</code>.
   1136      *
   1137      * <p>If the certificate is of type X.509 and has a <i>key usage</i>
   1138      * extension field marked as critical, and the value of the <i>key usage</i>
   1139      * extension field implies that the public key in
   1140      * the certificate and its corresponding private key are not
   1141      * supposed to be used for the operation represented by the value
   1142      * of <code>opmode</code>,
   1143      * an <code>InvalidKeyException</code>
   1144      * is thrown.
   1145      *
   1146      * <p> If this cipher requires any algorithm parameters that cannot be
   1147      * derived from the public key in the given certificate, the underlying
   1148      * cipher
   1149      * implementation is supposed to generate the required parameters itself
   1150      * (using provider-specific default or random values) if it is being
   1151      * initialized for encryption or key wrapping, and raise an <code>
   1152      * InvalidKeyException</code> if it is being initialized for decryption or
   1153      * key unwrapping.
   1154      * The generated parameters can be retrieved using
   1155      * {@link #getParameters() getParameters} or
   1156      * {@link #getIV() getIV} (if the parameter is an IV).
   1157      *
   1158      * <p>If this cipher requires algorithm parameters that cannot be
   1159      * derived from the input parameters, and there are no reasonable
   1160      * provider-specific default values, initialization will
   1161      * necessarily fail.
   1162      *
   1163      * <p>If this cipher (including its underlying feedback or padding scheme)
   1164      * requires any random bytes (e.g., for parameter generation), it will get
   1165      * them using the
   1166      * <code>SecureRandom</code>
   1167      * implementation of the highest-priority
   1168      * installed provider as the source of randomness.
   1169      * (If none of the installed providers supply an implementation of
   1170      * SecureRandom, a system-provided source of randomness will be used.)
   1171      *
   1172      * <p>Note that when a Cipher object is initialized, it loses all
   1173      * previously-acquired state. In other words, initializing a Cipher is
   1174      * equivalent to creating a new instance of that Cipher and initializing
   1175      * it.
   1176      *
   1177      * @param opmode the operation mode of this cipher (this is one of the
   1178      * following:
   1179      * <code>ENCRYPT_MODE</code>, <code>DECRYPT_MODE</code>,
   1180      * <code>WRAP_MODE</code> or <code>UNWRAP_MODE</code>)
   1181      * @param certificate the certificate
   1182      *
   1183      * @exception InvalidKeyException if the public key in the given
   1184      * certificate is inappropriate for initializing this cipher, or this
   1185      * cipher requires algorithm parameters that cannot be determined from the
   1186      * public key in the given certificate, or the keysize of the public key
   1187      * in the given certificate has a keysize that exceeds the maximum
   1188      * allowable keysize (as determined by the configured jurisdiction policy
   1189      * files).
   1190      * @throws UnsupportedOperationException if (@code opmode} is
   1191      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
   1192      * by the underlying {@code CipherSpi}.
   1193      */
   1194     public final void init(int opmode, Certificate certificate)
   1195             throws InvalidKeyException
   1196     {
   1197         init(opmode, certificate, JceSecurity.RANDOM);
   1198     }
   1199 
   1200     /**
   1201      * Initializes this cipher with the public key from the given certificate
   1202      * and
   1203      * a source of randomness.
   1204      *
   1205      * <p>The cipher is initialized for one of the following four operations:
   1206      * encryption, decryption, key wrapping
   1207      * or key unwrapping, depending on
   1208      * the value of <code>opmode</code>.
   1209      *
   1210      * <p>If the certificate is of type X.509 and has a <i>key usage</i>
   1211      * extension field marked as critical, and the value of the <i>key usage</i>
   1212      * extension field implies that the public key in
   1213      * the certificate and its corresponding private key are not
   1214      * supposed to be used for the operation represented by the value of
   1215      * <code>opmode</code>,
   1216      * an <code>InvalidKeyException</code>
   1217      * is thrown.
   1218      *
   1219      * <p>If this cipher requires any algorithm parameters that cannot be
   1220      * derived from the public key in the given <code>certificate</code>,
   1221      * the underlying cipher
   1222      * implementation is supposed to generate the required parameters itself
   1223      * (using provider-specific default or random values) if it is being
   1224      * initialized for encryption or key wrapping, and raise an
   1225      * <code>InvalidKeyException</code> if it is being
   1226      * initialized for decryption or key unwrapping.
   1227      * The generated parameters can be retrieved using
   1228      * {@link #getParameters() getParameters} or
   1229      * {@link #getIV() getIV} (if the parameter is an IV).
   1230      *
   1231      * <p>If this cipher requires algorithm parameters that cannot be
   1232      * derived from the input parameters, and there are no reasonable
   1233      * provider-specific default values, initialization will
   1234      * necessarily fail.
   1235      *
   1236      * <p>If this cipher (including its underlying feedback or padding scheme)
   1237      * requires any random bytes (e.g., for parameter generation), it will get
   1238      * them from <code>random</code>.
   1239      *
   1240      * <p>Note that when a Cipher object is initialized, it loses all
   1241      * previously-acquired state. In other words, initializing a Cipher is
   1242      * equivalent to creating a new instance of that Cipher and initializing
   1243      * it.
   1244      *
   1245      * @param opmode the operation mode of this cipher (this is one of the
   1246      * following:
   1247      * <code>ENCRYPT_MODE</code>, <code>DECRYPT_MODE</code>,
   1248      * <code>WRAP_MODE</code> or <code>UNWRAP_MODE</code>)
   1249      * @param certificate the certificate
   1250      * @param random the source of randomness
   1251      *
   1252      * @exception InvalidKeyException if the public key in the given
   1253      * certificate is inappropriate for initializing this cipher, or this
   1254      * cipher
   1255      * requires algorithm parameters that cannot be determined from the
   1256      * public key in the given certificate, or the keysize of the public key
   1257      * in the given certificate has a keysize that exceeds the maximum
   1258      * allowable keysize (as determined by the configured jurisdiction policy
   1259      * files).
   1260      * @throws UnsupportedOperationException if (@code opmode} is
   1261      * {@code WRAP_MODE} or {@code UNWRAP_MODE} but the mode is not implemented
   1262      * by the underlying {@code CipherSpi}.
   1263      */
   1264     public final void init(int opmode, Certificate certificate,
   1265                            SecureRandom random)
   1266             throws InvalidKeyException {
   1267         initialized = false;
   1268         checkOpmode(opmode);
   1269 
   1270         // Check key usage if the certificate is of
   1271         // type X.509.
   1272         if (certificate instanceof java.security.cert.X509Certificate) {
   1273             // Check whether the cert has a key usage extension
   1274             // marked as a critical extension.
   1275             X509Certificate cert = (X509Certificate) certificate;
   1276             Set<String> critSet = cert.getCriticalExtensionOIDs();
   1277 
   1278             if (critSet != null && !critSet.isEmpty()
   1279                     && critSet.contains(KEY_USAGE_EXTENSION_OID)) {
   1280                 boolean[] keyUsageInfo = cert.getKeyUsage();
   1281                 // keyUsageInfo[2] is for keyEncipherment;
   1282                 // keyUsageInfo[3] is for dataEncipherment.
   1283                 if ((keyUsageInfo != null) &&
   1284                         (((opmode == Cipher.ENCRYPT_MODE) &&
   1285                                 (keyUsageInfo.length > 3) &&
   1286                                 (keyUsageInfo[3] == false)) ||
   1287                                 ((opmode == Cipher.WRAP_MODE) &&
   1288                                         (keyUsageInfo.length > 2) &&
   1289                                         (keyUsageInfo[2] == false)))) {
   1290                     throw new InvalidKeyException("Wrong key usage");
   1291                 }
   1292             }
   1293         }
   1294 
   1295         PublicKey publicKey =
   1296                 (certificate == null ? null : certificate.getPublicKey());
   1297 
   1298         try {
   1299             chooseProvider(InitType.KEY, opmode, (Key) publicKey, null, null, random);
   1300         } catch (InvalidAlgorithmParameterException e) {
   1301             // should never occur
   1302             throw new InvalidKeyException(e);
   1303         }
   1304 
   1305         initialized = true;
   1306         this.opmode = opmode;
   1307 
   1308         // Android-removed: this debugging mechanism is not used in Android.
   1309         /*
   1310         if (!skipDebug && pdebug != null) {
   1311             pdebug.println("Cipher." + transformation + " " +
   1312                 getOpmodeString(opmode) + " algorithm from: " +
   1313                 this.provider.getName());
   1314         }
   1315         */
   1316     }
   1317 
   1318     /**
   1319      * Ensures that Cipher is in a valid state for update() and doFinal()
   1320      * calls - should be initialized and in ENCRYPT_MODE or DECRYPT_MODE.
   1321      * @throws IllegalStateException if Cipher object is not in valid state.
   1322      */
   1323     private void checkCipherState() {
   1324         if (!(this instanceof NullCipher)) {
   1325             if (!initialized) {
   1326                 throw new IllegalStateException("Cipher not initialized");
   1327             }
   1328             if ((opmode != Cipher.ENCRYPT_MODE) &&
   1329                 (opmode != Cipher.DECRYPT_MODE)) {
   1330                 throw new IllegalStateException("Cipher not initialized " +
   1331                                                 "for encryption/decryption");
   1332             }
   1333         }
   1334     }
   1335 
   1336     /**
   1337      * Continues a multiple-part encryption or decryption operation
   1338      * (depending on how this cipher was initialized), processing another data
   1339      * part.
   1340      *
   1341      * <p>The bytes in the <code>input</code> buffer are processed, and the
   1342      * result is stored in a new buffer.
   1343      *
   1344      * <p>If <code>input</code> has a length of zero, this method returns
   1345      * <code>null</code>.
   1346      *
   1347      * @param input the input buffer
   1348      *
   1349      * @return the new buffer with the result, or null if the underlying
   1350      * cipher is a block cipher and the input data is too short to result in a
   1351      * new block.
   1352      *
   1353      * @exception IllegalStateException if this cipher is in a wrong state
   1354      * (e.g., has not been initialized)
   1355      */
   1356     public final byte[] update(byte[] input) {
   1357         checkCipherState();
   1358 
   1359         // Input sanity check
   1360         if (input == null) {
   1361             throw new IllegalArgumentException("Null input buffer");
   1362         }
   1363 
   1364         updateProviderIfNeeded();
   1365         if (input.length == 0) {
   1366             return null;
   1367         }
   1368         return spi.engineUpdate(input, 0, input.length);
   1369     }
   1370 
   1371     /**
   1372      * Continues a multiple-part encryption or decryption operation
   1373      * (depending on how this cipher was initialized), processing another data
   1374      * part.
   1375      *
   1376      * <p>The first <code>inputLen</code> bytes in the <code>input</code>
   1377      * buffer, starting at <code>inputOffset</code> inclusive, are processed,
   1378      * and the result is stored in a new buffer.
   1379      *
   1380      * <p>If <code>inputLen</code> is zero, this method returns
   1381      * <code>null</code>.
   1382      *
   1383      * @param input the input buffer
   1384      * @param inputOffset the offset in <code>input</code> where the input
   1385      * starts
   1386      * @param inputLen the input length
   1387      *
   1388      * @return the new buffer with the result, or null if the underlying
   1389      * cipher is a block cipher and the input data is too short to result in a
   1390      * new block.
   1391      *
   1392      * @exception IllegalStateException if this cipher is in a wrong state
   1393      * (e.g., has not been initialized)
   1394      */
   1395     public final byte[] update(byte[] input, int inputOffset, int inputLen) {
   1396         checkCipherState();
   1397 
   1398         // Input sanity check
   1399         if (input == null || inputOffset < 0
   1400             || inputLen > (input.length - inputOffset) || inputLen < 0) {
   1401             throw new IllegalArgumentException("Bad arguments");
   1402         }
   1403 
   1404         updateProviderIfNeeded();
   1405         if (inputLen == 0) {
   1406             return null;
   1407         }
   1408         return spi.engineUpdate(input, inputOffset, inputLen);
   1409     }
   1410 
   1411     /**
   1412      * Continues a multiple-part encryption or decryption operation
   1413      * (depending on how this cipher was initialized), processing another data
   1414      * part.
   1415      *
   1416      * <p>The first <code>inputLen</code> bytes in the <code>input</code>
   1417      * buffer, starting at <code>inputOffset</code> inclusive, are processed,
   1418      * and the result is stored in the <code>output</code> buffer.
   1419      *
   1420      * <p>If the <code>output</code> buffer is too small to hold the result,
   1421      * a <code>ShortBufferException</code> is thrown. In this case, repeat this
   1422      * call with a larger output buffer. Use
   1423      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1424      * the output buffer should be.
   1425      *
   1426      * <p>If <code>inputLen</code> is zero, this method returns
   1427      * a length of zero.
   1428      *
   1429      * <p>Note: this method should be copy-safe, which means the
   1430      * <code>input</code> and <code>output</code> buffers can reference
   1431      * the same byte array and no unprocessed input data is overwritten
   1432      * when the result is copied into the output buffer.
   1433      *
   1434      * @param input the input buffer
   1435      * @param inputOffset the offset in <code>input</code> where the input
   1436      * starts
   1437      * @param inputLen the input length
   1438      * @param output the buffer for the result
   1439      *
   1440      * @return the number of bytes stored in <code>output</code>
   1441      *
   1442      * @exception IllegalStateException if this cipher is in a wrong state
   1443      * (e.g., has not been initialized)
   1444      * @exception ShortBufferException if the given output buffer is too small
   1445      * to hold the result
   1446      */
   1447     public final int update(byte[] input, int inputOffset, int inputLen,
   1448                             byte[] output)
   1449             throws ShortBufferException {
   1450         checkCipherState();
   1451 
   1452         // Input sanity check
   1453         if (input == null || inputOffset < 0
   1454             || inputLen > (input.length - inputOffset) || inputLen < 0) {
   1455             throw new IllegalArgumentException("Bad arguments");
   1456         }
   1457 
   1458         updateProviderIfNeeded();
   1459         if (inputLen == 0) {
   1460             return 0;
   1461         }
   1462         return spi.engineUpdate(input, inputOffset, inputLen,
   1463                                       output, 0);
   1464     }
   1465 
   1466     /**
   1467      * Continues a multiple-part encryption or decryption operation
   1468      * (depending on how this cipher was initialized), processing another data
   1469      * part.
   1470      *
   1471      * <p>The first <code>inputLen</code> bytes in the <code>input</code>
   1472      * buffer, starting at <code>inputOffset</code> inclusive, are processed,
   1473      * and the result is stored in the <code>output</code> buffer, starting at
   1474      * <code>outputOffset</code> inclusive.
   1475      *
   1476      * <p>If the <code>output</code> buffer is too small to hold the result,
   1477      * a <code>ShortBufferException</code> is thrown. In this case, repeat this
   1478      * call with a larger output buffer. Use
   1479      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1480      * the output buffer should be.
   1481      *
   1482      * <p>If <code>inputLen</code> is zero, this method returns
   1483      * a length of zero.
   1484      *
   1485      * <p>Note: this method should be copy-safe, which means the
   1486      * <code>input</code> and <code>output</code> buffers can reference
   1487      * the same byte array and no unprocessed input data is overwritten
   1488      * when the result is copied into the output buffer.
   1489      *
   1490      * @param input the input buffer
   1491      * @param inputOffset the offset in <code>input</code> where the input
   1492      * starts
   1493      * @param inputLen the input length
   1494      * @param output the buffer for the result
   1495      * @param outputOffset the offset in <code>output</code> where the result
   1496      * is stored
   1497      *
   1498      * @return the number of bytes stored in <code>output</code>
   1499      *
   1500      * @exception IllegalStateException if this cipher is in a wrong state
   1501      * (e.g., has not been initialized)
   1502      * @exception ShortBufferException if the given output buffer is too small
   1503      * to hold the result
   1504      */
   1505     public final int update(byte[] input, int inputOffset, int inputLen,
   1506                             byte[] output, int outputOffset)
   1507             throws ShortBufferException {
   1508         checkCipherState();
   1509 
   1510         // Input sanity check
   1511         if (input == null || inputOffset < 0
   1512             || inputLen > (input.length - inputOffset) || inputLen < 0
   1513             || outputOffset < 0) {
   1514             throw new IllegalArgumentException("Bad arguments");
   1515         }
   1516 
   1517         updateProviderIfNeeded();
   1518         if (inputLen == 0) {
   1519             return 0;
   1520         }
   1521         return spi.engineUpdate(input, inputOffset, inputLen,
   1522                                       output, outputOffset);
   1523     }
   1524 
   1525     /**
   1526      * Continues a multiple-part encryption or decryption operation
   1527      * (depending on how this cipher was initialized), processing another data
   1528      * part.
   1529      *
   1530      * <p>All <code>input.remaining()</code> bytes starting at
   1531      * <code>input.position()</code> are processed. The result is stored
   1532      * in the output buffer.
   1533      * Upon return, the input buffer's position will be equal
   1534      * to its limit; its limit will not have changed. The output buffer's
   1535      * position will have advanced by n, where n is the value returned
   1536      * by this method; the output buffer's limit will not have changed.
   1537      *
   1538      * <p>If <code>output.remaining()</code> bytes are insufficient to
   1539      * hold the result, a <code>ShortBufferException</code> is thrown.
   1540      * In this case, repeat this call with a larger output buffer. Use
   1541      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1542      * the output buffer should be.
   1543      *
   1544      * <p>Note: this method should be copy-safe, which means the
   1545      * <code>input</code> and <code>output</code> buffers can reference
   1546      * the same block of memory and no unprocessed input data is overwritten
   1547      * when the result is copied into the output buffer.
   1548      *
   1549      * @param input the input ByteBuffer
   1550      * @param output the output ByteByffer
   1551      *
   1552      * @return the number of bytes stored in <code>output</code>
   1553      *
   1554      * @exception IllegalStateException if this cipher is in a wrong state
   1555      * (e.g., has not been initialized)
   1556      * @exception IllegalArgumentException if input and output are the
   1557      *   same object
   1558      * @exception ReadOnlyBufferException if the output buffer is read-only
   1559      * @exception ShortBufferException if there is insufficient space in the
   1560      * output buffer
   1561      * @since 1.5
   1562      */
   1563     public final int update(ByteBuffer input, ByteBuffer output)
   1564             throws ShortBufferException {
   1565         checkCipherState();
   1566 
   1567         if ((input == null) || (output == null)) {
   1568             throw new IllegalArgumentException("Buffers must not be null");
   1569         }
   1570         if (input == output) {
   1571             throw new IllegalArgumentException("Input and output buffers must "
   1572                 + "not be the same object, consider using buffer.duplicate()");
   1573         }
   1574         if (output.isReadOnly()) {
   1575             throw new ReadOnlyBufferException();
   1576         }
   1577 
   1578         updateProviderIfNeeded();
   1579         return spi.engineUpdate(input, output);
   1580     }
   1581 
   1582     /**
   1583      * Finishes a multiple-part encryption or decryption operation, depending
   1584      * on how this cipher was initialized.
   1585      *
   1586      * <p>Input data that may have been buffered during a previous
   1587      * <code>update</code> operation is processed, with padding (if requested)
   1588      * being applied.
   1589      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1590      * tag is appended in the case of encryption, or verified in the
   1591      * case of decryption.
   1592      * The result is stored in a new buffer.
   1593      *
   1594      * <p>Upon finishing, this method resets this cipher object to the state
   1595      * it was in when previously initialized via a call to <code>init</code>.
   1596      * That is, the object is reset and available to encrypt or decrypt
   1597      * (depending on the operation mode that was specified in the call to
   1598      * <code>init</code>) more data.
   1599      *
   1600      * <p>Note: if any exception is thrown, this cipher object may need to
   1601      * be reset before it can be used again.
   1602      *
   1603      * @return the new buffer with the result
   1604      *
   1605      * @exception IllegalStateException if this cipher is in a wrong state
   1606      * (e.g., has not been initialized)
   1607      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   1608      * no padding has been requested (only in encryption mode), and the total
   1609      * input length of the data processed by this cipher is not a multiple of
   1610      * block size; or if this encryption algorithm is unable to
   1611      * process the input data provided.
   1612      * @exception BadPaddingException if this cipher is in decryption mode,
   1613      * and (un)padding has been requested, but the decrypted data is not
   1614      * bounded by the appropriate padding bytes
   1615      * @exception AEADBadTagException if this cipher is decrypting in an
   1616      * AEAD mode (such as GCM/CCM), and the received authentication tag
   1617      * does not match the calculated value
   1618      */
   1619     public final byte[] doFinal()
   1620             throws IllegalBlockSizeException, BadPaddingException {
   1621         checkCipherState();
   1622 
   1623         updateProviderIfNeeded();
   1624         return spi.engineDoFinal(null, 0, 0);
   1625     }
   1626 
   1627     /**
   1628      * Finishes a multiple-part encryption or decryption operation, depending
   1629      * on how this cipher was initialized.
   1630      *
   1631      * <p>Input data that may have been buffered during a previous
   1632      * <code>update</code> operation is processed, with padding (if requested)
   1633      * being applied.
   1634      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1635      * tag is appended in the case of encryption, or verified in the
   1636      * case of decryption.
   1637      * The result is stored in the <code>output</code> buffer, starting at
   1638      * <code>outputOffset</code> inclusive.
   1639      *
   1640      * <p>If the <code>output</code> buffer is too small to hold the result,
   1641      * a <code>ShortBufferException</code> is thrown. In this case, repeat this
   1642      * call with a larger output buffer. Use
   1643      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1644      * the output buffer should be.
   1645      *
   1646      * <p>Upon finishing, this method resets this cipher object to the state
   1647      * it was in when previously initialized via a call to <code>init</code>.
   1648      * That is, the object is reset and available to encrypt or decrypt
   1649      * (depending on the operation mode that was specified in the call to
   1650      * <code>init</code>) more data.
   1651      *
   1652      * <p>Note: if any exception is thrown, this cipher object may need to
   1653      * be reset before it can be used again.
   1654      *
   1655      * @param output the buffer for the result
   1656      * @param outputOffset the offset in <code>output</code> where the result
   1657      * is stored
   1658      *
   1659      * @return the number of bytes stored in <code>output</code>
   1660      *
   1661      * @exception IllegalStateException if this cipher is in a wrong state
   1662      * (e.g., has not been initialized)
   1663      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   1664      * no padding has been requested (only in encryption mode), and the total
   1665      * input length of the data processed by this cipher is not a multiple of
   1666      * block size; or if this encryption algorithm is unable to
   1667      * process the input data provided.
   1668      * @exception ShortBufferException if the given output buffer is too small
   1669      * to hold the result
   1670      * @exception BadPaddingException if this cipher is in decryption mode,
   1671      * and (un)padding has been requested, but the decrypted data is not
   1672      * bounded by the appropriate padding bytes
   1673      * @exception AEADBadTagException if this cipher is decrypting in an
   1674      * AEAD mode (such as GCM/CCM), and the received authentication tag
   1675      * does not match the calculated value
   1676      */
   1677     public final int doFinal(byte[] output, int outputOffset)
   1678             throws IllegalBlockSizeException, ShortBufferException,
   1679                BadPaddingException {
   1680         checkCipherState();
   1681 
   1682         // Input sanity check
   1683         if ((output == null) || (outputOffset < 0)) {
   1684             throw new IllegalArgumentException("Bad arguments");
   1685         }
   1686 
   1687         updateProviderIfNeeded();
   1688         return spi.engineDoFinal(null, 0, 0, output, outputOffset);
   1689     }
   1690 
   1691     /**
   1692      * Encrypts or decrypts data in a single-part operation, or finishes a
   1693      * multiple-part operation. The data is encrypted or decrypted,
   1694      * depending on how this cipher was initialized.
   1695      *
   1696      * <p>The bytes in the <code>input</code> buffer, and any input bytes that
   1697      * may have been buffered during a previous <code>update</code> operation,
   1698      * are processed, with padding (if requested) being applied.
   1699      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1700      * tag is appended in the case of encryption, or verified in the
   1701      * case of decryption.
   1702      * The result is stored in a new buffer.
   1703      *
   1704      * <p>Upon finishing, this method resets this cipher object to the state
   1705      * it was in when previously initialized via a call to <code>init</code>.
   1706      * That is, the object is reset and available to encrypt or decrypt
   1707      * (depending on the operation mode that was specified in the call to
   1708      * <code>init</code>) more data.
   1709      *
   1710      * <p>Note: if any exception is thrown, this cipher object may need to
   1711      * be reset before it can be used again.
   1712      *
   1713      * @param input the input buffer
   1714      *
   1715      * @return the new buffer with the result
   1716      *
   1717      * @exception IllegalStateException if this cipher is in a wrong state
   1718      * (e.g., has not been initialized)
   1719      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   1720      * no padding has been requested (only in encryption mode), and the total
   1721      * input length of the data processed by this cipher is not a multiple of
   1722      * block size; or if this encryption algorithm is unable to
   1723      * process the input data provided.
   1724      * @exception BadPaddingException if this cipher is in decryption mode,
   1725      * and (un)padding has been requested, but the decrypted data is not
   1726      * bounded by the appropriate padding bytes
   1727      * @exception AEADBadTagException if this cipher is decrypting in an
   1728      * AEAD mode (such as GCM/CCM), and the received authentication tag
   1729      * does not match the calculated value
   1730      */
   1731     public final byte[] doFinal(byte[] input)
   1732             throws IllegalBlockSizeException, BadPaddingException {
   1733         checkCipherState();
   1734 
   1735         // Input sanity check
   1736         if (input == null) {
   1737             throw new IllegalArgumentException("Null input buffer");
   1738         }
   1739 
   1740         updateProviderIfNeeded();
   1741         return spi.engineDoFinal(input, 0, input.length);
   1742     }
   1743 
   1744     /**
   1745      * Encrypts or decrypts data in a single-part operation, or finishes a
   1746      * multiple-part operation. The data is encrypted or decrypted,
   1747      * depending on how this cipher was initialized.
   1748      *
   1749      * <p>The first <code>inputLen</code> bytes in the <code>input</code>
   1750      * buffer, starting at <code>inputOffset</code> inclusive, and any input
   1751      * bytes that may have been buffered during a previous <code>update</code>
   1752      * operation, are processed, with padding (if requested) being applied.
   1753      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1754      * tag is appended in the case of encryption, or verified in the
   1755      * case of decryption.
   1756      * The result is stored in a new buffer.
   1757      *
   1758      * <p>Upon finishing, this method resets this cipher object to the state
   1759      * it was in when previously initialized via a call to <code>init</code>.
   1760      * That is, the object is reset and available to encrypt or decrypt
   1761      * (depending on the operation mode that was specified in the call to
   1762      * <code>init</code>) more data.
   1763      *
   1764      * <p>Note: if any exception is thrown, this cipher object may need to
   1765      * be reset before it can be used again.
   1766      *
   1767      * @param input the input buffer
   1768      * @param inputOffset the offset in <code>input</code> where the input
   1769      * starts
   1770      * @param inputLen the input length
   1771      *
   1772      * @return the new buffer with the result
   1773      *
   1774      * @exception IllegalStateException if this cipher is in a wrong state
   1775      * (e.g., has not been initialized)
   1776      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   1777      * no padding has been requested (only in encryption mode), and the total
   1778      * input length of the data processed by this cipher is not a multiple of
   1779      * block size; or if this encryption algorithm is unable to
   1780      * process the input data provided.
   1781      * @exception BadPaddingException if this cipher is in decryption mode,
   1782      * and (un)padding has been requested, but the decrypted data is not
   1783      * bounded by the appropriate padding bytes
   1784      * @exception AEADBadTagException if this cipher is decrypting in an
   1785      * AEAD mode (such as GCM/CCM), and the received authentication tag
   1786      * does not match the calculated value
   1787      */
   1788     public final byte[] doFinal(byte[] input, int inputOffset, int inputLen)
   1789             throws IllegalBlockSizeException, BadPaddingException {
   1790         checkCipherState();
   1791 
   1792         // Input sanity check
   1793         if (input == null || inputOffset < 0
   1794             || inputLen > (input.length - inputOffset) || inputLen < 0) {
   1795             throw new IllegalArgumentException("Bad arguments");
   1796         }
   1797 
   1798         updateProviderIfNeeded();
   1799         return spi.engineDoFinal(input, inputOffset, inputLen);
   1800     }
   1801 
   1802     /**
   1803      * Encrypts or decrypts data in a single-part operation, or finishes a
   1804      * multiple-part operation. The data is encrypted or decrypted,
   1805      * depending on how this cipher was initialized.
   1806      *
   1807      * <p>The first <code>inputLen</code> bytes in the <code>input</code>
   1808      * buffer, starting at <code>inputOffset</code> inclusive, and any input
   1809      * bytes that may have been buffered during a previous <code>update</code>
   1810      * operation, are processed, with padding (if requested) being applied.
   1811      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1812      * tag is appended in the case of encryption, or verified in the
   1813      * case of decryption.
   1814      * The result is stored in the <code>output</code> buffer.
   1815      *
   1816      * <p>If the <code>output</code> buffer is too small to hold the result,
   1817      * a <code>ShortBufferException</code> is thrown. In this case, repeat this
   1818      * call with a larger output buffer. Use
   1819      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1820      * the output buffer should be.
   1821      *
   1822      * <p>Upon finishing, this method resets this cipher object to the state
   1823      * it was in when previously initialized via a call to <code>init</code>.
   1824      * That is, the object is reset and available to encrypt or decrypt
   1825      * (depending on the operation mode that was specified in the call to
   1826      * <code>init</code>) more data.
   1827      *
   1828      * <p>Note: if any exception is thrown, this cipher object may need to
   1829      * be reset before it can be used again.
   1830      *
   1831      * <p>Note: this method should be copy-safe, which means the
   1832      * <code>input</code> and <code>output</code> buffers can reference
   1833      * the same byte array and no unprocessed input data is overwritten
   1834      * when the result is copied into the output buffer.
   1835      *
   1836      * @param input the input buffer
   1837      * @param inputOffset the offset in <code>input</code> where the input
   1838      * starts
   1839      * @param inputLen the input length
   1840      * @param output the buffer for the result
   1841      *
   1842      * @return the number of bytes stored in <code>output</code>
   1843      *
   1844      * @exception IllegalStateException if this cipher is in a wrong state
   1845      * (e.g., has not been initialized)
   1846      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   1847      * no padding has been requested (only in encryption mode), and the total
   1848      * input length of the data processed by this cipher is not a multiple of
   1849      * block size; or if this encryption algorithm is unable to
   1850      * process the input data provided.
   1851      * @exception ShortBufferException if the given output buffer is too small
   1852      * to hold the result
   1853      * @exception BadPaddingException if this cipher is in decryption mode,
   1854      * and (un)padding has been requested, but the decrypted data is not
   1855      * bounded by the appropriate padding bytes
   1856      * @exception AEADBadTagException if this cipher is decrypting in an
   1857      * AEAD mode (such as GCM/CCM), and the received authentication tag
   1858      * does not match the calculated value
   1859      */
   1860     public final int doFinal(byte[] input, int inputOffset, int inputLen,
   1861                              byte[] output)
   1862             throws ShortBufferException, IllegalBlockSizeException,
   1863             BadPaddingException {
   1864         checkCipherState();
   1865 
   1866         // Input sanity check
   1867         if (input == null || inputOffset < 0
   1868             || inputLen > (input.length - inputOffset) || inputLen < 0) {
   1869             throw new IllegalArgumentException("Bad arguments");
   1870         }
   1871 
   1872         updateProviderIfNeeded();
   1873         return spi.engineDoFinal(input, inputOffset, inputLen,
   1874                                        output, 0);
   1875     }
   1876 
   1877     /**
   1878      * Encrypts or decrypts data in a single-part operation, or finishes a
   1879      * multiple-part operation. The data is encrypted or decrypted,
   1880      * depending on how this cipher was initialized.
   1881      *
   1882      * <p>The first <code>inputLen</code> bytes in the <code>input</code>
   1883      * buffer, starting at <code>inputOffset</code> inclusive, and any input
   1884      * bytes that may have been buffered during a previous
   1885      * <code>update</code> operation, are processed, with padding
   1886      * (if requested) being applied.
   1887      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1888      * tag is appended in the case of encryption, or verified in the
   1889      * case of decryption.
   1890      * The result is stored in the <code>output</code> buffer, starting at
   1891      * <code>outputOffset</code> inclusive.
   1892      *
   1893      * <p>If the <code>output</code> buffer is too small to hold the result,
   1894      * a <code>ShortBufferException</code> is thrown. In this case, repeat this
   1895      * call with a larger output buffer. Use
   1896      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1897      * the output buffer should be.
   1898      *
   1899      * <p>Upon finishing, this method resets this cipher object to the state
   1900      * it was in when previously initialized via a call to <code>init</code>.
   1901      * That is, the object is reset and available to encrypt or decrypt
   1902      * (depending on the operation mode that was specified in the call to
   1903      * <code>init</code>) more data.
   1904      *
   1905      * <p>Note: if any exception is thrown, this cipher object may need to
   1906      * be reset before it can be used again.
   1907      *
   1908      * <p>Note: this method should be copy-safe, which means the
   1909      * <code>input</code> and <code>output</code> buffers can reference
   1910      * the same byte array and no unprocessed input data is overwritten
   1911      * when the result is copied into the output buffer.
   1912      *
   1913      * @param input the input buffer
   1914      * @param inputOffset the offset in <code>input</code> where the input
   1915      * starts
   1916      * @param inputLen the input length
   1917      * @param output the buffer for the result
   1918      * @param outputOffset the offset in <code>output</code> where the result
   1919      * is stored
   1920      *
   1921      * @return the number of bytes stored in <code>output</code>
   1922      *
   1923      * @exception IllegalStateException if this cipher is in a wrong state
   1924      * (e.g., has not been initialized)
   1925      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   1926      * no padding has been requested (only in encryption mode), and the total
   1927      * input length of the data processed by this cipher is not a multiple of
   1928      * block size; or if this encryption algorithm is unable to
   1929      * process the input data provided.
   1930      * @exception ShortBufferException if the given output buffer is too small
   1931      * to hold the result
   1932      * @exception BadPaddingException if this cipher is in decryption mode,
   1933      * and (un)padding has been requested, but the decrypted data is not
   1934      * bounded by the appropriate padding bytes
   1935      * @exception AEADBadTagException if this cipher is decrypting in an
   1936      * AEAD mode (such as GCM/CCM), and the received authentication tag
   1937      * does not match the calculated value
   1938      */
   1939     public final int doFinal(byte[] input, int inputOffset, int inputLen,
   1940                              byte[] output, int outputOffset)
   1941             throws ShortBufferException, IllegalBlockSizeException,
   1942             BadPaddingException {
   1943         checkCipherState();
   1944 
   1945         // Input sanity check
   1946         if (input == null || inputOffset < 0
   1947             || inputLen > (input.length - inputOffset) || inputLen < 0
   1948             || outputOffset < 0) {
   1949             throw new IllegalArgumentException("Bad arguments");
   1950         }
   1951 
   1952         updateProviderIfNeeded();
   1953         return spi.engineDoFinal(input, inputOffset, inputLen,
   1954                                        output, outputOffset);
   1955     }
   1956 
   1957     /**
   1958      * Encrypts or decrypts data in a single-part operation, or finishes a
   1959      * multiple-part operation. The data is encrypted or decrypted,
   1960      * depending on how this cipher was initialized.
   1961      *
   1962      * <p>All <code>input.remaining()</code> bytes starting at
   1963      * <code>input.position()</code> are processed.
   1964      * If an AEAD mode such as GCM/CCM is being used, the authentication
   1965      * tag is appended in the case of encryption, or verified in the
   1966      * case of decryption.
   1967      * The result is stored in the output buffer.
   1968      * Upon return, the input buffer's position will be equal
   1969      * to its limit; its limit will not have changed. The output buffer's
   1970      * position will have advanced by n, where n is the value returned
   1971      * by this method; the output buffer's limit will not have changed.
   1972      *
   1973      * <p>If <code>output.remaining()</code> bytes are insufficient to
   1974      * hold the result, a <code>ShortBufferException</code> is thrown.
   1975      * In this case, repeat this call with a larger output buffer. Use
   1976      * {@link #getOutputSize(int) getOutputSize} to determine how big
   1977      * the output buffer should be.
   1978      *
   1979      * <p>Upon finishing, this method resets this cipher object to the state
   1980      * it was in when previously initialized via a call to <code>init</code>.
   1981      * That is, the object is reset and available to encrypt or decrypt
   1982      * (depending on the operation mode that was specified in the call to
   1983      * <code>init</code>) more data.
   1984      *
   1985      * <p>Note: if any exception is thrown, this cipher object may need to
   1986      * be reset before it can be used again.
   1987      *
   1988      * <p>Note: this method should be copy-safe, which means the
   1989      * <code>input</code> and <code>output</code> buffers can reference
   1990      * the same byte array and no unprocessed input data is overwritten
   1991      * when the result is copied into the output buffer.
   1992      *
   1993      * @param input the input ByteBuffer
   1994      * @param output the output ByteBuffer
   1995      *
   1996      * @return the number of bytes stored in <code>output</code>
   1997      *
   1998      * @exception IllegalStateException if this cipher is in a wrong state
   1999      * (e.g., has not been initialized)
   2000      * @exception IllegalArgumentException if input and output are the
   2001      *   same object
   2002      * @exception ReadOnlyBufferException if the output buffer is read-only
   2003      * @exception IllegalBlockSizeException if this cipher is a block cipher,
   2004      * no padding has been requested (only in encryption mode), and the total
   2005      * input length of the data processed by this cipher is not a multiple of
   2006      * block size; or if this encryption algorithm is unable to
   2007      * process the input data provided.
   2008      * @exception ShortBufferException if there is insufficient space in the
   2009      * output buffer
   2010      * @exception BadPaddingException if this cipher is in decryption mode,
   2011      * and (un)padding has been requested, but the decrypted data is not
   2012      * bounded by the appropriate padding bytes
   2013      * @exception AEADBadTagException if this cipher is decrypting in an
   2014      * AEAD mode (such as GCM/CCM), and the received authentication tag
   2015      * does not match the calculated value
   2016      *
   2017      * @since 1.5
   2018      */
   2019     public final int doFinal(ByteBuffer input, ByteBuffer output)
   2020             throws ShortBufferException, IllegalBlockSizeException,
   2021             BadPaddingException {
   2022         checkCipherState();
   2023 
   2024         if ((input == null) || (output == null)) {
   2025             throw new IllegalArgumentException("Buffers must not be null");
   2026         }
   2027         if (input == output) {
   2028             throw new IllegalArgumentException("Input and output buffers must "
   2029                 + "not be the same object, consider using buffer.duplicate()");
   2030         }
   2031         if (output.isReadOnly()) {
   2032             throw new ReadOnlyBufferException();
   2033         }
   2034 
   2035         updateProviderIfNeeded();
   2036         return spi.engineDoFinal(input, output);
   2037     }
   2038 
   2039     /**
   2040      * Wrap a key.
   2041      *
   2042      * @param key the key to be wrapped.
   2043      *
   2044      * @return the wrapped key.
   2045      *
   2046      * @exception IllegalStateException if this cipher is in a wrong
   2047      * state (e.g., has not been initialized).
   2048      *
   2049      * @exception IllegalBlockSizeException if this cipher is a block
   2050      * cipher, no padding has been requested, and the length of the
   2051      * encoding of the key to be wrapped is not a
   2052      * multiple of the block size.
   2053      *
   2054      * @exception InvalidKeyException if it is impossible or unsafe to
   2055      * wrap the key with this cipher (e.g., a hardware protected key is
   2056      * being passed to a software-only cipher).
   2057      *
   2058      * @throws UnsupportedOperationException if the corresponding method in the
   2059      * {@code CipherSpi} is not supported.
   2060      */
   2061     public final byte[] wrap(Key key)
   2062             throws IllegalBlockSizeException, InvalidKeyException {
   2063         if (!(this instanceof NullCipher)) {
   2064             if (!initialized) {
   2065                 throw new IllegalStateException("Cipher not initialized");
   2066             }
   2067             if (opmode != Cipher.WRAP_MODE) {
   2068                 throw new IllegalStateException("Cipher not initialized " +
   2069                                                 "for wrapping keys");
   2070             }
   2071         }
   2072 
   2073         updateProviderIfNeeded();
   2074         return spi.engineWrap(key);
   2075     }
   2076 
   2077     /**
   2078      * Unwrap a previously wrapped key.
   2079      *
   2080      * @param wrappedKey the key to be unwrapped.
   2081      *
   2082      * @param wrappedKeyAlgorithm the algorithm associated with the wrapped
   2083      * key.
   2084      *
   2085      * @param wrappedKeyType the type of the wrapped key. This must be one of
   2086      * <code>SECRET_KEY</code>, <code>PRIVATE_KEY</code>, or
   2087      * <code>PUBLIC_KEY</code>.
   2088      *
   2089      * @return the unwrapped key.
   2090      *
   2091      * @exception IllegalStateException if this cipher is in a wrong state
   2092      * (e.g., has not been initialized).
   2093      *
   2094      * @exception NoSuchAlgorithmException if no installed providers
   2095      * can create keys of type <code>wrappedKeyType</code> for the
   2096      * <code>wrappedKeyAlgorithm</code>.
   2097      *
   2098      * @exception InvalidKeyException if <code>wrappedKey</code> does not
   2099      * represent a wrapped key of type <code>wrappedKeyType</code> for
   2100      * the <code>wrappedKeyAlgorithm</code>.
   2101      *
   2102      * @throws UnsupportedOperationException if the corresponding method in the
   2103      * {@code CipherSpi} is not supported.
   2104      */
   2105     public final Key unwrap(byte[] wrappedKey,
   2106                             String wrappedKeyAlgorithm,
   2107                             int wrappedKeyType)
   2108             throws InvalidKeyException, NoSuchAlgorithmException {
   2109 
   2110         if (!(this instanceof NullCipher)) {
   2111             if (!initialized) {
   2112                 throw new IllegalStateException("Cipher not initialized");
   2113             }
   2114             if (opmode != Cipher.UNWRAP_MODE) {
   2115                 throw new IllegalStateException("Cipher not initialized " +
   2116                                                 "for unwrapping keys");
   2117             }
   2118         }
   2119         if ((wrappedKeyType != SECRET_KEY) &&
   2120             (wrappedKeyType != PRIVATE_KEY) &&
   2121             (wrappedKeyType != PUBLIC_KEY)) {
   2122             throw new InvalidParameterException("Invalid key type");
   2123         }
   2124 
   2125         updateProviderIfNeeded();
   2126         return spi.engineUnwrap(wrappedKey,
   2127                                       wrappedKeyAlgorithm,
   2128                                       wrappedKeyType);
   2129     }
   2130 
   2131     private AlgorithmParameterSpec getAlgorithmParameterSpec(
   2132                                       AlgorithmParameters params)
   2133             throws InvalidParameterSpecException {
   2134         if (params == null) {
   2135             return null;
   2136         }
   2137 
   2138         String alg = params.getAlgorithm().toUpperCase(Locale.ENGLISH);
   2139 
   2140         if (alg.equalsIgnoreCase("RC2")) {
   2141             return params.getParameterSpec(RC2ParameterSpec.class);
   2142         }
   2143 
   2144         if (alg.equalsIgnoreCase("RC5")) {
   2145             return params.getParameterSpec(RC5ParameterSpec.class);
   2146         }
   2147 
   2148         if (alg.startsWith("PBE")) {
   2149             return params.getParameterSpec(PBEParameterSpec.class);
   2150         }
   2151 
   2152         if (alg.startsWith("DES")) {
   2153             return params.getParameterSpec(IvParameterSpec.class);
   2154         }
   2155         return null;
   2156     }
   2157 
   2158     /**
   2159      * Returns the maximum key length for the specified transformation
   2160      * according to the installed JCE jurisdiction policy files. If
   2161      * JCE unlimited strength jurisdiction policy files are installed,
   2162      * Integer.MAX_VALUE will be returned.
   2163      * For more information on default key size in JCE jurisdiction
   2164      * policy files, please see Appendix E in the
   2165      * <a href=
   2166      *   "{@docRoot}openjdk-redirect.html?v=8&path=/technotes/guides/security/crypto/CryptoSpec.html#AppC">
   2167      * Java Cryptography Architecture Reference Guide</a>.
   2168      *
   2169      * @param transformation the cipher transformation.
   2170      * @return the maximum key length in bits or Integer.MAX_VALUE.
   2171      * @exception NullPointerException if <code>transformation</code> is null.
   2172      * @exception NoSuchAlgorithmException if <code>transformation</code>
   2173      * is not a valid transformation, i.e. in the form of "algorithm" or
   2174      * "algorithm/mode/padding".
   2175      * @since 1.5
   2176      */
   2177     public static final int getMaxAllowedKeyLength(String transformation)
   2178             throws NoSuchAlgorithmException {
   2179         // Android-changed: Remove references to CryptoPermission.
   2180         // Throw early if transformation == null or isn't valid.
   2181         //
   2182         // CryptoPermission cp = getConfiguredPermission(transformation);
   2183         // return cp.getMaxAllowedKeyLength();
   2184         if (transformation == null) {
   2185             throw new NullPointerException("transformation == null");
   2186         }
   2187         // Throws NoSuchAlgorithmException if necessary.
   2188         tokenizeTransformation(transformation);
   2189         return Integer.MAX_VALUE;
   2190     }
   2191 
   2192     /**
   2193      * Returns an AlgorithmParameterSpec object which contains
   2194      * the maximum cipher parameter value according to the
   2195      * jurisdiction policy file. If JCE unlimited strength jurisdiction
   2196      * policy files are installed or there is no maximum limit on the
   2197      * parameters for the specified transformation in the policy file,
   2198      * null will be returned.
   2199      *
   2200      * @param transformation the cipher transformation.
   2201      * @return an AlgorithmParameterSpec which holds the maximum
   2202      * value or null.
   2203      * @exception NullPointerException if <code>transformation</code>
   2204      * is null.
   2205      * @exception NoSuchAlgorithmException if <code>transformation</code>
   2206      * is not a valid transformation, i.e. in the form of "algorithm" or
   2207      * "algorithm/mode/padding".
   2208      * @since 1.5
   2209      */
   2210     public static final AlgorithmParameterSpec getMaxAllowedParameterSpec(
   2211             String transformation) throws NoSuchAlgorithmException {
   2212         // Android-changed: Remove references to CryptoPermission.
   2213         // Throw early if transformation == null or isn't valid.
   2214         //
   2215         // CryptoPermission cp = getConfiguredPermission(transformation);
   2216         // return cp.getAlgorithmParameterSpec();
   2217         if (transformation == null) {
   2218             throw new NullPointerException("transformation == null");
   2219         }
   2220         // Throws NoSuchAlgorithmException if necessary.
   2221         tokenizeTransformation(transformation);
   2222         return null;
   2223     }
   2224 
   2225     /**
   2226      * Continues a multi-part update of the Additional Authentication
   2227      * Data (AAD).
   2228      * <p>
   2229      * Calls to this method provide AAD to the cipher when operating in
   2230      * modes such as AEAD (GCM/CCM).  If this cipher is operating in
   2231      * either GCM or CCM mode, all AAD must be supplied before beginning
   2232      * operations on the ciphertext (via the {@code update} and {@code
   2233      * doFinal} methods).
   2234      *
   2235      * @param src the buffer containing the Additional Authentication Data
   2236      *
   2237      * @throws IllegalArgumentException if the {@code src}
   2238      * byte array is null
   2239      * @throws IllegalStateException if this cipher is in a wrong state
   2240      * (e.g., has not been initialized), does not accept AAD, or if
   2241      * operating in either GCM or CCM mode and one of the {@code update}
   2242      * methods has already been called for the active
   2243      * encryption/decryption operation
   2244      * @throws UnsupportedOperationException if the corresponding method
   2245      * in the {@code CipherSpi} has not been overridden by an
   2246      * implementation
   2247      *
   2248      * @since 1.7
   2249      */
   2250     public final void updateAAD(byte[] src) {
   2251         if (src == null) {
   2252             throw new IllegalArgumentException("src buffer is null");
   2253         }
   2254 
   2255         updateAAD(src, 0, src.length);
   2256     }
   2257 
   2258     /**
   2259      * Continues a multi-part update of the Additional Authentication
   2260      * Data (AAD), using a subset of the provided buffer.
   2261      * <p>
   2262      * Calls to this method provide AAD to the cipher when operating in
   2263      * modes such as AEAD (GCM/CCM).  If this cipher is operating in
   2264      * either GCM or CCM mode, all AAD must be supplied before beginning
   2265      * operations on the ciphertext (via the {@code update} and {@code
   2266      * doFinal} methods).
   2267      *
   2268      * @param src the buffer containing the AAD
   2269      * @param offset the offset in {@code src} where the AAD input starts
   2270      * @param len the number of AAD bytes
   2271      *
   2272      * @throws IllegalArgumentException if the {@code src}
   2273      * byte array is null, or the {@code offset} or {@code length}
   2274      * is less than 0, or the sum of the {@code offset} and
   2275      * {@code len} is greater than the length of the
   2276      * {@code src} byte array
   2277      * @throws IllegalStateException if this cipher is in a wrong state
   2278      * (e.g., has not been initialized), does not accept AAD, or if
   2279      * operating in either GCM or CCM mode and one of the {@code update}
   2280      * methods has already been called for the active
   2281      * encryption/decryption operation
   2282      * @throws UnsupportedOperationException if the corresponding method
   2283      * in the {@code CipherSpi} has not been overridden by an
   2284      * implementation
   2285      *
   2286      * @since 1.7
   2287      */
   2288     public final void updateAAD(byte[] src, int offset, int len) {
   2289         checkCipherState();
   2290 
   2291         // Input sanity check
   2292         if ((src == null) || (offset < 0) || (len < 0)
   2293                 || ((len + offset) > src.length)) {
   2294             throw new IllegalArgumentException("Bad arguments");
   2295         }
   2296 
   2297         updateProviderIfNeeded();
   2298         if (len == 0) {
   2299             return;
   2300         }
   2301         spi.engineUpdateAAD(src, offset, len);
   2302     }
   2303 
   2304     /**
   2305      * Continues a multi-part update of the Additional Authentication
   2306      * Data (AAD).
   2307      * <p>
   2308      * Calls to this method provide AAD to the cipher when operating in
   2309      * modes such as AEAD (GCM/CCM).  If this cipher is operating in
   2310      * either GCM or CCM mode, all AAD must be supplied before beginning
   2311      * operations on the ciphertext (via the {@code update} and {@code
   2312      * doFinal} methods).
   2313      * <p>
   2314      * All {@code src.remaining()} bytes starting at
   2315      * {@code src.position()} are processed.
   2316      * Upon return, the input buffer's position will be equal
   2317      * to its limit; its limit will not have changed.
   2318      *
   2319      * @param src the buffer containing the AAD
   2320      *
   2321      * @throws IllegalArgumentException if the {@code src ByteBuffer}
   2322      * is null
   2323      * @throws IllegalStateException if this cipher is in a wrong state
   2324      * (e.g., has not been initialized), does not accept AAD, or if
   2325      * operating in either GCM or CCM mode and one of the {@code update}
   2326      * methods has already been called for the active
   2327      * encryption/decryption operation
   2328      * @throws UnsupportedOperationException if the corresponding method
   2329      * in the {@code CipherSpi} has not been overridden by an
   2330      * implementation
   2331      *
   2332      * @since 1.7
   2333      */
   2334     public final void updateAAD(ByteBuffer src) {
   2335         checkCipherState();
   2336 
   2337         // Input sanity check
   2338         if (src == null) {
   2339             throw new IllegalArgumentException("src ByteBuffer is null");
   2340         }
   2341 
   2342         updateProviderIfNeeded();
   2343         if (src.remaining() == 0) {
   2344             return;
   2345         }
   2346         spi.engineUpdateAAD(src);
   2347     }
   2348 
   2349     /**
   2350      * Returns the {@code CipherSpi} backing this {@code Cipher} or {@code null} if no
   2351      * {@code CipherSpi} is backing this {@code Cipher}.
   2352      *
   2353      * @hide
   2354      */
   2355     public CipherSpi getCurrentSpi() {
   2356         return spi;
   2357     }
   2358 
   2359     /** The attribute used for supported paddings. */
   2360     private static final String ATTRIBUTE_PADDINGS = "SupportedPaddings";
   2361 
   2362     /** The attribute used for supported modes. */
   2363     private static final String ATTRIBUTE_MODES = "SupportedModes";
   2364 
   2365     /**
   2366      * If the attribute listed exists, check that it matches the regular
   2367      * expression.
   2368      */
   2369     static boolean matchAttribute(Provider.Service service, String attr, String value) {
   2370         if (value == null) {
   2371             return true;
   2372         }
   2373         final String pattern = service.getAttribute(attr);
   2374         if (pattern == null) {
   2375             return true;
   2376         }
   2377         final String valueUc = value.toUpperCase(Locale.US);
   2378         return valueUc.matches(pattern.toUpperCase(Locale.US));
   2379     }
   2380 
   2381     /** Items that need to be set on the Cipher instance. */
   2382     enum NeedToSet {
   2383         NONE, MODE, PADDING, BOTH,
   2384     }
   2385 
   2386     /**
   2387      * Expresses the various types of transforms that may be used during
   2388      * initialization.
   2389      */
   2390     static class Transform {
   2391         private final String name;
   2392         private final NeedToSet needToSet;
   2393 
   2394         public Transform(String name, NeedToSet needToSet) {
   2395             this.name = name;
   2396             this.needToSet = needToSet;
   2397         }
   2398     }
   2399 
   2400     /**
   2401      * Keeps track of the possible arguments to {@code Cipher#init(...)}.
   2402      */
   2403     static class InitParams {
   2404         final InitType initType;
   2405         final int opmode;
   2406         final Key key;
   2407         final SecureRandom random;
   2408         final AlgorithmParameterSpec spec;
   2409         final AlgorithmParameters params;
   2410 
   2411         InitParams(InitType initType, int opmode, Key key, SecureRandom random,
   2412                 AlgorithmParameterSpec spec, AlgorithmParameters params) {
   2413             this.initType = initType;
   2414             this.opmode = opmode;
   2415             this.key = key;
   2416             this.random = random;
   2417             this.spec = spec;
   2418             this.params = params;
   2419         }
   2420     }
   2421 
   2422     /**
   2423      * Used to keep track of which underlying {@code CipherSpi#engineInit(...)}
   2424      * variant to call when testing suitability.
   2425      */
   2426     static enum InitType {
   2427         KEY, ALGORITHM_PARAMS, ALGORITHM_PARAM_SPEC,
   2428     }
   2429 
   2430     class SpiAndProviderUpdater {
   2431         /**
   2432          * Lock held while the SPI is initializing.
   2433          */
   2434         private final Object initSpiLock = new Object();
   2435 
   2436         /**
   2437          * The provider specified when instance created.
   2438          */
   2439         private final Provider specifiedProvider;
   2440 
   2441         /**
   2442          * The SPI implementation.
   2443          */
   2444         private final CipherSpi specifiedSpi;
   2445 
   2446         SpiAndProviderUpdater(Provider specifiedProvider, CipherSpi specifiedSpi) {
   2447             this.specifiedProvider = specifiedProvider;
   2448             this.specifiedSpi = specifiedSpi;
   2449         }
   2450 
   2451         void setCipherSpiImplAndProvider(CipherSpi cipherSpi, Provider provider) {
   2452             Cipher.this.spi = cipherSpi;
   2453             Cipher.this.provider = provider;
   2454         }
   2455 
   2456         /**
   2457          * Makes sure a CipherSpi that matches this type is selected. If
   2458          * {@code key != null} then it assumes that a suitable provider exists for
   2459          * this instance (used by {@link Cipher#init}. If the {@code initParams} is passed
   2460          * in, then the {@code CipherSpi} returned will be initialized.
   2461          *
   2462          * @throws InvalidKeyException if the specified key cannot be used to
   2463          *                             initialize this cipher.
   2464          */
   2465         CipherSpiAndProvider updateAndGetSpiAndProvider(
   2466                 InitParams initParams,
   2467                 CipherSpi spiImpl,
   2468                 Provider provider)
   2469                 throws InvalidKeyException, InvalidAlgorithmParameterException {
   2470             if (specifiedSpi != null) {
   2471                 return new CipherSpiAndProvider(specifiedSpi, provider);
   2472             }
   2473             synchronized (initSpiLock) {
   2474                 // This is not only a matter of performance. Many methods like update, doFinal, etc.
   2475                 // call {@code #getSpi()} (ie, {@code #getSpi(null /* params */)}) and without this
   2476                 // shortcut they would override an spi that was chosen using the key.
   2477                 if (spiImpl != null && initParams == null) {
   2478                     return new CipherSpiAndProvider(spiImpl, provider);
   2479                 }
   2480                 final CipherSpiAndProvider sap = tryCombinations(
   2481                         initParams, specifiedProvider, tokenizedTransformation);
   2482                 if (sap == null) {
   2483                     throw new ProviderException("No provider found for "
   2484                             + Arrays.toString(tokenizedTransformation));
   2485                 }
   2486                 setCipherSpiImplAndProvider(sap.cipherSpi, sap.provider);
   2487                 return new CipherSpiAndProvider(sap.cipherSpi, sap.provider);
   2488             }
   2489         }
   2490 
   2491         /**
   2492          * Convenience call when the Key is not available.
   2493          */
   2494         CipherSpiAndProvider updateAndGetSpiAndProvider(CipherSpi spiImpl, Provider provider) {
   2495             try {
   2496                 return updateAndGetSpiAndProvider(null, spiImpl, provider);
   2497             } catch (InvalidKeyException | InvalidAlgorithmParameterException e) {
   2498                 throw new ProviderException("Exception thrown when params == null", e);
   2499            }
   2500         }
   2501 
   2502         CipherSpi getCurrentSpi(CipherSpi spiImpl) {
   2503             if (specifiedSpi != null) {
   2504                 return specifiedSpi;
   2505             }
   2506 
   2507             synchronized (initSpiLock) {
   2508                 return spiImpl;
   2509             }
   2510         }
   2511     }
   2512 
   2513     /**
   2514      * Tries to find the correct {@code Cipher} transform to use. Returns a
   2515      * {@link org.apache.harmony.security.fortress.Engine.SpiAndProvider}, throws the first exception that was
   2516      * encountered during attempted initialization, or {@code null} if there are
   2517      * no providers that support the {@code initParams}.
   2518      * <p>
   2519      * {@code tokenizedTransformation} must be in the format returned by
   2520      * {@link Cipher#checkTransformation(String)}. The combinations of mode strings
   2521      * tried are as follows:
   2522      * <ul>
   2523      * <li><code>[cipher]/[mode]/[padding]</code>
   2524      * <li><code>[cipher]/[mode]</code>
   2525      * <li><code>[cipher]//[padding]</code>
   2526      * <li><code>[cipher]</code>
   2527      * </ul>
   2528      * {@code services} is a list of cipher services. Needs to be non-null only if
   2529      * {@code provider != null}
   2530      */
   2531     static CipherSpiAndProvider tryCombinations(InitParams initParams, Provider provider,
   2532             String[] tokenizedTransformation)
   2533             throws InvalidKeyException,
   2534             InvalidAlgorithmParameterException {
   2535         // Enumerate all the transforms we need to try
   2536         ArrayList<Transform> transforms = new ArrayList<Transform>();
   2537         if (tokenizedTransformation[1] != null && tokenizedTransformation[2] != null) {
   2538             transforms.add(new Transform(tokenizedTransformation[0] + "/" + tokenizedTransformation[1] + "/"
   2539                     + tokenizedTransformation[2], NeedToSet.NONE));
   2540         }
   2541         if (tokenizedTransformation[1] != null) {
   2542             transforms.add(new Transform(tokenizedTransformation[0] + "/" + tokenizedTransformation[1],
   2543                     NeedToSet.PADDING));
   2544         }
   2545         if (tokenizedTransformation[2] != null) {
   2546             transforms.add(new Transform(tokenizedTransformation[0] + "//" + tokenizedTransformation[2],
   2547                     NeedToSet.MODE));
   2548         }
   2549         transforms.add(new Transform(tokenizedTransformation[0], NeedToSet.BOTH));
   2550 
   2551         // Try each of the transforms and keep track of the first exception
   2552         // encountered.
   2553         Exception cause = null;
   2554 
   2555         if (provider != null) {
   2556             for (Transform transform : transforms) {
   2557                 Provider.Service service = provider.getService("Cipher", transform.name);
   2558                 if (service == null) {
   2559                     continue;
   2560                 }
   2561                 return tryTransformWithProvider(initParams, tokenizedTransformation, transform.needToSet,
   2562                                 service);
   2563             }
   2564         } else {
   2565             for (Provider prov : Security.getProviders()) {
   2566                 for (Transform transform : transforms) {
   2567                     Provider.Service service = prov.getService("Cipher", transform.name);
   2568                     if (service == null) {
   2569                         continue;
   2570                     }
   2571 
   2572                     if (initParams == null || initParams.key == null
   2573                             || service.supportsParameter(initParams.key)) {
   2574                         try {
   2575                             CipherSpiAndProvider sap = tryTransformWithProvider(initParams,
   2576                                     tokenizedTransformation, transform.needToSet, service);
   2577                             if (sap != null) {
   2578                                 return sap;
   2579                             }
   2580                         } catch (Exception e) {
   2581                             if (cause == null) {
   2582                                 cause = e;
   2583                             }
   2584                         }
   2585                     }
   2586                 }
   2587             }
   2588         }
   2589         if (cause instanceof InvalidKeyException) {
   2590             throw (InvalidKeyException) cause;
   2591         } else if (cause instanceof InvalidAlgorithmParameterException) {
   2592             throw (InvalidAlgorithmParameterException) cause;
   2593         } else if (cause instanceof RuntimeException) {
   2594             throw (RuntimeException) cause;
   2595         } else if (cause != null) {
   2596             throw new InvalidKeyException("No provider can be initialized with given key", cause);
   2597         } else if (initParams == null || initParams.key == null) {
   2598             return null;
   2599         } else {
   2600             // Since the key is not null, a suitable provider exists,
   2601             // and it is an InvalidKeyException.
   2602             throw new InvalidKeyException(
   2603                     "No provider offers " + Arrays.toString(tokenizedTransformation) + " for "
   2604                     + initParams.key.getAlgorithm() + " key of class "
   2605                     + initParams.key.getClass().getName() + " and export format "
   2606                     + initParams.key.getFormat());
   2607         }
   2608     }
   2609 
   2610     static class CipherSpiAndProvider {
   2611         CipherSpi cipherSpi;
   2612         Provider provider;
   2613 
   2614         CipherSpiAndProvider(CipherSpi cipherSpi, Provider provider) {
   2615             this.cipherSpi = cipherSpi;
   2616             this.provider = provider;
   2617         }
   2618     }
   2619 
   2620     /**
   2621      * Tries to initialize the {@code Cipher} from a given {@code service}. If
   2622      * initialization is successful, the initialized {@code spi} is returned. If
   2623      * the {@code service} cannot be initialized with the specified
   2624      * {@code initParams}, then it's expected to throw
   2625      * {@code InvalidKeyException} or {@code InvalidAlgorithmParameterException}
   2626      * as a hint to the caller that it should continue searching for a
   2627      * {@code Service} that will work.
   2628      */
   2629     static CipherSpiAndProvider tryTransformWithProvider(InitParams initParams,
   2630             String[] tokenizedTransformation, NeedToSet type, Provider.Service service)
   2631                 throws InvalidKeyException, InvalidAlgorithmParameterException  {
   2632         try {
   2633             /*
   2634              * Check to see if the Cipher even supports the attributes before
   2635              * trying to instantiate it.
   2636              */
   2637             if (!matchAttribute(service, ATTRIBUTE_MODES, tokenizedTransformation[1])
   2638                     || !matchAttribute(service, ATTRIBUTE_PADDINGS, tokenizedTransformation[2])) {
   2639                 return null;
   2640             }
   2641 
   2642             CipherSpiAndProvider sap = new CipherSpiAndProvider(
   2643                 (CipherSpi) service.newInstance(null), service.getProvider());
   2644             if (sap.cipherSpi == null || sap.provider == null) {
   2645                 return null;
   2646             }
   2647             CipherSpi spi = sap.cipherSpi;
   2648             if (((type == NeedToSet.MODE) || (type == NeedToSet.BOTH))
   2649                     && (tokenizedTransformation[1] != null)) {
   2650                 spi.engineSetMode(tokenizedTransformation[1]);
   2651             }
   2652             if (((type == NeedToSet.PADDING) || (type == NeedToSet.BOTH))
   2653                     && (tokenizedTransformation[2] != null)) {
   2654                 spi.engineSetPadding(tokenizedTransformation[2]);
   2655             }
   2656 
   2657             if (initParams != null) {
   2658                 switch (initParams.initType) {
   2659                     case ALGORITHM_PARAMS:
   2660                         spi.engineInit(initParams.opmode, initParams.key, initParams.params,
   2661                                 initParams.random);
   2662                         break;
   2663                     case ALGORITHM_PARAM_SPEC:
   2664                         spi.engineInit(initParams.opmode, initParams.key, initParams.spec,
   2665                                 initParams.random);
   2666                         break;
   2667                     case KEY:
   2668                         spi.engineInit(initParams.opmode, initParams.key, initParams.random);
   2669                         break;
   2670                     default:
   2671                         throw new AssertionError("This should never be reached");
   2672                 }
   2673             }
   2674             return new CipherSpiAndProvider(spi, sap.provider);
   2675         } catch (NoSuchAlgorithmException ignored) {
   2676         } catch (NoSuchPaddingException ignored) {
   2677         }
   2678         return null;
   2679     }
   2680 }
   2681