javax.crypto

接口
异常
java.lang.Object
  继承者 javax.crypto.CipherSpi

public abstract class CipherSpi
     
extends Object

此类为 Cipher 类定义了服务提供者接口 (SPI)。此类中的所有抽象方法都必须由每个想要提供实现特定 cipher 算法的加密服务提供者实现。

为创建封装了此 CipherSpi 类实例的 Cipher 实例,应用程序调用 Cipher 引擎类的 getInstance 工厂方法之一并指定请求的转换。作为可选项,应用程序还可以指定提供者的名称。

转换 是描述为产生某种输出而在给定的输入上执行的操作(或一组操作)的字符串。转换始终包括加密算法的名称(例如,DES),后面可能跟有一个反馈模式和填充方案。

转换具有下面的形式:

  • "算法/模式/填充”或

  • "算法

(后一种情况下,使用此模式和填充方案的特定于提供者的默认值)。例如,以下是有效的转换:

     Cipher c = Cipher.getInstance("DES/CBC/PKCS5Padding");
 

一个提供者可能为每个算法/模式/填充 组合提供一个单独的类,也有可能决定提供多个表示与算法算法/模式算法//填充 (注意,是双斜线)对应的子转换的一般类,在这种情况下,请求的模式和/或填充由 CiphergetInstance 方法自动设置,它调用的是提供者的 CipherSpi 子类的 engineSetModeengineSetPadding 方法。

提供者主类中的 Cipher 属性可能具有以下格式之一:

  •      // provider's subclass of "CipherSpi" implements "algName" with
         // pluggable mode and padding
         Cipher.algName
     
  •      // provider's subclass of "CipherSpi" implements "algName" in the
         // specified "mode", with pluggable padding
         Cipher.algName/mode
     
  •      // provider's subclass of "CipherSpi" implements "algName" with the
         // specified "padding", with pluggable mode
         Cipher.algName//padding
     
  •      // provider's subclass of "CipherSpi" implements "algName" with the
         // specified "mode" and "padding"
         Cipher.algName/mode/padding
     

例如,某提供者可能提供实现 DES/ECB/PKCS5PaddingCipherSpi 子类,以及实现 DES/CBC/PKCS5PaddingDES/CFB/PKCS5PaddingDES/OFB/PKCS5PaddingCipherSpi 子类。该提供者在其主类中将有以下 Cipher 属性:

  •      Cipher.DES/ECB/PKCS5Padding
     
  •      Cipher.DES/CBC/PKCS5Padding
     
  •      Cipher.DES/CFB/PKCS5Padding
     
  •      Cipher.DES/OFB/PKCS5Padding
     

另一个提供者可能实现一个用于以上每个模式的类(即一个用于 ECB 的类、一个用于 CBC 的类、一个用于 CFB 的类及一个用于 OFB 的类),一个用于 PKCS5Padding 的类,以及一个通过子类化 CipherSpi 所得到的通用 DES 类。该提供者在其主类中将有以下 Cipher 属性:

  •      Cipher.DES
     

Cipher 引擎类的 getInstance 工厂方法遵守这些规则,以便为“算法”形式的转换实例化提供者的 CipherSpi 实现:

  1. 检查提供者是否已为指定的“算法”注册了一个 CipherSpi 子类。

    如果已经注册,则实例化此类,使用其模式和填充方案的默认值(由提供者给出)。

    如果未注册,则抛出 NoSuchAlgorithmException

Cipher 引擎类的 getInstance 工厂方法遵守这些规则,以便为“算法/模式/填充”形式的转换实例化提供者的 CipherSpi 实现:

  1. 检查提供者是否已为指定的“算法/模式/填充”转换注册了一个 CipherSpi 子类。

    如果已注册,则将其实例化。

    如果未注册,则转到下一步。

  2. 检查提供者是否已为“算法/模式”子转换注册了一个 CipherSpi 子类。

    如果已注册,则将其实例化,并在新实例上调用 engineSetPadding(padding)

    如果未注册,则转到下一步。

  3. 检查提供者是否已为“算法//填充”子转换注册了一个 CipherSpi 子类(注意,是双斜线的)。

    如果已注册,则将其实例化,并在新实例上调用 engineSetMode(mode)

    如果未注册,则转到下一步。

  4. 检查提供者是否已为“算法”子转换注册了一个 CipherSpi 子类。

    如果已注册,则将其实例化,并在新实例上调用 engineSetMode(mode)engineSetPadding(padding)

    如果未注册,则抛出 NoSuchAlgorithmException

