Java非对称加密算法--RSA加密算法

来源:互联网 发布:如何学淘宝运营 编辑:程序博客网 时间:2024/04/30 04:14

Java非对称加密算法--RSA加密算法

         RSA加密算法是一种非对称加密算法。在公开密钥加密和电子商业中RSA被广泛使用。RSA是1977年由罗纳德·李维斯特(Ron Rivest)、阿迪·萨莫尔(Adi Shamir)和伦纳德·阿德曼(Leonard Adleman)一起提出的。当时他们三人都在麻省理工学院工作。RSA就是他们三人姓氏开头字母拼在一起组成的。

1973年,在英国政府通讯总部工作的数学家克利福德·柯克斯(Clifford Cocks)在一个内部文件中提出了一个相同的算法,但他的发现被列入机密,一直到1997年才被发表。

         对极大整数做因数分解的难度决定了RSA算法的可靠性。换言之,对一极大整数做因数分解愈困难,RSA算法愈可靠。假如有人找到一种快速因数分解的算法的话,那么用RSA加密的信息的可靠性就肯定会极度下降。但找到这样的算法的可能性是非常小的。今天只有短的RSA钥匙才可能被强力方式解破。到2013年为止,世界上还没有任何可靠的攻击RSA算法的方式。只要其钥匙的长度足够长,用RSA加密的信息实际上是不能被解破的。

         下面我是采用Bouncy Castle实现的RSA加密算法。Bouncy Castle 是一种用于 Java 平台的开放源码的轻量级密码术包。它支持大量的密码术算法,并提供 JCE 1.2.1 的实现。因为 Bouncy Castle 被设计成轻量级的,所以从 J2SE 1.4 到 J2ME(包括 MIDP)平台,它都可以运行。它是在 MIDP 上运行的唯一完整的密码术包。

