SM2加解密示例

假设 Alice 和 Bob 想要用 SM2 算法加密和解密一些敏感数据,他们的公私钥对如下:

Alice 公钥:04 b7 1a f3 79 82 a3 8b f1 11 50 56 d7 63 50 24 eb 9f 4b 0a 08 23 9a 18 0c 6c 6a 5b 81 94 25 4c e7 a4 0a e9 03 1b 09 36 8f fc 5e 93 c7 4d b9 f2 be 7a 8c 92 56 08 7f 71 17

Alice 私钥:32 36 c6 ee 84 e6 03 28 0a 59 51 94 52 83 e2 54 4c 72 98 20 da b3 d4 42 0b f4 f0 31 2c 59 bd 2a

Bob 公钥:04 84 af a2 02 90 7b 36 9a 6a 75 99 52 00 c2 56 62 9a 21 93 9c 5d 6a 5f 07 18 97 6f 35 d4 87 7e 2c 83 b2 03 6d b8 e1 c1 6c 77 8b c2 0c d5 f9
cd 7a 4a 87 b7 21 23 ee 27 b2 f7 2b 10

Bob 私钥:4c 6f 86 21 3c 7b d1 77 2a 3e ec db 5c 58 3e 5e e7 30 6b 9e 6c db 5b 64 82 58 27 b4 79 87 3a 1d

现在 Alice 想要加密一段明文 “This is a secret message”,并将其发送给 Bob 进行解密。加解密的流程如下:

  1. Alice 将明文转换成字节数组,计算该数组的哈希值。这里的哈希函数使用 SHA-256。
String plainText = "This is a secret message";
byte[] plainBytes = plainText.getBytes();
byte[] digest = SM3Digest.hash(plainBytes); //使用 SM3 作为哈希函数,对明文取哈希值
  1. Alice 产生一个随机数 k,并利用 k 和自己的私钥计算出一个点 R。然后将该点的 X 坐标转换成整数,作为加密的参数。
BigInteger k = new BigInteger(256, new SecureRandom()); // 产生随机数 k
ECPrivateKeyParameters privateKey = Util.getPrivateKey("32 36 c6 ee 84 e6 03 28 0a 59 51 94 52 83 e2 54 4c 72 98 20 da b3 d4 42 0b f4 f0 31 2c 59 bd 2a");
ECDomainParameters domainParameters = privateKey.getParameters();
ECPoint R = ECAlgorithms.referenceMultiply(domainParameters.getG(), k); // 计算点 R = k * G
BigInteger x1 = R.getXCoord().toBigInteger(); // 取 R 的 X 坐标
  1. Alice 利用 Bob 的公钥和上一步计算得到的 X 坐标,对明文进行加密。加密后的结果是一个字节数组。
byte[] encryptedData = SM2Encrypt.encrypt(Util.hexToBytes("04 84 af a2 02 90 7b 36 9a 6a 75 99 52 00 c2 56 62 9a 21 93 9c 5d 6a 5f 07 18 97 6f 35 d4 87 7e 2c 83 b2 03 6d b8 e1 c1 6c 77 8b c2 0c d5 f9 cd 7a 4a 87 b7 21 23 ee 27 b2 f7 2b 10"), x1, digest); // 使用 SM2 对明文进行加密
  1. Bob 利用自己的私钥解密上一步得到的字节数组。
ECPrivateKeyParameters privateKey = Util.getPrivateKey("4c 6f 86 21 3c 7b d1 77 2a 3e ec db 5c 58 3e 5e e7 30 6b 9e 6c db 5b 64 82 58 27 b4 79 87 3a 1d");
ECDomainParameters domainParameters = privateKey.getParameters();
BigInteger x2 = new BigInteger(1, SM2Encrypt.decrypt(encryptedData, privateKey)).and(domainParameters.getCurve().getField().getCharacteristic().subtract(BigInteger.ONE)); // 使用 SM2 解密密文
  1. Bob 将 x2 带入到一个哈希函数中,得到一个字节数组,将其与上一步解密得到的明文对比是否相同。如果相同,则解密成功。
byte[] decryptData = SM2Encrypt.decrypt(encryptedData, privateKey); // 用私钥解密
byte[] digest = SM3Digest.hash(decryptData); // 对解密后的结果取哈希值
if (Arrays.equals(digest, SM3Digest.hash(plainBytes))) { // 对比解密后的结果是否与原始明文的哈希值相同
    System.out.println("Decryption Succeeded!");
} else {
    System.out.println("Decryption Failed!");
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值