从以下版本开始:
1.4
另请参见:
KeyGenerator, SecretKey

构造方法摘要
CipherSpi()
           
 
方法摘要
protected abstract  byte[] engineDoFinal(byte[] input, int inputOffset, int inputLen)
          按单部分操作加密或解密数据,或者结束一个多部分操作。
protected abstract  int engineDoFinal(byte[] input, int inputOffset, int inputLen, byte[] output, int outputOffset)
          按单部分操作加密或解密数据,或者结束一个多部分操作。
protected  int engineDoFinal(ByteBuffer input, ByteBuffer output)
          按单部分操作加密或解密数据,或者结束一个多部分操作。
protected abstract  int engineGetBlockSize()
          返回块的大小(以字节为单位)。
protected abstract  byte[] engineGetIV()
          返回新缓冲区中的初始化向量 (IV)。
protected  int engineGetKeySize(Key key)
          返回给定密钥对象的密钥大小,以位为单位。
protected abstract  int engineGetOutputSize(int inputLen)
          在给定了输入长度 inputLen(以字节为单位)的情况下,返回用于保存下一个 updatedoFinal 操作结果所需的输出缓冲区长度的字节数。
protected abstract  AlgorithmParameters engineGetParameters()
          返回此 cipher 使用的参数。
protected abstract  void engineInit(int opmode, Key key, AlgorithmParameterSpec params, SecureRandom random)
          用一个密钥、一组算法参数和一个随机源初始化此 cipher。
protected abstract  void engineInit(int opmode, Key key, AlgorithmParameters params, SecureRandom random)
          用一个密钥、一组算法参数和一个随机源初始化此 cipher。
protected abstract  void engineInit(int opmode, Key key, SecureRandom random)
          用密钥和随机源初始化此 cipher。
protected abstract  void engineSetMode(String mode)
          设置此 cipher 的模式。
protected abstract  void engineSetPadding(String padding)
          设置此 cipher 的填充机制。
protected  Key engineUnwrap(byte[] wrappedKey, String wrappedKeyAlgorithm, int wrappedKeyType)
          打开一个以前包装的密钥。
protected abstract  byte[] engineUpdate(byte[] input, int inputOffset, int inputLen)
          继续多部分加密或解密操作(取决于此 cipher 的初始化方式),以处理其他数据部分。
protected abstract  int engineUpdate(byte[] input, int inputOffset, int inputLen, byte[] output, int outputOffset)
          继续多部分加密或解密操作(取决于此 cipher 的初始化方式),以处理其他数据部分。
protected  int engineUpdate(ByteBuffer input, ByteBuffer output)
          继续多部分加密或解密操作(取决于此 cipher 的初始化方式),以处理其他数据部分。
protected  byte[] engineWrap(Key key)
          将密钥包装。
 
从类 java.lang.Object 继承的方法
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
 

构造方法详细信息

CipherSpi

public CipherSpi()
方法详细信息

engineSetMode

protected abstract void engineSetMode(String mode)
                               throws NoSuchAlgorithmException
设置此 cipher 的模式。

参数:
mode - cipher 模式
抛出:
NoSuchAlgorithmException - 如果请求的 cipher 模式不存在

engineSetPadding

protected abstract void engineSetPadding(String padding)
                                  throws NoSuchPaddingException
设置此 cipher 的填充机制。

参数:
padding - 填充机制
抛出:
NoSuchPaddingException - 如果请求的填充机制不存在

engineGetBlockSize

protected abstract int engineGetBlockSize()
返回块的大小(以字节为单位)。

