DES算法Java实现源代码

合集下载

DES加密算法javac#

DES加密算法javac#

DES加密算法javac#项⽬中⽤到的数据加密⽅式是ECB模式的DES加密得到的⼗六进制字符串。

技术⽀持让写⼀个.net版的加密算法。

这⾥做⼀下记录。

java版:16进制使⽤的是bouncycastle。

import com.emaxcard.codec.CodecException;import com.emaxcard.codec.Hex;import sun.misc.BASE64Encoder;import javax.crypto.Cipher;import javax.crypto.SecretKey;import javax.crypto.spec.SecretKeySpec;public class DESEncrypt {public static String encodeECB(String src, String key) throws CodecException {try {SecretKey deskey = new SecretKeySpec(key.getBytes("UTF-8"), "DESede");Cipher cipher = Cipher.getInstance("DESede/ECB/PKCS5Padding");cipher.init(Cipher.ENCRYPT_MODE, deskey);byte[] cipherInfo = cipher.doFinal(src.getBytes("UTF-8"));System.out.println("cipherInfo:"+new BASE64Encoder().encode(cipherInfo));return Hex.encode(cipherInfo);} catch (Exception var5) {throw new CodecException(var5);}}public static String decodeECB(String src, String key) throws CodecException {try {SecretKey deskey = new SecretKeySpec(key.getBytes("UTF-8"), "DESede");Cipher cipher = Cipher.getInstance("DESede/ECB/PKCS5Padding");cipher.init(Cipher.DECRYPT_MODE, deskey);byte[] decodeRes = cipher.doFinal(Hex.decode(src));return new String(decodeRes, "UTF-8");} catch (Exception var5) {throw new CodecException(var5);}}}public class Hex {public Hex() {}public static byte[] decode(String data) throws CodecException {try {return org.bouncycastle.util.encoders.Hex.decode(data);} catch (Exception var2) {throw new CodecException(var2.getMessage(), var2);}}public static String encode(byte[] data) {return new String(org.bouncycastle.util.encoders.Hex.encode(data));}public static void main(String[] args) throws CodecException {System.out.println(encode("a张y".getBytes()));System.out.println(new String(decode("")));}}.net(c#)版:using System;using System.IO;using System.Security.Cryptography;using System.Text;namespace ConsoleApplication1{class DESEncrypt{public static string encodeECB(string encryptString, String key){byte[] keyBytes = Encoding.UTF8.GetBytes(key.Substring(0, 8));byte[] keyIV = keyBytes;byte[] inputByteArray = Encoding.UTF8.GetBytes(encryptString);DESCryptoServiceProvider provider = new DESCryptoServiceProvider();provider.Mode = CipherMode.ECB;provider.Padding = PaddingMode.PKCS7;MemoryStream mStream = new MemoryStream();CryptoStream cStream = new CryptoStream(mStream, provider.CreateEncryptor(keyBytes, keyIV), CryptoStreamMode.Write); cStream.Write(inputByteArray, 0, inputByteArray.Length);cStream.FlushFinalBlock();//return Convert.ToBase64String(mStream.ToArray());return Hex.encode(mStream.ToArray());}public static string DesDecrypt(string decryptString, String key){byte[] keyBytes = Encoding.UTF8.GetBytes(key.Substring(0, 8));byte[] keyIV = keyBytes;//byte[] inputByteArray = Convert.FromBase64String(decryptString);byte[] inputByteArray = Hex.decode(decryptString);DESCryptoServiceProvider provider = new DESCryptoServiceProvider();provider.Mode = CipherMode.ECB;provider.Padding = PaddingMode.PKCS7;MemoryStream mStream = new MemoryStream();CryptoStream cStream = new CryptoStream(mStream, provider.CreateDecryptor(keyBytes, keyIV), CryptoStreamMode.Write); cStream.Write(inputByteArray, 0, inputByteArray.Length);cStream.FlushFinalBlock();return Encoding.UTF8.GetString(mStream.ToArray());}}}using System;using System.Globalization;using System.Text;namespace ConsoleApplication1{sealed class Hex{public static byte[] decode(String mHex){mHex = mHex.Replace("", "");if (mHex.Length <= 0) return null;byte[] vBytes = new byte[mHex.Length / 2];for (int i = 0; i < mHex.Length; i += 2)if (!byte.TryParse(mHex.Substring(i, 2), NumberStyles.HexNumber, null, out vBytes[i / 2]))vBytes[i / 2] = 0;return vBytes;}public static String encode(byte[] data){//** 以下两种⽅式都可以//⽅式1StringBuilder hexString = new StringBuilder();for (int i = 0; i < data.Length; i++){hexString.AppendFormat("{0:x2}", data[i]); //System.Convert.ToString(data[i], 16);}return hexString.ToString();//⽅式2//return BitConverter.ToString(data).Replace("-", "").ToLower();}}}BitConverter.ToString⽅法签名://// 摘要:// 将指定的字节数组的每个元素的数值转换为它的等效⼗六进制字符串表⽰形式。

DES加密和解密java代码

DES加密和解密java代码

DES加密和解密java代码在说DES加密算法之前,我们⾸先了解⼏个基本概念:1. 明⽂:明⽂是指没有经过加密的数据。

⼀般⽽⾔,明⽂都是等待传输的数据。

由于没有经过加密,明⽂很容易被识别与破解,因此在传输明⽂之前必须进⾏加密处理。

2. 密⽂:密⽂只是明⽂经过某种加密算法⽽得到的数据,通常密⽂的形式复杂难以识别及理解。

3. 密钥:密钥是⼀种参数,它是在明⽂转换为密⽂或将密⽂转换为明⽂的算法中输⼊的参数。

4. 对称加密:通信双⽅同时掌握⼀个密钥,加密解密都是由⼀个密钥完成的(即加密密钥等于解密密钥,加解密密钥可以相互推倒出来)。

双⽅通信前共同拟定⼀个密钥,不对第三⽅公开。

5. 分组加密:分组密码是将明⽂分成固定长度的组,每⼀组都采⽤同⼀密钥和算法进⾏加密,输出也是固定长度的密⽂。

好了了解这些以后,我们再来说DES加密算法。

DES 算法是⼀种常见的分组加密算法,由IBM公司在1971年提出。

DES 算法是分组加密算法的典型代表,同时也是应⽤最为⼴泛的对称加密算法。

下⾯我们详细介绍下:1.分组长度:DES 加密算法中,明⽂和密⽂为 64 位分组。

密钥的长度为 64 位,但是密钥的每个第⼋位设置为奇偶校验位,因此密钥的实际长度为56位。

2.加密流程:DES 加密算法⼤致分为 4 步:初始置换、⽣成⼦密钥、迭代过程、逆置换。

代码如下:需特别注意:不要使⽤JDK中⾃带的sun.misc.BASE64Decoder类去做BASE64,该类会在最后⾯多加换⾏。

⽽应使⽤apache中的mons.codec.binary.Base64这个类来做base64加密。

(待验证)import javax.crypto.Cipher;import javax.crypto.SecretKeyFactory;import javax.crypto.spec.DESKeySpec;import javax.crypto.spec.IvParameterSpec;import java.security.Key;import java.security.SecureRandom;import mons.codec.binary.Base64;public class DESUtil {// 偏移变量,固定占8位字节private final static String IV_PARAMETER = "12345678";// 字符编码public static final String CHARSET_UTF8 = "UTF-8";// 加密算法DESpublic static final String DES = "DES";// 电话本模式public static final String DES_ECB = "DES/ECB/PKCS5Padding";// 加密块链模式--推荐public static final String DES_CBC = "DES/CBC/PKCS5Padding";// 测试public static void main(String args[]) {// 待加密内容String str = "false";// 密码,长度要是8的倍数String password = "87654321";String result = DESUtil.encryptCBC(password, str);System.out.println("加密后:" + new String(result));// 直接将如上内容解密try {String decryResult = DESUtil.decryptCBC(password, result);System.out.println("解密后:" + new String(decryResult));} catch (Exception e1) {e1.printStackTrace();}}/*** ⽣成key** @param password* @return* @throws Exception*/private static Key generateKey(String password) throws Exception {DESKeySpec dks = new DESKeySpec(password.getBytes(CHARSET_UTF8));SecretKeyFactory keyFactory = SecretKeyFactory.getInstance(DES);return keyFactory.generateSecret(dks);}/*** DES加密字符串--ECB格式** @param password* 加密密码,长度不能够⼩于8位* @param data* 待加密字符串* @return加密后内容*/public static String encryptECB(String password, String data) {if (password == null || password.length() < 8) {throw new RuntimeException("加密失败,key不能⼩于8位");}if (data == null) {return null;}try {Key secretKey = generateKey(password);Cipher cipher = Cipher.getInstance(DES_ECB);cipher.init(Cipher.ENCRYPT_MODE, secretKey, new SecureRandom());byte[] bytes = cipher.doFinal(data.getBytes(CHARSET_UTF8));// JDK1.8及以上可直接使⽤Base64,JDK1.7及以下可以使⽤BASE64Encoder return new String(Base64.encodeBase64(bytes));} catch (Exception e) {e.printStackTrace();return data;}}/*** DES解密字符串--ECB格式** @param password* 解密密码,长度不能够⼩于8位* @param data* 待解密字符串* @return解密后内容*/public static String decryptECB(String password, String data)throws Exception {Key secretKey = generateKey(password);Cipher cipher = Cipher.getInstance(DES_ECB);cipher.init(Cipher.DECRYPT_MODE, secretKey, new SecureRandom());return new String(cipher.doFinal(Base64.decodeBase64(data.getBytes(CHARSET_UTF8))), CHARSET_UTF8);}/*** DES加密字符串-CBC加密格式** @param password* 加密密码,长度不能够⼩于8位* @param data* 待加密字符串* @return加密后内容*/public static String encryptCBC(String password, String data) {if (password == null || password.length() < 8) {throw new RuntimeException("加密失败,key不能⼩于8位");}if (data == null) {return null;}try {Key secretKey = generateKey(password);Cipher cipher = Cipher.getInstance(DES_CBC);IvParameterSpec spec = new IvParameterSpec(IV_PARAMETER.getBytes(CHARSET_UTF8));cipher.init(Cipher.ENCRYPT_MODE, secretKey, spec);byte[] bytes = cipher.doFinal(data.getBytes(CHARSET_UTF8));// JDK1.8及以上可直接使⽤Base64,JDK1.7及以下可以使⽤BASE64Encoder return new String(Base64.encodeBase64(bytes));} catch (Exception e) {e.printStackTrace();return data;}}/*** DES解密字符串--CBC格式** @param password* 解密密码,长度不能够⼩于8位* @param data* 待解密字符串* @return解密后内容*/public static String decryptCBC(String password, String data) throws Exception {Key secretKey = generateKey(password);Cipher cipher = Cipher.getInstance(DES_CBC);IvParameterSpec spec = new IvParameterSpec(IV_PARAMETER.getBytes(CHARSET_UTF8));cipher.init(Cipher.DECRYPT_MODE, secretKey, spec);return new String(cipher.doFinal(Base64.decodeBase64(data.getBytes(CHARSET_UTF8))), CHARSET_UTF8); }}。

DES算法源代码-JAVA

DES算法源代码-JAVA

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加密,得到第二组密文C24)之后的数据以此类推,得到Cn5)按顺序连为即为加密结果。

