From ee032cf94a94c63dc76f062cfc6ad0b5c9e01dba Mon Sep 17 00:00:00 2001 From: luotao Date: Mon, 4 Sep 2023 18:26:39 +0800 Subject: [PATCH] =?UTF-8?q?fix:=20=E4=BF=AE=E5=A4=8D=E5=AE=A2=E6=88=B7?= =?UTF-8?q?=E7=AB=AFCertificateVerify=E6=B6=88=E6=81=AF=E6=9C=AA=E7=AD=BE?= =?UTF-8?q?=E5=90=8D=E5=AF=BC=E8=87=B4decrypt=5Ferror=E9=94=99=E8=AF=AF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/com/aliyun/gmsse/crypto/Crypto.java | 49 +++++++++++++++++-- .../protocol/ClientConnectionContext.java | 7 ++- .../protocol/ServerConnectionContext.java | 12 ++++- 3 files changed, 60 insertions(+), 8 deletions(-) diff --git a/src/main/java/com/aliyun/gmsse/crypto/Crypto.java b/src/main/java/com/aliyun/gmsse/crypto/Crypto.java index d5714e8..d1c9ba7 100644 --- a/src/main/java/com/aliyun/gmsse/crypto/Crypto.java +++ b/src/main/java/com/aliyun/gmsse/crypto/Crypto.java @@ -17,18 +17,18 @@ import org.bouncycastle.asn1.DLSequence; import org.bouncycastle.asn1.gm.GMNamedCurves; import org.bouncycastle.asn1.x9.X9ECParameters; +import org.bouncycastle.crypto.CipherParameters; +import org.bouncycastle.crypto.CryptoException; import org.bouncycastle.crypto.Digest; import org.bouncycastle.crypto.InvalidCipherTextException; import org.bouncycastle.crypto.digests.SM3Digest; import org.bouncycastle.crypto.engines.SM2Engine; import org.bouncycastle.crypto.macs.HMac; -import org.bouncycastle.crypto.params.ECDomainParameters; -import org.bouncycastle.crypto.params.ECPrivateKeyParameters; -import org.bouncycastle.crypto.params.ECPublicKeyParameters; -import org.bouncycastle.crypto.params.KeyParameter; -import org.bouncycastle.crypto.params.ParametersWithRandom; +import org.bouncycastle.crypto.params.*; +import org.bouncycastle.crypto.signers.SM2Signer; import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPrivateKey; import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPublicKey; +import org.bouncycastle.jce.spec.ECParameterSpec; public class Crypto { private static X9ECParameters x9ECParameters = GMNamedCurves.getByName("sm2p256v1"); @@ -159,4 +159,43 @@ public static byte[] hash(byte[] bytes) { digest.doFinal(output, 0); return output; } + + public static byte[] sign(BCECPrivateKey ecPriKey, byte[] withId, byte[] srcData){ + ECParameterSpec parameterSpec = ecPriKey.getParameters(); + ECDomainParameters domainParameters = new ECDomainParameters(parameterSpec.getCurve(), parameterSpec.getG(), + parameterSpec.getN(), parameterSpec.getH()); + ECPrivateKeyParameters priKeyParameters = new ECPrivateKeyParameters(ecPriKey.getD(), domainParameters); + SM2Signer signer = new SM2Signer(); + CipherParameters param = null; + ParametersWithRandom pwr = new ParametersWithRandom(priKeyParameters, new SecureRandom()); + if (withId != null) { + param = new ParametersWithID(pwr, withId); + } else { + param = pwr; + } + signer.init(true, param); + signer.update(srcData, 0, srcData.length); + try { + return signer.generateSignature(); + } catch (CryptoException e) { + e.printStackTrace(); + } + return new byte[0]; + } + public static boolean verify(BCECPublicKey ecPublicKey, byte[] withId, byte[] srcData,byte[] sign){ + ECParameterSpec parameterSpec = ecPublicKey.getParameters(); + ECDomainParameters domainParameters = new ECDomainParameters(parameterSpec.getCurve(), parameterSpec.getG(), + parameterSpec.getN(), parameterSpec.getH()); + ECPublicKeyParameters pubKeyParameters = new ECPublicKeyParameters(ecPublicKey.getQ(), domainParameters); + SM2Signer signer = new SM2Signer(); + CipherParameters param; + if (withId != null) { + param = new ParametersWithID(pubKeyParameters, withId); + } else { + param = pubKeyParameters; + } + signer.init(false, param); + signer.update(srcData, 0, srcData.length); + return signer.verifySignature(sign); + } } diff --git a/src/main/java/com/aliyun/gmsse/protocol/ClientConnectionContext.java b/src/main/java/com/aliyun/gmsse/protocol/ClientConnectionContext.java index e925abe..8baf392 100644 --- a/src/main/java/com/aliyun/gmsse/protocol/ClientConnectionContext.java +++ b/src/main/java/com/aliyun/gmsse/protocol/ClientConnectionContext.java @@ -3,6 +3,7 @@ import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; +import java.security.PrivateKey; import java.security.cert.CertificateException; import java.security.cert.X509Certificate; import java.util.ArrayList; @@ -14,6 +15,7 @@ import org.bouncycastle.crypto.engines.SM4Engine; import org.bouncycastle.crypto.params.KeyParameter; +import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPrivateKey; import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPublicKey; import com.aliyun.gmsse.AlertException; @@ -182,7 +184,10 @@ private void sendCertificateVerify() throws IOException { for (Handshake handshake : handshakes) { out.write(handshake.getBytes()); } - byte[] signature = Crypto.hash(out.toByteArray()); + // byte[] signature = Crypto.hash(out.toByteArray()); + byte[] source = Crypto.hash(out.toByteArray()); + PrivateKey key = sslContext.getKeyManager().getPrivateKey("sign"); + byte[] signature = Crypto.sign((BCECPrivateKey) key,null,source); CertificateVerify cv = new CertificateVerify(signature); Handshake hs = new Handshake(Handshake.Type.CERTIFICATE_VERIFY, cv); Record rc = new Record(ContentType.HANDSHAKE, version, hs.getBytes()); diff --git a/src/main/java/com/aliyun/gmsse/protocol/ServerConnectionContext.java b/src/main/java/com/aliyun/gmsse/protocol/ServerConnectionContext.java index 95de3b9..833842f 100644 --- a/src/main/java/com/aliyun/gmsse/protocol/ServerConnectionContext.java +++ b/src/main/java/com/aliyun/gmsse/protocol/ServerConnectionContext.java @@ -19,6 +19,7 @@ import org.bouncycastle.crypto.engines.SM4Engine; import org.bouncycastle.crypto.params.KeyParameter; import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPrivateKey; +import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPublicKey; import org.bouncycastle.jcajce.spec.SM2ParameterSpec; import org.bouncycastle.jce.provider.BouncyCastleProvider; @@ -123,8 +124,15 @@ private void receiveCertificateVerify() throws IOException { for (Handshake handshake : handshakes) { out.write(handshake.getBytes()); } - byte[] signature = Crypto.hash(out.toByteArray()); - if (!Arrays.equals(signature, cv.getSignature())) { + // byte[] signature = Crypto.hash(out.toByteArray()); + // if (!Arrays.equals(signature, cv.getSignature())) { + // throw new SSLException("certificate verify failed"); + // } + X509Certificate signCert = session.peerCerts[0]; + byte[] source = Crypto.hash(out.toByteArray()); + boolean flag = Crypto.verify((BCECPublicKey)signCert.getPublicKey(),null,source, + cv.getSignature()); + if (!flag) { throw new SSLException("certificate verify failed"); } handshakes.add(cf);