返回:
块的大小(以字节为单位),如果底层算法不是块 cipher,则返回 0

engineGetOutputSize

protected abstract int engineGetOutputSize(int inputLen)
在给定了输入长度 inputLen(以字节为单位)的情况下,返回用于保存下一个 updatedoFinal 操作结果所需的输出缓冲区长度的字节数。

此调用还考虑到来自上一个 update 调用的任何未处理(已缓存)的数据和填充。

下一个 updatedoFinal 调用的实际输出长度可能小于此方法返回的长度。

参数:
inputLen - 输入长度(以字节为单位)
返回:
所需的输出缓冲区大小(以字节为单位)

engineGetIV

protected abstract byte[] engineGetIV()
返回新缓冲区中的初始化向量 (IV)。

此方法在基于密码的加密或解密上下文中很有用,此时 IV 派生自用户提供的 passphrase。

返回:
新缓冲区中的初始化向量,如果底层算法不使用 IV,或 IV 尚未设置,则返回 null。

engineGetParameters

protected abstract AlgorithmParameters engineGetParameters()
返回此 cipher 使用的参数。

返回的参数可能与初始化此 cipher 所使用的参数相同;如果此 cipher 要求使用算法参数但却未使用任何参数进行初始化,则返回的参数可能会包含由默认值和底层 cipher 实现所使用的随机参数值的组合。

返回:
此 cipher 使用的参数,如果此 cipher 不使用任何参数,则返回 null。

engineInit

protected abstract void engineInit(int opmode,
                                   Key key,
                                   SecureRandom random)
                            throws InvalidKeyException
用密钥和随机源初始化此 cipher。

为以下 4 种操作之一初始化该 cipher:加密、解密、密钥包装或密钥打开,这取决于 opmode 的值。

如果此 cipher 要求使用任何算法参数,而此参数又无法从给定的 key 派生,则在被初始化为加密或密钥包装时,底层 cipher 实现将会自己生成所需的参数(使用特定于提供者的默认或随机值);在初始化为解密或密钥打开时,将引发 InvalidKeyException。可以用 engineGetParametersengineGetIV 获取生成的参数(如果该参数为 IV)。

如果此 cipher(包括其底层反馈或填充方案)要求使用任何随机字节(例如,用于参数生成),那么它将从 random 获取这些随机字节。

注意,当初始化 Cipher 对象时,它将失去所有以前获得的状态。换句话说,初始化 Cipher 相当于创建该 Cipher 的一个新实例并将其初始化。

