把Java生成的RSA公钥、私钥转换成.NET使用的XML格式
测试代码:
PrivateKey privateKey=RSAUtils.getRSAPrivateKeyBybase64(savePrivateKey); PublicKey publicKey=RSAUtils.getRSAPublidKeyBybase64(savePublicKey); String publicKeyXml = getRSAPublicKeyAsNetFormat(publicKey.getEncoded()); String privateKeyXml = getRSAPrivateKeyAsNetFormat(privateKey.getEncoded());
import java.security.KeyFactory; import java.security.interfaces.RSAPrivateCrtKey; import java.security.interfaces.RSAPublicKey; import java.security.spec.PKCS8EncodedKeySpec; import java.security.spec.X509EncodedKeySpec;
1 private static String getRSAPrivateKeyAsNetFormat(byte[] encodedPrivkey) {
2 try {
3 StringBuffer buff = new StringBuffer(1024);
4
5 PKCS8EncodedKeySpec pvkKeySpec = new PKCS8EncodedKeySpec(
6 encodedPrivkey);
7 KeyFactory keyFactory = KeyFactory.getInstance("RSA");
8 RSAPrivateCrtKey pvkKey = (RSAPrivateCrtKey) keyFactory
9 .generatePrivate(pvkKeySpec);
10
11 buff.append("<RSAKeyValue>");
12 buff.append("<Modulus>"
13 + CodeUtils.base64Encode(removeMSZero(pvkKey.getModulus().toByteArray()))
14 + "</Modulus>");
15
16 buff.append("<Exponent>"
17 + CodeUtils.base64Encode(removeMSZero(pvkKey.getPublicExponent()
18 .toByteArray())) + "</Exponent>");
19
20 buff.append("<P>"
21 + CodeUtils.base64Encode(removeMSZero(pvkKey.getPrimeP().toByteArray()))
22 + "</P>");
23
24 buff.append("<Q>"
25 + CodeUtils.base64Encode(removeMSZero(pvkKey.getPrimeQ().toByteArray()))
26 + "</Q>");
27
28 buff.append("<DP>"
29 + CodeUtils.base64Encode(removeMSZero(pvkKey.getPrimeExponentP()
30 .toByteArray())) + "</DP>");
31
32 buff.append("<DQ>"
33 + CodeUtils.base64Encode(removeMSZero(pvkKey.getPrimeExponentQ()
34 .toByteArray())) + "</DQ>");
35
36 buff.append("<InverseQ>"
37 + CodeUtils.base64Encode(removeMSZero(pvkKey.getCrtCoefficient()
38 .toByteArray())) + "</InverseQ>");
39
40 buff.append("<D>"
41 + CodeUtils.base64Encode(removeMSZero(pvkKey.getPrivateExponent()
42 .toByteArray())) + "</D>");
43 buff.append("</RSAKeyValue>");
44
45 return buff.toString().replaceAll("[ \t\n\r]", "");
46 } catch (Exception e) {
47 System.err.println(e);
48 return null;
49 }
50 }
51
52 private static String getRSAPublicKeyAsNetFormat(byte[] encodedPublicKey) {
53 try {
54
55 KeyFactory keyFactory = KeyFactory.getInstance("RSA");
56 RSAPublicKey pukKey = (RSAPublicKey) keyFactory.generatePublic(new X509EncodedKeySpec(encodedPublicKey));
57
58 StringBuffer buff = new StringBuffer(1024);
59 buff.append("<RSAKeyValue>");
60 buff.append("<Modulus>"
61 + CodeUtils.base64Encode(removeMSZero(pukKey.getModulus().toByteArray()))
62 + "</Modulus>");
63 buff.append("<Exponent>"
64 + CodeUtils.base64Encode(removeMSZero(pukKey.getPublicExponent().toByteArray())) + "</Exponent>");
65 buff.append("</RSAKeyValue>");
11
66 return buff.toString().replaceAll("[ \t\n\r]", "");
67 } catch (Exception e) {
68 System.err.println(e);
69 return null;
70 }
71 }
private static byte[] removeMSZero(byte[] data) { byte[] data1; int len = data.length; if (data[0] == 0) { data1 = new byte[data.length - 1]; System.arraycopy(data, 1, data1, 0, len - 1); } else data1 = data; return data1; }
RSAUtils.java
// // Source code recreated from a .class file by IntelliJ IDEA // (powered by Fernflower decompiler) // package com.union.pufa; import java.math.BigInteger; import java.security.Key; import java.security.KeyFactory; import java.security.KeyPair; import java.security.KeyPairGenerator; import java.security.NoSuchAlgorithmException; import java.security.PrivateKey; import java.security.Provider; import java.security.PublicKey; import java.security.SecureRandom; import java.security.Signature; import java.security.interfaces.RSAPrivateKey; import java.security.interfaces.RSAPublicKey; import java.security.spec.InvalidKeySpecException; import java.security.spec.PKCS8EncodedKeySpec; import java.security.spec.RSAKeyGenParameterSpec; import java.security.spec.RSAPrivateKeySpec; import java.security.spec.RSAPublicKeySpec; import java.security.spec.X509EncodedKeySpec; import javax.crypto.Cipher; import org.apache.commons.codec.binary.Hex; import org.apache.commons.lang.StringUtils; import org.bouncycastle.jce.provider.BouncyCastleProvider; import org.slf4j.Logger; import org.slf4j.LoggerFactory; public abstract class RSAUtils { private static final Logger LOGGER = LoggerFactory.getLogger(RSAUtils.class); private static final String ALGORITHOM = "RSA"; private static final Provider DEFAULT_PROVIDER = new BouncyCastleProvider(); private static final String SIGNATURE_MD5WITHRSA = "MD5withRSA"; private static final String SIGNATURE_SHA1WITHRSA = "SHA1withRSA"; private static final String SIGNATURE_ALGORITHM_DEFAULT = "NONEwithRSA"; private static final String CIPHER_TRANSFORMATION_DEFAULT = "RSA/ECB/PKCS1Padding"; private static final String HASHID_SHA1 = "01"; private static final String HASHID_MD5 = "02"; private static KeyPairGenerator keyPairGen = null; private static KeyFactory keyFactory = null; static { try { keyPairGen = KeyPairGenerator.getInstance("RSA", DEFAULT_PROVIDER); keyFactory = KeyFactory.getInstance("RSA", DEFAULT_PROVIDER); } catch (NoSuchAlgorithmException var1) { LOGGER.error(var1.getMessage()); } } private RSAUtils() { } public static synchronized KeyPair generateRSAKeyPair(int keysize, BigInteger publicExponent) { try { keyPairGen.initialize(new RSAKeyGenParameterSpec(keysize, publicExponent), new SecureRandom()); return keyPairGen.generateKeyPair(); } catch (Exception var3) { LOGGER.error("生成模长 =" + keysize + ",指数=" + publicExponent + "的RSA密钥对失败", var3); return null; } } public static PrivateKey getRSAPrivateKey(String hexModulus, String hexPrivateExponent) { if(!StringUtils.isBlank(hexModulus) && !StringUtils.isBlank(hexPrivateExponent)) { BigInteger mbig = new BigInteger(hexModulus, 16); BigInteger ebig = new BigInteger(hexPrivateExponent, 16); RSAPrivateKeySpec prispec = new RSAPrivateKeySpec(mbig, ebig); try { return keyFactory.generatePrivate(prispec); } catch (InvalidKeySpecException var6) { LOGGER.error("hexModulus or hexPrivateExponent value is invalid. return null(RSAPrivateKey)."); return null; } } else { if(LOGGER.isDebugEnabled()) { LOGGER.debug("hexModulus and hexPrivateExponent cannot be empty. RSAPrivateKey value is null to return."); } return null; } } public static PublicKey getRSAPublidKey(String hexModulus, String hexPublicExponent) { if(!StringUtils.isBlank(hexModulus) && !StringUtils.isBlank(hexPublicExponent)) { BigInteger mbig = new BigInteger(hexModulus, 16); BigInteger ebig = new BigInteger(hexPublicExponent, 16); RSAPublicKeySpec pubspec = new RSAPublicKeySpec(mbig, ebig); try { return keyFactory.generatePublic(pubspec); } catch (InvalidKeySpecException var6) { LOGGER.error("hexModulus or hexPublicExponent value is invalid. return null(RSAPublicKey)."); return null; } } else { if(LOGGER.isDebugEnabled()) { LOGGER.debug("hexModulus and hexPublicExponent cannot be empty. return null(RSAPublicKey)."); } return null; } } public static String getBase64CodeKey(Key key) { return CodeUtils.base64Encode(key.getEncoded()); } public static String getNakedPublicKey(RSAPublicKey key) { return key.getModulus().toString(16).toUpperCase(); } private static byte[] getAsn1Len(int len) { int ret = false; byte[] buff = new byte[10]; byte[] asn1Len = (byte[])null; if(len > '\uffff') { return null; } else { byte ret; if(len > 255) { buff[0] = -126; buff[1] = (byte)((len & '\uff00') >> 8); buff[2] = (byte)(len & 255); ret = 3; } else if((len & 128) != 0) { buff[0] = -127; buff[1] = (byte)len; ret = 2; } else { buff[0] = (byte)len; ret = 1; } asn1Len = new byte[ret]; System.arraycopy(buff, 0, asn1Len, 0, ret); return asn1Len; } } public static byte[] getDerPK(byte[] pkModule, byte[] exp) { byte[] buff = new byte[4096]; byte[] tbuff = new byte[4096]; byte[] tmp = (byte[])null; byte[] derPK = (byte[])null; int offset = false; int len = false; int lenOfPkModule = pkModule.length; int lenOfExp = exp.length; if(pkModule != null && exp != null) { int offset = 0; tbuff[offset] = 2; int offset = offset + 1; tmp = getAsn1Len(lenOfPkModule + 1); System.arraycopy(tmp, 0, tbuff, offset, tmp.length); offset += tmp.length; tbuff[offset] = 0; ++offset; System.arraycopy(pkModule, 0, tbuff, offset, lenOfPkModule); offset += lenOfPkModule; tbuff[offset] = 2; ++offset; tmp = getAsn1Len(lenOfExp); System.arraycopy(tmp, 0, tbuff, offset, tmp.length); offset += tmp.length; System.arraycopy(exp, 0, tbuff, offset, lenOfExp); offset += lenOfExp; int len = offset; offset = 0; buff[offset] = 48; offset = offset + 1; tmp = getAsn1Len(len); System.arraycopy(tmp, 0, buff, offset, tmp.length); offset += tmp.length; System.arraycopy(tbuff, 0, buff, offset, len); offset += len; derPK = new byte[offset]; System.arraycopy(buff, 0, derPK, 0, offset); return derPK; } else { return null; } } public static String getDerPKWithAscHex(String pkModule, String exp) { return pkModule != null && exp != null?CodeUtils.byte2hex(getDerPK(CodeUtils.hex2byte(pkModule), CodeUtils.hex2byte(exp))):null; } public static PublicKey getPKfromDerPK(String racalPK) { byte[] racalPKStr = (byte[])null; if(racalPK == null) { return null; } else { racalPKStr = CodeUtils.hex2byte(racalPK); int offset = 0; if(racalPKStr[offset] != 48) { return null; } else { int offset = offset + 1; int i; int lenOfNextPart; int bitsOfLenFlag; if((racalPKStr[offset] & 255) <= 128) { lenOfNextPart = racalPKStr[offset] & 255; ++offset; } else { bitsOfLenFlag = (racalPKStr[offset] & 255) - 128; ++offset; i = 0; for(lenOfNextPart = 0; i < bitsOfLenFlag; ++offset) { lenOfNextPart += racalPKStr[offset] & 255; ++i; } } if((racalPKStr[offset] & 255) != 2) { return null; } else { ++offset; --lenOfNextPart; int lenOfPK = false; int lenOfPK; if((racalPKStr[offset] & 255) <= 128) { lenOfPK = racalPKStr[offset] & 255; ++offset; } else { bitsOfLenFlag = (racalPKStr[offset] & 255) - 128; ++offset; i = 0; for(lenOfPK = 0; i < bitsOfLenFlag; ++offset) { lenOfPK += racalPKStr[offset] & 255; ++i; } } while(lenOfPK % 8 != 0) { if((racalPKStr[offset] & 255) != 0) { return null; } ++offset; --lenOfPK; } byte[] LPk = new byte[lenOfPK]; System.arraycopy(racalPKStr, offset, LPk, 0, lenOfPK); String pk = CodeUtils.byte2hex(LPk); offset += lenOfPK; int lenOfEval = false; if(racalPKStr[offset] != 2) { return null; } else { ++offset; int lenOfEval = racalPKStr[offset]; ++offset; byte[] LPkEval = new byte[lenOfEval]; System.arraycopy(racalPKStr, offset, LPkEval, 0, lenOfEval); return getRSAPublidKey(pk, CodeUtils.byte2hex(LPkEval)); } } } } } public static RSAPublicKey getRSAPublidKeyBybase64(String base64s) { X509EncodedKeySpec keySpec = new X509EncodedKeySpec(CodeUtils.base64Decode(base64s)); RSAPublicKey publicKey = null; try { publicKey = (RSAPublicKey)keyFactory.generatePublic(keySpec); } catch (InvalidKeySpecException var4) { LOGGER.error("base64编码=" + base64s + "转RSA公钥失败", var4); } return publicKey; } public static RSAPrivateKey getRSAPrivateKeyBybase64(String base64s) { PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(CodeUtils.base64Decode(base64s)); RSAPrivateKey privateKey = null; try { privateKey = (RSAPrivateKey)keyFactory.generatePrivate(keySpec); } catch (InvalidKeySpecException var4) { LOGGER.error("base64编码=" + base64s + "转RSA私钥失败", var4); } return privateKey; } public static byte[] encrypt(Key key, byte[] data) throws Exception { Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding", DEFAULT_PROVIDER); cipher.init(1, key); return cipher.doFinal(data); } public static byte[] decrypt(Key key, byte[] data) throws Exception { Cipher cipher = Cipher.getInstance("RSA/ECB/PKCS1Padding", DEFAULT_PROVIDER); cipher.init(2, key); return cipher.doFinal(data); } public static String encryptString(Key key, String plaintext) { if(key != null && plaintext != null) { byte[] data = plaintext.getBytes(); try { byte[] en_data = encrypt(key, data); return new String(Hex.encodeHex(en_data)); } catch (Exception var4) { LOGGER.error(var4.getCause().getMessage()); return null; } } else { return null; } } public static String encryptStr4essc(Key key, String plaintext, String accNo, String encType) { if(key != null && plaintext != null) { if("1".equals(encType)) { plaintext = CodeUtils.paddingRightStr(plaintext, 'F', 16); } else if("0".equals(encType)) { plaintext = CodeUtils.asc2ascInt2hexasc(CodeUtils.paddingRightStr(plaintext, 'F', 16)); } byte[] data = CodeUtils.hex2byte(plaintext); try { byte[] en_data = encrypt(key, data); return (new String(Hex.encodeHex(en_data))).toUpperCase(); } catch (Exception var6) { LOGGER.error(var6.getCause().getMessage()); return null; } } else { return null; } } public static String decryptString(Key key, String encrypttext) { if(key != null && !StringUtils.isBlank(encrypttext)) { try { byte[] en_data = Hex.decodeHex(encrypttext.toCharArray()); byte[] data = decrypt(key, en_data); return new String(data); } catch (Exception var4) { LOGGER.error(String.format("\"%s\" Decryption failed. Cause: %s", new Object[]{encrypttext, var4.getCause().getMessage()})); return null; } } else { return null; } } public static String sign(RSAPrivateKey privatekey, String dataFillMode, String hashID, String data) throws Exception { Signature signature = Signature.getInstance("NONEwithRSA"); if("01".equals(hashID)) { data = CodeUtils.sha1String(data).toUpperCase(); } else if("02".equals(hashID)) { data = CodeUtils.md5String(data).toUpperCase(); } signature.initSign(privatekey); signature.update(data.getBytes()); return CodeUtils.byte2hex(signature.sign()).toUpperCase(); } public static boolean verifySign(PublicKey publicKey, String dataFillMode, String hashID, String data, String sign) throws Exception { Signature signature = Signature.getInstance("NONEwithRSA"); if("01".equals(hashID)) { data = CodeUtils.sha1String(data).toUpperCase(); } else if("02".equals(hashID)) { data = CodeUtils.md5String(data).toUpperCase(); } signature.initVerify(publicKey); signature.update(data.getBytes()); return signature.verify(CodeUtils.hex2byte(sign.toUpperCase())); } }