日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

des 向量 java_在JAVA中使用DES算法

發布時間:2023/12/10 编程问答 24 豆豆
生活随笔 收集整理的這篇文章主要介紹了 des 向量 java_在JAVA中使用DES算法 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

DES算法提供CBC, OFB, CFB, ECB四種模式,MAC是基于ECB實現的。

一、數據補位

DES數據加解密就是將數據按照8個字節一段進行DES加密或解密得到一段8個字節的密文或者明文,最后一段不足8個字節,按照需求補足8個字節(通常補00或者FF,根據實際要求不同)進行計算,之后按照順序將計算所得的數據連在一起即可。

這里有個問題就是為什么要進行數據補位?主要原因是DES算法加解密時要求數據必須為8個字節。

二、ECB模式

DES?ECB(電子密本方式)其實非常簡單,就是將數據按照8個字節一段進行DES加密或解密得到一段8個字節的密文或者明文,最后一段不足8個字節,按照需求補足8個字節進行計算,之后按照順序將計算所得的數據連在一起即可,各段數據之間互不影響。

三、CBC模式

DES CBC(密文分組鏈接方式)有點麻煩,它的實現機制使加密的各段數據之間有了聯系。其實現的機理如下:

加密步驟如下:

1)首先將數據按照8個字節一組進行分組得到D1D2......Dn(若數據不是8的整數倍,用指定的PADDING數據補位)

2)第一組數據D1與初始化向量I異或后的結果進行DES加密得到第一組密文C1(初始化向量I為全零)

3)第二組數據D2與第一組的加密結果C1異或以后的結果進行DES加密,得到第二組密文C2

4)之后的數據以此類推,得到Cn

5)按順序連為C1C2C3......Cn即為加密結果。

解密是加密的逆過程,步驟如下:

1)首先將數據按照8個字節一組進行分組得到C1C2C3......Cn

2)將第一組數據進行解密后與初始化向量I進行異或得到第一組明文D1(注意:一定是先解密再異或)

3)將第二組數據C2進行解密后與第一組密文數據進行異或得到第二組數據D2

4)之后依此類推,得到Dn

5)按順序連為D1D2D3......Dn即為解密結果。

這里注意一點,解密的結果并不一定是我們原來的加密數據,可能還含有你補得位,一定要把補位去掉才是你的原來的數據。