<span style="font-size:14px;">package com.qiuzhping.rsa;import org.bouncycastle.jce.provider.BouncyCastleProvider;import java.io.ByteArrayOutputStream;import java.io.File;import java.io.FileInputStream;import java.io.FileOutputStream;import java.io.ObjectInputStream;import java.io.ObjectOutputStream;import java.security.KeyPair;import java.security.KeyPairGenerator;import java.security.NoSuchAlgorithmException;import java.security.PrivateKey;import java.security.PublicKey;import java.security.SecureRandom;import javax.crypto.Cipher;/** * 非对称加密是公钥加密,私钥来解密.使用的是Bouncy Castle 是一种用于 Java 平台的开放源码的轻量级密码术包. * 1、此Demo使用的是bcprov-ext-jdk15on-152.jar  * 2、把jar文件复制到 $JAVA_HOME$\jre\lib\ext目录下面 * 3、修改配置文件\jre\lib\security\java.security * security.provider.1=sun.security.provider.Sun * security.provider.2=sun.security.rsa.SunRsaSign * security.provider.3=com.sun.net.ssl.internal.ssl.Provider * security.provider.4=com.sun.crypto.provider.SunJCE * security.provider.5=sun.security.jgss.SunProvider * security.provider.6=com.sun.security.sasl.Provider * security.provider.7=org.jcp.xml.dsig.internal.dom.XMLDSigRI * security.provider.8=sun.security.smartcardio.SunPCSC 上述8个是JDK已经实现了的加密方式. 将 * security.provider.9=org.bouncycastle.jce.provider.BouncyCastleProvider 添加到后面. * 非对称加密称为公钥加密,算法更加复杂,速度慢,加密和解密钥匙不相同,任何人都可以知道公钥,只有一个人持有私钥可以解密。 *  * @author Peter.Qiu *  */public class RsaUtil {/** * 根据publicKey 对data进行加密. *  * @param publicKey * @param data * @throws Exception * @author Peter.Qiu */public static byte[] encryptMode(PublicKey publicKey, byte[] data)throws Exception {try {Cipher cipher = Cipher.getInstance("RSA",new BouncyCastleProvider());cipher.init(Cipher.ENCRYPT_MODE, publicKey);// ENCRYPT_MODE 加密int blockSize = cipher.getBlockSize();int outputSize = cipher.getOutputSize(data.length);int leavedSize = data.length % blockSize;int blocksSize = leavedSize != 0 ? data.length / blockSize + 1: data.length / blockSize;byte[] raw = new byte[outputSize * blocksSize];int i = 0;while (data.length - i * blockSize > 0) {if (data.length - i * blockSize > blockSize) {cipher.doFinal(data, i * blockSize, blockSize, raw, i* outputSize);} else {cipher.doFinal(data, i * blockSize, data.length - i* blockSize, raw, i * outputSize);}i++;}return raw;} catch (Exception e) {throw e;}}/** * 根据privateKey 对data进行解密. *  * @param privateKey * @param data * @throws Exception * @author Peter.Qiu */public static byte[] decryptMode(PrivateKey privateKey, byte[] data)throws Exception {Cipher cipher = Cipher.getInstance("RSA", new BouncyCastleProvider());cipher.init(Cipher.DECRYPT_MODE, privateKey);// DECRYPT_MODE 解密int blockSize = cipher.getBlockSize();ByteArrayOutputStream bout = new ByteArrayOutputStream(64);int j = 0;while (data.length - j * blockSize > 0) {bout.write(cipher.doFinal(data, j * blockSize, blockSize));j++;}return bout.toByteArray();}/** * 获取密钥. *  * @param rsaKeyStore * @return * @throws Exception * @author Peter.Qiu */public static KeyPair getKeyPair(String rsaKeyStore) throws Exception {FileInputStream fis = new FileInputStream(rsaKeyStore);ObjectInputStream oos = new ObjectInputStream(fis);KeyPair kp = (KeyPair) oos.readObject();oos.close();fis.close();return kp;}/** * 将密钥写入文件. *  * @param kp * @param path * @throws Exception * @author Peter.Qiu */public static void saveKeyPair(KeyPair kp, String path) throws Exception {File file = new File(path);if (!file.exists() || file.isDirectory()) {file.createNewFile();}FileOutputStream fos = new FileOutputStream(path);ObjectOutputStream oos = new ObjectOutputStream(fos);// 生成密钥oos.writeObject(kp);oos.close();fos.close();}/** * 用于生成公匙或私匙. *  * @return * @throws NoSuchAlgorithmException * @author Peter.Qiu */public static KeyPair generateKeyPair() throws NoSuchAlgorithmException {SecureRandom sr = new SecureRandom();KeyPairGenerator kg = KeyPairGenerator.getInstance("RSA",new BouncyCastleProvider());// 注意密钥大小最好为1024,否则解密会有乱码情况.kg.initialize(1024, sr);KeyPair genKeyPair = kg.genKeyPair();return genKeyPair;}/** * 将公密或私密写入文件. *  * @param obj * @param path * @throws Exception * @author Peter.Qiu */public static void saveFile(Object obj, String path) throws Exception {File file = new File(path);if (!file.exists() || file.isDirectory()) {file.createNewFile();}FileOutputStream fos = new FileOutputStream(path);ObjectOutputStream oos = new ObjectOutputStream(fos);// 生成密钥oos.writeObject(obj);oos.close();fos.close();}/** * 获取公密. *  * @param publicKeyPath * @return * @throws Exception * @author Peter.Qiu */public static PublicKey getPublicKey(String publicKeyPath) throws Exception {FileInputStream fis = new FileInputStream(publicKeyPath);ObjectInputStream oos = new ObjectInputStream(fis);PublicKey kp = (PublicKey) oos.readObject();oos.close();fis.close();return kp;}/** * 获取私密. *  * @param privateKeyPath * @return * @throws Exception * @author Peter.Qiu */public static PrivateKey getPrivateKey(String privateKeyPath)throws Exception {FileInputStream fis = new FileInputStream(privateKeyPath);ObjectInputStream oos = new ObjectInputStream(fis);PrivateKey kp = (PrivateKey) oos.readObject();oos.close();fis.close();return kp;}public static void main(String[] args) throws Exception {File dir = new File("./key/");if (!dir.exists()) {dir.mkdir();}// 获取公匙及私匙KeyPair generateKeyPair = getKeyPair("./key/key");// 生成公钥及私钥// generateKeyPair = generateKeyPair();// 存储KeyPair到本地用于后期解密 注意修改前台RSAKeyPair// saveKeyPair(generateKeyPair,"./key/key");System.out.println("generateKeyPair : " + generateKeyPair);// 公匙 用于前台加密PublicKey publicKey = null;// generateKeyPair.getPublic();publicKey = getPublicKey("./key/publicKey.key");System.out.println("publicKey:" + publicKey);// saveFile(publicKey,"./key/publicKey.key");// 私匙 存储在后台用于解密PrivateKey privateKey = null;// generateKeyPair.getPrivate(); //privateKey = getPrivateKey("./key/privateKey.key");//System.out.println("privateKey:" + privateKey);// saveFile(privateKey,"./key/privateKey.key");// 测试加密解密String test = "saaaa";test = "Peter.Qiu丘丘丘邱";System.out.println("加密前字符:" + test);byte[] en_test = encryptMode(publicKey, test.getBytes("UTF-8"));System.out.println("加密后字符:" + new String(en_test));byte[] de_test = decryptMode(privateKey, en_test);System.out.println("解密后字符:" + new String(de_test, "UTF-8"));}}</span>


转摘请注明:http://blog.csdn.net/qiuzhping/article/details/44344373

效果图:

对应完整的项目:http://download.csdn.net/detail/qiu_11/8509319


2 0
原创粉丝点击