javax.crypto.BadPaddingException: Given final block not properly padded

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了javax.crypto.BadPaddingException: Given final block not properly padded相关的知识,希望对你有一定的参考价值。

加解密代码如下:
public static byte[] encryptRes(byte[] data, byte[] desKey)
try
IvParameterSpec spec = new IvParameterSpec(desKey);
DESKeySpec dks = new DESKeySpec(desKey);
SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("DES");
SecretKey securekey = keyFactory.generateSecret(dks);

Cipher cipher = Cipher.getInstance("DES/CBC/PKCS5Padding");
cipher.init(Cipher.ENCRYPT_MODE, securekey, spec);
byte[] encryptContent = cipher.doFinal(data);
return encryptContent;
catch (Exception e)
return null;



public static byte[] decryptRes(byte[] data, byte[] desKey)
try
IvParameterSpec spec = new IvParameterSpec(desKey);
DESKeySpec dks = new DESKeySpec(desKey);
SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("DES");
SecretKey securekey = keyFactory.generateSecret(dks);

Cipher cipher = Cipher.getInstance("DES/CBC/PKCS5Padding");
cipher.init(Cipher.DECRYPT_MODE, securekey, spec);
//data = Base64.decode(data);

byte[] encryptContent = cipher.doFinal(data);
return encryptContent;
catch (Exception e)
e.printStackTrace();
return null;



解密时,异常信息如下所示:
javax.crypto.BadPaddingException: Given final block not properly padded
at com.sun.crypto.provider.SunJCE_h.b(DashoA12275)
at com.sun.crypto.provider.SunJCE_h.b(DashoA12275)
at com.sun.crypto.provider.DESCipher.engineDoFinal(DashoA12275)
at javax.crypto.Cipher.doFinal(DashoA12275)
at beans.DESUtil.decryptRes(DESUtil.java:39)
at beans.DESUtil.decryptCertKey(DESUtil.java:61)
at beans.PublicKeyList.getPublicKeyList(PublicKeyList.java:53)
at servlet.GetPublicKey.doGet(GetPublicKey.java:29)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:690)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:803)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter
……
请各位高手指点一下,应该怎么解决,不甚感激!

要实现在java端用PKCS7Padding填充,需要用到bouncycastle组件来实现,下面我会提供该包的下载。下面是一个简单的测试,上代码!

001    package com.encrypt.file;    

002    import java.io.UnsupportedEncodingException;    

003    importjava.security.Key;     

006    import java.security.Security;    

007         

008    importjavax.crypto.Cipher;     

009    importjavax.crypto.SecretKey;     

010    importjavax.crypto.spec.SecretKeySpec;     

011         

012    public classAES256Encryption     

013             

014             /**    

015             * 密钥算法    

016             * java6支持56位密钥,bouncycastle支持64位    

017             * */     

018            public static finalString KEY_ALGORITHM="AES";     

019                   

020            /**    

021             * 加密/解密算法/工作模式/填充方式    

022             *     

023             * JAVA6 支持PKCS5PADDING填充方式    

024             * Bouncy castle支持PKCS7Padding填充方式    

025             * */     

026            public static finalString CIPHER_ALGORITHM="AES/ECB/PKCS7Padding";     

027                   

028            /**    

029             *     

030             * 生成密钥,java6只支持56位密钥,bouncycastle支持64位密钥    

031             * @return byte[] 二进制密钥    

032             * */     

033            public static byte[] initkey() throwsException     

034                       

035    //          //实例化密钥生成器     

036    //          Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider());    

037    //          KeyGenerator kg=KeyGenerator.getInstance(KEY_ALGORITHM, "BC");     

038    //          //初始化密钥生成器,AES要求密钥长度为128位、192位、256位     

039    ////            kg.init(256);     

040    //          kg.init(128);    

041    //          //生成密钥     

042    //          SecretKey secretKey=kg.generateKey();     

043    //          //获取二进制密钥编码形式     

044    //          return secretKey.getEncoded();     

045                //为了便于测试,这里我把key写死了,如果大家需要自动生成,可用上面注释掉的代码    

046                return new byte[]  0x08, 0x08, 0x04, 0x0b, 0x02, 0x0f, 0x0b, 0x0c,    

047                        0x01, 0x03, 0x09, 0x07, 0x0c, 0x03, 0x07, 0x0a, 0x04, 0x0f,    

048                        0x06, 0x0f, 0x0e, 0x09, 0x05, 0x01, 0x0a, 0x0a, 0x01, 0x09,    

049                        0x06, 0x07, 0x09, 0x0d ;    

050                

051         

052            /**    

053             * 转换密钥    

054             * @param key 二进制密钥    

055             * @return Key 密钥    

056             * */     