参数:
opmode - 此 cipher 的操作模式(其为如下之一: ENCRYPT_MODEDECRYPT_MODEWRAP_MODEUNWRAP_MODE
key - 加密密钥
random - 随机源
抛出:
InvalidKeyException - 如果给定的 key 不适合初始化此 cipher,如果要将此 cipher 初始化为解密,并且它所要求的算法参数无法从给定的 key 确定。

engineInit

protected abstract void engineInit(int opmode,
                                   Key key,
                                   AlgorithmParameterSpec params,
                                   SecureRandom random)
                            throws InvalidKeyException,
                                   InvalidAlgorithmParameterException
用一个密钥、一组算法参数和一个随机源初始化此 cipher。

为以下 4 种操作之一初始化该 cipher:加密、解密、密钥包装或密钥打开,这取决于 opmode 的值。

如果此 cipher 要求使用任何算法参数,而 params 为 null,则在被初始化为加密或密钥包装时,底层 cipher 实现将会自己生成所需的参数(使用特定于提供者的默认或随机值);在初始化为解密或密钥打开时,将引发 InvalidAlgorithmParameterException。可以用 engineGetParametersengineGetIV 获取生成的参数(如果该参数为 IV)。

如果此 cipher(包括其底层反馈或填充方案)要求使用任何随机字节(例如,用于参数生成),那么它将从 random 获取这些随机字节。

注意,当初始化 Cipher 对象时,它将失去所有以前获得的状态。换句话说,初始化 Cipher 相当于创建该 Cipher 的一个新实例并将其初始化。

参数:
opmode - 此 cipher 的操作模式(其为如下之一: ENCRYPT_MODEDECRYPT_MODEWRAP_MODEUNWRAP_MODE
key - 加密密钥
params - 算法参数
random - 随机源
抛出:
InvalidKeyException - 如果给定的 key 不适合初始化此 cipher
InvalidAlgorithmParameterException - 如果给定的算法参数不适合此 cipher,如果要将此 cipher 初始化为解密,并且要求使用算法参数,而 params 为 null。

engineInit

protected abstract void engineInit(int opmode,
                                   Key key,
                                   AlgorithmParameters params,
                                   SecureRandom random)
                            throws InvalidKeyException,
                                   InvalidAlgorithmParameterException
用一个密钥、一组算法参数和一个随机源初始化此 cipher。

为以下 4 种操作之一初始化该 cipher:加密、解密、密钥包装或密钥打开,这取决于 opmode 的值。

如果此 cipher 要求使用任何算法参数,而 params 为 null,则在被初始化为加密或密钥包装时,底层 cipher 实现将会自己生成所需的参数(使用特定于提供者的默认或随机值);在初始化为解密或密钥打开时,将引发 InvalidAlgorithmParameterException。可以用 engineGetParametersengineGetIV 获取生成的参数(如果该参数为 IV)。

如果此 cipher(包括其底层反馈或填充方案)要求使用任何随机字节(例如,用于参数生成),那么它将从 random 获取这些随机字节。

注意,当初始化 Cipher 对象时,它将失去所有以前获得的状态。换句话说,初始化 Cipher 相当于创建该 Cipher 的一个新实例并将其初始化。

参数:
opmode - 此 cipher 的操作模式(其为如下之一: ENCRYPT_MODEDECRYPT_MODEWRAP_MODEUNWRAP_MODE
key - 加密密钥
params - 算法参数
random - 随机源
抛出:
InvalidKeyException - 如果给定的 key 不适合初始化此 cipher
InvalidAlgorithmParameterException - 如果给定的算法参数不适合此 cipher,如果要将此 cipher 初始化为解密,并且要求使用算法参数,而 params 为 null。

engineUpdate

protected abstract byte[] engineUpdate(byte[] input,
                                       int inputOffset,
                                       int inputLen)
继续多部分加密或解密操作(取决于此 cipher 的初始化方式),以处理其他数据部分。

处理 input 缓冲区中从 inputOffset 开始(包含)的前 inputLen 个字节,并将结果存储在新的缓冲区中。

参数:
input - 输入缓冲区
inputOffset - input 中输入开始位置的偏移量
inputLen - 输入长度
返回:
包含结果的新缓冲区,如果底层 cipher 为块 cipher 并且输入数据太短而无法形成新的块时,则返回 null。

engineUpdate

protected abstract int engineUpdate(byte[] input,
                                    int inputOffset,
                                    int inputLen,
                                    byte[] output,
                                    int outputOffset)
                             throws ShortBufferException
继续多部分加密或解密操作(取决于此 cipher 的初始化方式),以处理其他数据部分。

处理 input 缓冲区中从 inputOffset 开始(包含)的前 inputLen 个字节,并将结果存储在 output 缓冲区中从 outputOffset 开始(包含)的位置。

如果 output 缓冲区太小无法保存该结果,则抛出 ShortBufferException

参数:
input - 输入缓冲区
inputOffset - input 中输入开始位置的偏移量
inputLen - 输入长度
output - 保存结果的缓冲区
outputOffset - output 中存储结果的位置的偏移量
返回:
output 中存储的字节数
抛出:
ShortBufferException - 如果给定的输出缓冲区太小无法保存该结果

engineUpdate

protected int engineUpdate(ByteBuffer input,
                           ByteBuffer output)
                    throws ShortBufferException
继续多部分加密或解密操作(取决于此 cipher 的初始化方式),以处理其他数据部分。

处理从 input.position() 开始的所有 input.remaining() 字节。结果存储在输出缓冲区中。返回时,输入缓冲区的位置将等于其限制;其限制并未改变。输出缓冲区的位置将前移 n,其中 n 为此方法返回的值;输出缓冲区的限制并未改变。

如果 output.remaining() 个字节还不够保存该结果,则抛出 ShortBufferException

如果能够比 byte 数组更有效地处理 ByteBuffer,子类应考虑重写此方法。

参数:
input - 输入 ByteBuffer
output - 输出 ByteBuffer
返回:
output 中存储的字节数
抛出:
ShortBufferException - 如果输出缓冲区中没有足够的空间
NullPointerException - 如果任一参数为 null
从以下版本开始:
1.5

engineDoFinal

protected abstract byte[] engineDoFinal(byte[] input,
                                        int inputOffset,
                                        int inputLen)
                                 throws IllegalBlockSizeException,
                                        BadPaddingException
按单部分操作加密或解密数据,或者结束一个多部分操作。数据被加密还是解密取决于此 cipher 的初始化方式。

处理 input 缓冲区中从 inputOffset 开始(包含)的前 inputLen 个字节以及可能在上一次 update 操作过程中已缓存的任何输入字节,其中应用了填充(如果需要)。结果存储在新缓冲区中。

结束时,此方法将把此 cipher 对象重置为上一次调用 engineInit 初始化得到的状态。即重置该对象,可供加密或解密(取决于调用 engineInit 时指定的操作模式)更多的数据。

注:如果抛出了任何异常,则再次使用此 cipher 对象前,可能需要将其重置。

参数:
input - 输入缓冲区
inputOffset - input 中输入开始位置的偏移量
inputLen - 输入长度
返回:
存储结果的新缓冲区
抛出:
IllegalBlockSizeException - 如果此 cipher 为块 cipher,未请求任何填充(只针对加密模式),并且由此 cipher 处理的数据总输入长度不是块大小的倍数,如果此加密算法无法处理所提供的输入数据。
BadPaddingException - 如果此 cipher 为解密模式,并且未请求填充或不填充,但解密的数据没有用适当的填充字节所限制

engineDoFinal

protected abstract int engineDoFinal(byte[] input,
                                     int inputOffset,
                                     int inputLen,
                                     byte[] output,
                                     int outputOffset)
                              throws ShortBufferException,
                                     IllegalBlockSizeException,
                                     BadPaddingException
按单部分操作加密或解密数据,或者结束一个多部分操作。数据被加密还是解密取决于此 cipher 的初始化方式。

处理 input 缓冲区中从 inputOffset 开始(包含)的前 inputLen 个字节以及可能在上一次 update 操作过程中已缓存的任何输入字节,其中应用了填充(如果需要)。结果存储在 output 缓冲区中从 outputOffset(包含)开始的位置。

如果 output 缓冲区太小无法保存该结果,则抛出 ShortBufferException

结束时,此方法将把此 cipher 对象重置为上一次调用 engineInit 初始化得到的状态。即重置该对象,可供加密或解密(取决于调用 engineInit 时指定的操作模式)更多的数据。

注:如果抛出了任何异常,则再次使用此 cipher 对象前,可能需要将其重置。

参数:
input - 输入缓冲区
inputOffset - input 中输入开始位置的偏移量
inputLen - 输入长度
output - 保存结果的缓冲区
outputOffset - output 中存储结果的位置的偏移量
返回:
output 中存储的字节数
抛出:
IllegalBlockSizeException - 如果此 cipher 为块 cipher,未请求任何填充(只针对加密模式),并且由此 cipher 处理的数据总输入长度不是块大小的倍数,如果此加密算法无法处理所提供的输入数据。
ShortBufferException - 如果给定的输出缓冲区太小无法保存结果
BadPaddingException - 如果 cipher 为解密模式,并且未请求填充或不填充,但解密的数据没有用适当的填充字节所限制

engineDoFinal

protected int engineDoFinal(ByteBuffer input,
                            ByteBuffer output)
                     throws ShortBufferException,
                            IllegalBlockSizeException,
                            BadPaddingException
按单部分操作加密或解密数据,或者结束一个多部分操作。数据被加密还是解密取决于此 cipher 的初始化方式。

处理从 input.position() 开始的所有 input.remaining() 字节。结果存储在输出缓冲区中。返回时,输入缓冲区的位置将等于其限制;其限制并未改变。输出缓冲区的位置将前移 n,其中 n 为此方法返回的值;输出缓冲区的限制并未改变。

如果 output.remaining() 个字节还不够保存该结果,则抛出 ShortBufferException

结束时,此方法将把此 cipher 对象重置为上一次调用 engineInit 初始化得到的状态。即重置该对象,可供加密或解密(取决于调用 engineInit 时指定的操作模式)更多的数据。

注:如果抛出了任何异常,则再次使用此 cipher 对象前,可能需要将其重置。

如果能够比 byte 数组更有效地处理 ByteBuffer,子类应考虑重写此方法。

参数:
input - 输入 ByteBuffer
output - 输出 ByteBuffer
返回:
output 中存储的字节数
抛出:
IllegalBlockSizeException - 如果此 cipher 为块 cipher,未请求任何填充(只针对加密模式),并且由此 cipher 处理的数据总输入长度不是块大小的倍数,如果此加密算法无法处理所提供的输入数据。
ShortBufferException - 如果输出缓冲区没有足够的空间
BadPaddingException - 如果 cipher 为解密模式,并且未请求填充或不填充,但解密的数据没有用适当的填充字节所限制
NullPointerException - 如果任一参数为 null
从以下版本开始:
1.5

engineWrap

protected byte[] engineWrap(Key key)
                     throws IllegalBlockSizeException,
                            InvalidKeyException
将密钥包装。

已将此具体方法添加到了先前定义过的抽象类中。(为向后兼容,它不能为抽象方法)。可以由提供者重写以包装该密钥。如果给定的密钥无法被包装,则这样的重写可能会抛出 IllegalBlockSizeException 或 InvalidKeyException (在指定情况下)。如果不重写此方法,则它总是抛出 UnsupportedOperationException。

参数:
key - 要包装的密钥。
返回:
已包装的密钥。
抛出:
IllegalBlockSizeException - 如果此 cipher 为块 cipher,未请求填充,并且要包装的密钥的编码长度不是块大小的倍数。
InvalidKeyException - 如果不可能用此 cipher 包装该密钥,或这样做不安全(例如,将一个硬件保护的密钥传给只要求软件保护的 cipher)。

engineUnwrap

protected Key engineUnwrap(byte[] wrappedKey,
                           String wrappedKeyAlgorithm,
                           int wrappedKeyType)
                    throws InvalidKeyException,
                           NoSuchAlgorithmException
打开一个以前包装的密钥。

已将此具体方法添加到了先前定义过的抽象类中。(为向后兼容,它不能为抽象方法)。可以由提供者重写以打开以前包装的密钥。如果无法打开给定的包装密钥,则这样的重写可能会抛出 InvalidKeyException。如果不重写此方法,则它总是抛出 UnsupportedOperationException。

参数:
wrappedKey - 要打开的密钥。
wrappedKeyAlgorithm - 与此包装密钥关联的算法。
wrappedKeyType - 已包装密钥的类型。此类型为 SECRET_KEYPRIVATE_KEYPUBLIC_KEY 之一。
返回:
打开的密钥。
抛出:
NoSuchAlgorithmException - 如果没有一个已安装的提供者能够为 wrappedKeyAlgorithm 创建类型为 wrappedKeyType 的密钥。
InvalidKeyException - 如果 wrappedKey 并不为 wrappedKeyAlgorithm 表示类型为 wrappedKeyType 的已包装密钥。

engineGetKeySize

protected int engineGetKeySize(Key key)
                        throws InvalidKeyException
返回给定密钥对象的密钥大小,以位为单位。

已将此具体方法添加到了先前定义过的抽象类中。如果提供者未重写此方法,则将抛出 UnsupportedOperationException

参数:
key - 密钥对象
返回:
给定密钥对象的密钥大小。
抛出:
InvalidKeyException - 如果 key 无效。