解密是加密的逆过程,步骤如下:)首先将数据按照8个字节一组进行分组得到2)将第一组数据进行解密后与初始化向量I进行异或得到第一组明文D1(注意:一定是先解密再异或)3)将第二组数据C2进行解密后与第一组密文数据进行异或得到第二组数据D24)之后依此类推,得到Dn5)按顺序连为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 modeCipher 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 modeCipher 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算法,解密出错。

DES加密解密Java代码

DES加密解密Java代码
mainMenu.add(generateItem);
mainMenu.addSeparator();
mainMenu.add(encryptItem);
mainMenu.add(decryptItem);
menuBar.add(mainMenu);
setJMenuBar(menuBar);
//添加文本区
if (fileName == null)
return;
//读取密文
FileInputStream fis = new FileInputStream(fileName);
byte[] cipherText = new byte[fis.available()];
fis.read(cipherText);
jfc.setDialogTitle("打开加密文本内容");
if (jfc.showOpenDialog(this) == JFileChooser.APPROVE_OPTION) {
fileName = jfc.getSelectedFile().getPath();
}
//如果没有选择文件,就退出
e1.printStackTrace();
}
} else if (e.getSource() == decryptItem) {
try {
//读取密钥文件的完整路径
String fileName = null;
//设置文件选择对话框
JFileChooser jfc = new JFileChooser();
add(jsp);
//添加事件监听
generateItem.addActionListener(this);

DES可逆加密算法JAVA源代码

DES可逆加密算法JAVA源代码

DES可逆加密算法JAVA源代码下面是一个实现DES可逆加密算法的Java源代码。

该代码共1281个字符(字母、符号、数字)。

```javaimport javax.crypto.Cipher;import javax.crypto.SecretKey;import javax.crypto.SecretKeyFactory;import javax.crypto.spec.DESKeySpec;import java.nio.charset.StandardCharsets;import java.util.Base64;public class DESprivate static final String key = "mysecret"; // 设置密钥public static void main(String[] args)String plainText = "Hello, World!"; // 要进行加密的明文String encryptedText = encrypt(plainText);System.out.println("Encrypted text: " + encryptedText);String decryptedText = decrypt(encryptedText);System.out.println("Decrypted text: " + decryptedText);}public static String encrypt(String plainText)tryDESKeySpec desKeySpec = newDESKeySpec(key.getBytes(StandardCharsets.UTF_8));SecretKeyFactory keyFactory =SecretKeyFactory.getInstance("DES");SecretKey secretKey = keyFactory.generateSecret(desKeySpec);Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding");cipher.init(Cipher.ENCRYPT_MODE, secretKey);byte[] encryptedBytes =cipher.doFinal(plainText.getBytes(StandardCharsets.UTF_8));return Base64.getEncoder(.encodeToString(encryptedBytes);} catch (Exception e)e.printStackTrace(;}return null;}public static String decrypt(String encryptedText)tryDESKeySpec desKeySpec = newDESKeySpec(key.getBytes(StandardCharsets.UTF_8));SecretKeyFactory keyFactory =SecretKeyFactory.getInstance("DES");SecretKey secretKey = keyFactory.generateSecret(desKeySpec);Cipher cipher = Cipher.getInstance("DES/ECB/PKCS5Padding");cipher.init(Cipher.DECRYPT_MODE, secretKey);byte[] decryptedBytes =cipher.doFinal(Base64.getDecoder(.decode(encryptedText));return new String(decryptedBytes, StandardCharsets.UTF_8);} catch (Exception e)e.printStackTrace(;}return null;}```该代码使用DES算法进行加密和解密,使用密钥"mysecret"对数据进行处理。

DES加密算法及其在Java中的实现

DES加密算法及其在Java中的实现
DES用56位密钥对64位的明文数据块进行加密 ,每次加密 可 以 对 64位 的 明 文 数 据 进 行 16轮 编 码 ,经 过 一 系 列 替 换 和 移 位 后,输出完全不同的64位密纹数据。 DES入口参数有3个:Key、 Data、Mode,其中Key为7个 字 节 共56位 (另 有8位 作 为 奇 偶 校 验 位,这样保证了明文与密钥长度的一致性 ),是DES算法的工作 密钥;Data为8位字节64位, 是要被加密或解密的数据;Mode为 DES的工作方式,由两种:加密、解密。 由于DES算法使用64位的 标准算法和逻辑运算、运算速度快、密钥产生容易,因此适合当 前大多数计算机上用软件方法实现, 同时也适用于专用芯片 上。
利 用 DES算 法 加 密 的 步 骤 如 下 : (1)生成一个安全密钥。 在加密或解密任何数据之前需要 有一个密钥。密钥是随同被加密的应用程序一起发布的一段数 据,密钥代码如下所示。 // 生成一个可信任的随机数源 Secure Random sr=new SecureRandom(); // 为我们选择的DES算法生成一个KeyGenerator对象 KeyGenerator kg=KeyGenerator.getInstance ("DES"); Kg.init(sr); // 生成密钥 Secret Key key=kg.generateKey(); // 将密钥数据保存为文件供以后使用, 其中key Filename 为保存的文件名 Util.writeFile (key Filename, key.getEncoded()); (2)加密数据 。 得到密钥之后 ,接 下 来 就 可以 用 它 加 密 数 据。 密钥加密原始数据如下所示。 // 产生一个可信任的随机数源 SecureRandom sr=new SecureRandom(); //从密钥文件key Filename中得到密钥数据 Byte rawKeyData[]=Util.readFile(key Filename); // 从原始密钥数据创建DESKeySpec对象 DESKeySpec dks=new DESKeySpec(rawKeyData); // 创建一个密钥工厂,然后用它把DESKeySpec转 换成Secret Key对象 SecretKeyFactory key Factory = SecretKeyFactory.getInstance ("DES"); Secret Key key=keyFactory.generateSecret(dks); // Cipher对象实际完成加密操作 Cipher cipher=Cipher.getInstance("DES"); // 用密钥初始化Cipher对象 cipher.init(Cipher.ENCRYPT_MODE,key,sr); // 通过读类文件获取需要加密的数据 Byte data []=Util.readFile(filename); // 执行加密操作

DES加密算法的JAVA实现

DES加密算法的JAVA实现

目录摘要 (3)一、目的与意义 (4)二、DES概述 (5)三、DES加解密算法原理 (7)1.加密 (6)2.子密钥生成 (11)3.解密 (13)四、加解密算法的实现 (14)1.软件版本 (14)2.平台 (14)3.源代码 (14)4.运行结果 (24)五、总结 (25)【摘要】1973年5月15 日,美国国家标准局(现在的美国国家标准就是研究所,即NIST)在联邦记录中公开征集密码体制,这一举措最终导致了数据加密标准(DES)的出现,它曾经成为世界上最广泛使用的密码体制。

DES由IBM开发,它是早期被称为Lucifer体制的改进。

DES在1975年3月17日首次在联邦记录中公布,在经过大量的公开讨论后,1977年2月15日DES被采纳为“非密级”应用的一个标准。

最初预期DES作为标准只能使用10~15年;然而,事实证明DES要长寿得多。

被采纳后,大约每隔5年就被评审一次。

DES的最后一次评审是在1999年1月。

本文阐述了DES发展现状及对网络安全的重要意义,并在此基础上对DES算法原理进行详细的介绍和分析。

通过应用DES算法加解密的具体实现,进一步加深对DES算法的理解,论证了DES算法具有加密快速且强壮的优点,适合对含有大量信息的文件进行加密,同时分析了DES算法密钥过短(56位)所带来的安全隐患。

【关键词】DES 加密解密明文密文一、目的与意义随着计算机和通信网络的广泛应用,信息的安全性已经受到人们的普遍重视。

信息安全已不仅仅局限于政治,军事以及外交领域,而且现在也与人们的日常生活息息相关。

现在,密码学理论和技术已得到了迅速的发展,它是信息科学和技术中的一个重要研究领域。

在近代密码学上值得一提的大事有两件:一是1977年美国国家标准局正式公布实施了美国的数据加密标准(DES),公开它的加密算法,并批准用于非机密单位及商业上的保密通信。

密码学的神秘面纱从此被揭开。

二是Diffie和Hellman联合写的一篇文章“密码学的新方向”,提出了适应网络上保密通信的公钥密码思想,拉开了公钥密码研究的序幕。

DES算法实现

DES算法实现

DES算法实现:java语言下可以导入org.apache前缀的类库,apache组织给出了org.apache.codec类库,将基本的加密和解密方法打包成现成方法,并且提供了DES算法必备的S盒。

所以这个实现方法会采用org.apache.codec类库,采用结合源代码的方式进行编写。

工程名为ZDESAl即DES Algorithm,下面包含两个类,DESCoder负责生成密钥,DESCoderTest负责进行密钥的左移、置换选择,扩充等操作。

下面给出DESCoder类的设计思路和源代码:import java.security.Key;import javax.crypto.Cipher;import javax.crypto.KeyGenerator;import javax.crypto.SecretKey;import javax.crypto.SecretKeyFactory;import javax.crypto.spec.DESKeySpec;/***DES安全编码组件*@author Hawke7*@version 1.0*/public abstract class DESCoder {/***密钥算法<br>*Java6只支持56位密钥<br>*Bouncy Castle支持64位密钥*/public static final String KEY_ALGORITHM = "DES";/***加密/解密算法/工作模式/填充方式*/public static final String CIPHER_ALGORITHM= "DES/ECB/PKCS5Padding";/***转换密钥*@param key二进制密钥*@return key二进制密钥*@throws Exception*/private static Key toKey(byte[] key) throws Exception {// 实例化DES密钥材料DESKeySpec dks = new DESKeySpec(key);// 实例化秘密密钥工厂SecretKeyFactory keyFactory =SecretKeyFactory.getInstance(KEY_ALGORITHM);// 生成私密密钥SecretKey secretKey = keyFactory.generateSecret(dks);return secretKey;}/***解密*@param data待解密数据*@param key密钥*@return byte[]解密数据*@throws Exception*/public static byte[] decrypt(byte[] data, byte[] key) throws Exception {// 还原密钥Key k = toKey(key);// 实例化Cipher cipher = Cipher.getInstance(CIPHER_ALGORITHM);// 初始化,设置为解密模式cipher.init(Cipher.DECRYPT_MODE, k);// 执行操作return cipher.doFinal(data);}/***加密*@param data待加密数据*@param key密钥*@return byte[]加密数据*@throws Exception*/public static byte[] encrypt(byte[] data, byte[] key) throws Exception {// 还原密钥Key k = toKey(key);// 实例化Cipher cipher = Cipher.getInstance(CIPHER_ALGORITHM);// 初始化,设置为解密模式cipher.init(Cipher.ENCRYPT_MODE, k);// 执行操作return cipher.doFinal(data);}/***生成密钥<br>*Java6只支持56位密钥<br>*Bouncy Castle支持64位密钥<br>*@return byte[]二进制密钥*@throws Exception*/public static byte[] initKey() throws Exception {/** 实例化密钥生成器* 若要使用64位密钥注意替换* 将下述代码中的* KeyGenerator.getInstance(CIPHER_ALGORITHM);* 替换为* KeyGenerator.getInstance(CIPHER_ALGORITHM, "BC");*/KeyGenerator kg = KeyGenerator.getInstance(KEY_ALGORITHM);/** 初始化密钥生成器* 若要使用64位密钥注意替换* 将下面代码kg.init(56)* 替换为kg.init(64)*/kg.init(56);// 生成私密密钥SecretKey secretKey = kg.generateKey();// 获得密钥的二进制编码形式return secretKey.getEncoded();}}首先DESCoder要定义成抽象类,因为其中全部是static静态方法toKey,toKey初始化密钥材料,并且实例化密钥工厂,因为DES算法要进行16轮迭代,所以工厂每一次都要给出不同的密钥,从而增强雪崩效应。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

package des;/*** 加密过程:* 1.初始置换IP:将明文顺序打乱重新排列,置换输出为64位。

* 2.将置换输出的64位明文分成左右凉拌,左一半为L0,右一半称为R0,各32位。

* 3。

计算函数的16轮迭代。

* a)第一轮加密迭代:左半边输入L0,右半边输入R0:由轮函数f实现子密钥K1对R0的加密,*结果为32位数据组f(R0,K1),*b)第二轮加密迭代:左半边输入L1=R0,右半边输入R1=L0⊕f(R0,K1),由轮函数f实现子密钥* K2对R1的加密,结果为32位数据组f(R1,K2),f(R1,K2)与L1模2相加,得到一个32为数据组L1⊕f(R1,K2).* c)第3到16轮迭代分别用密钥K3,K4……K16进行。

4.再经过逆初始置换IP-1,将数据打乱重排,生成64位密文。

** 子密钥生成过程:* 1.将64位的密钥经过PC-1置换生成56位密钥。

* 2.将56位的密钥分成左右两部分,分别进行移位操作(一共进行16轮),产生16个56位长度的子密钥。

* 3.将16个56位的子密钥分别进行PC-2置换生成16个48位的子密钥。

** 轮函数f的工作过程:* 1.在第i次加密迭代过程中,扩展置换E对32位的Ri-1的各位通过置换表置换为48位的输出。

* 2.将该48位的输出与子密钥Ki进行异或操作,运算结果经过S盒代换运算,得到一个32位比特的输出。

* 3。

该32位比特输出再经过P置换表进行P运算,将其各位打乱重排,生成32位的输出。

** @author Ouyang**/public class Des {int[] byteKey;public Des(int[] byteKey) {this.byteKey = byteKey;}private static final int[] IP = { 58, 50, 42, 34, 26, 18, 10, 2, 60, 52,44, 36, 28, 20, 12, 4, 62, 54, 46, 38, 30, 22, 14, 6, 64, 56, 48,40, 32, 24, 16, 8, 57, 49, 41, 33, 25, 17, 9, 1, 59, 51, 43, 35,27, 19, 11, 3, 61, 53, 45, 37, 29, 21, 13, 5, 63, 55, 47, 39, 31,23, 15, 7 }; // 64private static final int[] IP_1 = { 40, 8, 48, 16, 56, 24, 64, 32, 39, 7,47, 15, 55, 23, 63, 31, 38, 6, 46, 14, 54, 22, 62, 30, 37, 5, 45,13, 53, 21, 61, 29, 36, 4, 44, 12, 52, 20, 60, 28, 35, 3, 43, 11,51, 19, 59, 27, 34, 2, 42, 10, 50, 18, 58, 26, 33, 1, 41, 9, 49,17, 57, 25 }; // 64private static final int[] PC_1 = { 57, 49, 41, 33, 25, 17, 9, 1, 58, 50,42, 34, 26, 18, 10, 2, 59, 51, 43, 35, 27, 19, 11, 3, 60, 52, 44,36, 63, 55, 47, 39, 31, 23, 15, 7, 62, 54, 46, 38, 30, 22, 14, 6,61, 53, 45, 37, 29, 21, 13, 5, 28, 20, 12, 4 }; // 56private static final int[] PC_2 = { 14, 17, 11, 24, 1, 5, 3, 28, 15, 6, 21,10, 23, 19, 12, 4, 26, 8, 16, 7, 27, 20, 13, 2, 41, 52, 31, 37, 47,55, 30, 40, 51, 45, 33, 48, 44, 49, 39, 56, 34, 53, 46, 42, 50, 36,29, 32 }; // 48private static final int[] E = { 32, 1, 2, 3, 4, 5, 4, 5, 6, 7, 8, 9, 8, 9,10, 11, 12, 13, 12, 13, 14, 15, 16, 17, 16, 17, 18, 19, 20, 21, 20,21, 22, 23, 24, 25, 24, 25, 26, 27, 28, 29, 28, 29, 30, 31, 32, 1 }; // 48 private static final int[] P = { 16, 7, 20, 21, 29, 12, 28, 17, 1, 15, 23,26, 5, 18, 31, 10, 2, 8, 24, 14, 32, 27, 3, 9, 19, 13, 30, 6, 22,11, 4, 25 }; // 32private static final int[][][] S_Box = {// S-盒{// S_Box[1]{ 14, 4, 13, 1, 2, 15, 11, 8, 3, 10, 6, 12, 5, 9, 0, 7 },{ 0, 15, 7, 4, 14, 2, 13, 1, 10, 6, 12, 11, 9, 5, 3, 8 },{ 4, 1, 14, 8, 13, 6, 2, 11, 15, 12, 9, 7, 3, 10, 5, 0 },{ 15, 12, 8, 2, 4, 9, 1, 7, 5, 11, 3, 14, 10, 0, 6, 13 } }, { // S_Box[2]{ 15, 1, 8, 14, 6, 11, 3, 4, 9, 7, 2, 13, 12, 0, 5, 10 },{ 3, 13, 4, 7, 15, 2, 8, 14, 12, 0, 1, 10, 6, 9, 11, 5 },{ 0, 14, 7, 11, 10, 4, 13, 1, 5, 8, 12, 6, 9, 3, 2, 15 },{ 13, 8, 10, 1, 3, 15, 4, 2, 11, 6, 7, 12, 0, 5, 14, 9 } }, { // S_Box[3]{ 10, 0, 9, 14, 6, 3, 15, 5, 1, 13, 12, 7, 11, 4, 2, 8 },{ 13, 7, 0, 9, 3, 4, 6, 10, 2, 8, 5, 14, 12, 11, 15, 1 },{ 13, 6, 4, 9, 8, 15, 3, 0, 11, 1, 2, 12, 5, 10, 14, 7 },{ 1, 10, 13, 0, 6, 9, 8, 7, 4, 15, 14, 3, 11, 5, 2, 12 } }, { // S_Box[4]{ 7, 13, 14, 3, 0, 6, 9, 10, 1, 2, 8, 5, 11, 12, 4, 15 },{ 13, 8, 11, 5, 6, 15, 0, 3, 4, 7, 2, 12, 1, 10, 14, 9 },{ 10, 6, 9, 0, 12, 11, 7, 13, 15, 1, 3, 14, 5, 2, 8, 4 },{ 3, 15, 0, 6, 10, 1, 13, 8, 9, 4, 5, 11, 12, 7, 2, 14 } }, { // S_Box[5]{ 2, 12, 4, 1, 7, 10, 11, 6, 8, 5, 3, 15, 13, 0, 14, 9 },{ 14, 11, 2, 12, 4, 7, 13, 1, 5, 0, 15, 10, 3, 9, 8, 6 },{ 4, 2, 1, 11, 10, 13, 7, 8, 15, 9, 12, 5, 6, 3, 0, 14 },{ 11, 8, 12, 7, 1, 14, 2, 13, 6, 15, 0, 9, 10, 4, 5, 3 } }, { // S_Box[6]{ 12, 1, 10, 15, 9, 2, 6, 8, 0, 13, 3, 4, 14, 7, 5, 11 },{ 10, 15, 4, 2, 7, 12, 9, 5, 6, 1, 13, 14, 0, 11, 3, 8 },{ 9, 14, 15, 5, 2, 8, 12, 3, 7, 0, 4, 10, 1, 13, 11, 6 },{ 4, 3, 2, 12, 9, 5, 15, 10, 11, 14, 1, 7, 6, 0, 8, 13 } }, { // S_Box[7]{ 4, 11, 2, 14, 15, 0, 8, 13, 3, 12, 9, 7, 5, 10, 6, 1 },{ 13, 0, 11, 7, 4, 9, 1, 10, 14, 3, 5, 12, 2, 15, 8, 6 },{ 1, 4, 11, 13, 12, 3, 7, 14, 10, 15, 6, 8, 0, 5, 9, 2 },{ 6, 11, 13, 8, 1, 4, 10, 7, 9, 5, 0, 15, 14, 2, 3, 12 } }, { // S_Box[8]{ 13, 2, 8, 4, 6, 15, 11, 1, 10, 9, 3, 14, 5, 0, 12, 7 },{ 1, 15, 13, 8, 10, 3, 7, 4, 12, 5, 6, 11, 0, 14, 9, 2 },{ 7, 11, 4, 1, 9, 12, 14, 2, 0, 6, 10, 13, 15, 3, 5, 8 },{ 2, 1, 14, 7, 4, 10, 8, 13, 15, 12, 9, 0, 3, 5, 6, 11 } } }; private static final int[] LeftMove = { 1, 1, 2, 2, 2, 2, 2, 2, 1, 2, 2, 2, 2, 2, 2, 1 };/*** 对64位明文进行IP置换处理,* @param data 需要经过初始IP置换的明文* @return 64位经过置换处理的明文*/public int[] IpReplace(int[] data){int[] ipMingWen = new int[64];for (int i = 0; i < ipMingWen.length; i++) {ipMingWen[i] = data[IP[i]-1];}return ipMingWen;}public static int[] StringToBits(String data){byte[] test = data.getBytes();int[] IntVa = new int[64];int[] IntDa = new int[8];for (int i = 0; i < 8; i++) {IntDa[i] = test[i];if (IntDa[i] < 0) {IntDa[i] += 256;IntDa[i] %= 256;}}for (int i = 0; i < 8; i++) {for (int j = 0; j < 8; j++) {IntVa[((i * 8) + 7) - j] = IntDa[i] % 2;IntDa[i] = IntDa[i] / 2;}}return IntVa;}/*** 功能:对给定的数组按照offset指定的位数进行循环左移,输出经过左移后的数组* 作用:将经过pc-1置换处理后的56位密钥先分成左右各28位,然后根据左移表要求对密钥进行左移* @param key 经过pc-1处理后的56位密钥* @return 单个56位的子密钥(初步,未经过pc2置换)*/public int[] LeftMove(int[] key,int offset){int[] subKey = new int[56];int[] C0 = new int[28];int[] D0 = new int[28];int[] C1 = new int[28];int[] D1 = new int[28];for (int i = 0; i < 28; i++) {C0[i] = key[i];D0[i] = key[i+28];}if(offset == 1){for(int i = 0; i < 27;i++){C1[i] = C0[i+1];D1[i] = D0[i+1];}C1[27] = C0[0];D1[27] = D0[0];}else if(offset == 2){for (int i = 0; i < 26; i++) {C1[i] = C0[i+2];D1[i] = D0[i+2];}C1[26] = C0[0];D1[26] = D0[0];C1[27] = C0[1];D1[27] = D0[1];}for (int i = 0; i < 28; i++) {subKey[i] = C1[i];subKey[i+28] = D1[i];}return subKey;}/*** 根据经过PC-1置换后的56位密钥生成16个56位的子密钥。

相关文档
最新文档