*** DES算法*/public class DES {?? /**?? *?? * @return DES算法密鑰?? */?? public static byte[] generateKey() {?? ???? try {?? ???? ??? // DES算法要求有一個可信任的隨機數源?? ???? ??? SecureRandom sr = new SecureRandom();?? ???? ??? // 生成一個DES算法的KeyGenerator對象?? ???? ??? KeyGenerator kg = KeyGenerator.getInstance("DES");?? ???? ??? kg.init(sr);?? ???? ??? // 生成密鑰?? ???? ??? SecretKey secretKey = kg.generateKey();?? ???? ??? // 獲取密鑰數據?? ???? ??? byte[] key = secretKey.getEncoded();?? ???? ??? return key;?? ???? } catch (NoSuchAlgorithmException e) {?? ???? ??? System.err.println("DES算法,生成密鑰出錯!");?? ???? ??? e.printStackTrace();?? ???? }?? ???? return null;?? }?? /**?? * 加密函數?? *?? * @param data?? *??????????? 加密數據?? * @param key?? *??????????? 密鑰?? * @return 返回加密后的數據?? */?? public static byte[] encrypt(byte[] data, byte[] key) {?? ???? try {?? ???? ??? // DES算法要求有一個可信任的隨機數源?? ???? ??? SecureRandom sr = new SecureRandom();?? ???? ??? // 從原始密鑰數據創建DESKeySpec對象?? ???? ??? DESKeySpec dks = new DESKeySpec(key);?? ???? ??? // 創建一個密匙工廠,然后用它把DESKeySpec轉換成?? ???? ??? // 一個SecretKey對象?? ???? ??? SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("DES");?? ???? ??? SecretKey secretKey = keyFactory.generateSecret(dks);?? ???? ??? // using DES in ECB mode?? ???? ??? Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding");?? ???? ??? // 用密匙初始化Cipher對象?? ???? ??? cipher.init(Cipher.ENCRYPT_MODE, secretKey, sr);?? ???? ??? // 執行加密操作?? ???? ??? byte encryptedData[] = cipher.doFinal(data);?? ???? ??? return encryptedData;?? ???? } catch (Exception e) {?? ???? ??? System.err.println("DES算法,加密數據出錯!");?? ???? ??? e.printStackTrace();?? ???? }?? ???? return null;?? }?? /**?? * 解密函數?? *?? * @param data?? *??????????? 解密數據?? * @param key?? *??????????? 密鑰?? * @return 返回解密后的數據?? */?? public static byte[] decrypt(byte[] data, byte[] key) {?? ???? try {?? ???? ??? // DES算法要求有一個可信任的隨機數源?? ???? ??? SecureRandom sr = new SecureRandom();?? ???? ??? // byte rawKeyData[] = /* 用某種方法獲取原始密匙數據 */;?? ???? ??? // 從原始密匙數據創建一個DESKeySpec對象?? ???? ??? DESKeySpec dks = new DESKeySpec(key);?? ???? ??? // 創建一個密匙工廠,然后用它把DESKeySpec對象轉換成?? ???? ??? // 一個SecretKey對象?? ???? ??? SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("DES");?? ???? ??? SecretKey secretKey = keyFactory.generateSecret(dks);?? ???? ??? // using DES in ECB mode?? ???? ??? Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding");?? ???? ??? // 用密匙初始化Cipher對象?? ???? ??? cipher.init(Cipher.DECRYPT_MODE, secretKey, sr);?? ???? ??? // 正式執行解密操作?? ???? ??? byte decryptedData[] = cipher.doFinal(data);?? ???? ??? return decryptedData;?? ???? } catch (Exception e) {?? ???? ??? System.err.println("DES算法,解密出錯。");?? ???? ??? e.printStackTrace();?? ???? }?? ???? return null;?? }?? /**?? * 加密函數?? *?? * @param data?? *??????????? 加密數據?? * @param key?? *??????????? 密鑰?? * @return 返回加密后的數據?? */?? public static byte[] CBCEncrypt(byte[] data, byte[] key, byte[] iv) {?? ???? try {?? ???? ??? // 從原始密鑰數據創建DESKeySpec對象?? ???? ??? DESKeySpec dks = new DESKeySpec(key);?? ???? ??? // 創建一個密匙工廠,然后用它把DESKeySpec轉換成?? ???? ??? // 一個SecretKey對象?? ???? ??? SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("DES");?? ???? ??? SecretKey secretKey = keyFactory.generateSecret(dks);?? ???? ??? // Cipher對象實際完成加密操作?? ???? ??? Cipher cipher = Cipher.getInstance("DES/CBC/PKCS5Padding");?? ???? ??? // 若采用NoPadding模式,data長度必須是8的倍數?? ???? ??? // Cipher cipher = Cipher.getInstance("DES/CBC/NoPadding");?? ???? ??? // 用密匙初始化Cipher對象?? ???? ??? IvParameterSpec param = new IvParameterSpec(iv);?? ???? ??? cipher.init(Cipher.ENCRYPT_MODE, secretKey, param);?? ???? ??? // 執行加密操作?? ???? ??? byte encryptedData[] = cipher.doFinal(data);?? ???? ??? return encryptedData;?? ???? } catch (Exception e) {?? ???? ??? System.err.println("DES算法,加密數據出錯!");?? ???? ??? e.printStackTrace();?? ???? }?? ???? return null;?? }?? /**?? * 解密函數?? *?? * @param data?? *??????????? 解密數據?? * @param key?? *??????????? 密鑰?? * @return 返回解密后的數據?? */?? public static byte[] CBCDecrypt(byte[] data, byte[] key, byte[] iv) {?? ???? try {?? ???? ??? // 從原始密匙數據創建一個DESKeySpec對象?? ???? ??? DESKeySpec dks = new DESKeySpec(key);?? ???? ??? // 創建一個密匙工廠,然后用它把DESKeySpec對象轉換成?? ???? ??? // 一個SecretKey對象?? ???? ??? SecretKeyFactory keyFactory = SecretKeyFactory.getInstance("DES");?? ???? ??? SecretKey secretKey = keyFactory.generateSecret(dks);?? ???? ??? // using DES in CBC mode?? ???? ??? Cipher cipher = Cipher.getInstance("DES/CBC/PKCS5Padding");?? ???? ??? // 若采用NoPadding模式,data長度必須是8的倍數?? ???? ??? // Cipher cipher = Cipher.getInstance("DES/CBC/NoPadding");?? ???? ??? // 用密匙初始化Cipher對象?? ???? ??? IvParameterSpec param = new IvParameterSpec(iv);?? ???? ??? cipher.init(Cipher.DECRYPT_MODE, secretKey, param);?? ???? ??? // 正式執行解密操作?? ???? ??? byte decryptedData[] = cipher.doFinal(data);?? ???? ??? return decryptedData;?? ???? } catch (Exception e) {?? ???? ??? System.err.println("DES算法,解密出錯。");?? ???? ??? e.printStackTrace();?? ???? }?? ???? return null;?? }?? public static void main(String[] args) {?? ???? try {?? ???? ??? byte[] key = "11111111".getBytes();?? ???? ??? byte[] iv = "22222222".getBytes();?? ???? ??? byte[] data = DES.encrypt("ebc mode test".getBytes(), key);?? ???? ??? System.out.print("EBC mode:");?? ???? ??? System.out.println(new String(DES.decrypt(data, key)));?? ???? ??? System.out.print("CBC mode:");?? ???? ??? data = DES.CBCEncrypt("cbc mode test".getBytes(), key, iv);?? ???? ??? System.out.println(new String(DES.CBCDecrypt(data, key, iv)));?? ???? ?????? ???? } catch (Exception e) {?? ???? ??? e.printStackTrace();?? ???? }?? }}

DES的幾種填補方式

DES是對64位數據的加密算法,如數據位數不足64位的倍數,需要填充,補充到64位的倍數。

NoPadding

API或算法本身不對數據進行處理,加密數據由加密雙方約定填補算法。例如若對字符串數據進行加解密,可以補充\0或者空格,然后trim

PKCS5Padding

加密前:數據字節長度對8取余,余數為m,若m>0,則補足8-m個字節,字節數值為8-m,即差幾個字節就補幾個字節,字節數值即為補充的字節數,若為0則補充8個字節的8

解密后:取最后一個字節,值為m,則從數據尾部刪除m個字節,剩余數據即為加密前的原文

因為DES是一種block cipher,一個block要8個字節,所以要加密的東西要分成8字節的整數倍,不足的就填充。

PKCS5Padding這種填充,填的字節代表所填字節的總數:

比如差三個字節的話填為 @@@@@333

差7個字節就填為 @7777777

沒有差就填 88888888

總結

以上是生活随笔為你收集整理的des 向量 java_在JAVA中使用DES算法的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。