057            public static Key toKey(byte[] key) throwsException     

058                //实例化DES密钥     

059                //生成密钥     

060                SecretKey secretKey=newSecretKeySpec(key,KEY_ALGORITHM);     

061                returnsecretKey;     

062                 

063                   

064            /**    

065             * 加密数据    

066             * @param data 待加密数据    

067             * @param key 密钥    

068             * @return byte[] 加密后的数据    

069             * */     

070            public static byte[] encrypt(byte[] data,byte[] key) throwsException     

071                //还原密钥     

072                Key k=toKey(key);     

073                /**    

074                 * 实例化    

075                 * 使用 PKCS7PADDING 填充方式,按如下方式实现,就是调用bouncycastle组件实现    

076                 * Cipher.getInstance(CIPHER_ALGORITHM,"BC")    

077                 */     

078                Security.addProvider(new org.bouncycastle.jce.provider.BouncyCastleProvider());    

079                Cipher cipher=Cipher.getInstance(CIPHER_ALGORITHM, "BC");     

080                //初始化,设置为加密模式     

081                cipher.init(Cipher.ENCRYPT_MODE, k);     

082                //执行操作     

083                returncipher.doFinal(data);     

084                 

085            /**    

086             * 解密数据    

087             * @param data 待解密数据    

088             * @param key 密钥    

089             * @return byte[] 解密后的数据    

090             * */     

091            public static byte[] decrypt(byte[] data,byte[] key) throwsException     

092                //欢迎密钥     

093                Key k =toKey(key);     

094                /**    

095                 * 实例化    

096                 * 使用 PKCS7PADDING 填充方式,按如下方式实现,就是调用bouncycastle组件实现    

097                 * Cipher.getInstance(CIPHER_ALGORITHM,"BC")    

098                 */     

099                Cipher cipher=Cipher.getInstance(CIPHER_ALGORITHM);     

100                //初始化,设置为解密模式    

101                cipher.init(Cipher.DECRYPT_MODE, k);     

102                //执行操作     

103                returncipher.doFinal(data);     

104                 

105            /**    

106             * @param args    

107             * @throws UnsupportedEncodingException    

108             * @throws Exception     

109             */     

110            public static void main(String[] args) throwsUnsupportedEncodingException     

111                     

112                String str="AES";     

113                System.out.println("原文:"+str);     

114         

115                //初始化密钥     

116                byte[] key;    

117                try     

118                    key = AES256Encryption.initkey();    

119                    System.out.print("密钥:");     

120                    for(int i = 0;i<key.length;i++)    

121                        System.out.printf("%x", key[i]);    

122                        

123                    System.out.print("\\n");    

124                    //加密数据     

125                    byte[] data=AES256Encryption.encrypt(str.getBytes(), key);     

126                    System.out.print("加密后:");    

127                    for(int i = 0;i<data.length;i++)    

128                        System.out.printf("%x", data[i]);    

129                        

130                    System.out.print("\\n");    

131                         

132                    //解密数据     

133                    data=AES256Encryption.decrypt(data, key);     

134                    System.out.println("解密后:"+newString(data));    

135                 catch (Exception e)    

136                    // TODO Auto-generated catch block    

137                    e.printStackTrace();    

138                     

139                      

140                 

141            

运行程序后的结果截图:

      

运行程序,这里需要自己创建一个简单的应用程序,简单的布局:


加密后的密文:


大家可以看到这里的密文和java端的密文是一致的,这样我们就成功完成了。只要密文和密钥是一致的,那么解密应该就不会有什么问题了后面如果有需要解密的可以自己调用解密的那个方法就可以了。

jce_policy-6.zip 下载链接:http://www.oracle.com/technetwork/java/javase/downloads/jce-6-download-429243.html

下载解压后将里边的两个jar包(local_policy.jar,US_export_policy.jar)替换掉jdk安装路径下security文件夹中的两个包。

Java是一种可以撰写跨平台应用软件的面向对象的程序设计语言。Java 技术具有卓越的通用性、高效性、平台移植性和安全性,广泛应用于PC、数据中心、游戏控制台、科学超级计算机、移动电话和互联网,同时拥有全球最大的开发者专业社群。

参考技术A 根据你提供的错误消息。
我认为出现这个问题可能是你的加密和解密使用的填充算法不一致导致的。
1、要确认下是否加密和解密都是使用相同的填充算法(也就是说,是否都是使用PKCS5Padding)
2、确认下你要解密的字节数组是否正确。本回答被提问者和网友采纳

以上是关于javax.crypto.BadPaddingException: Given final block not properly padded的主要内容,如果未能解决你的问题,请参考以下文章