当前位置:   article > 正文

SM2国密加解、签名验签(包含ASN1转换)_php 将c1c3c2 格式 转 asn1

php 将c1c3c2 格式 转 asn1

依赖

<dependency>
    <groupId>org.bouncycastle</groupId>
    <artifactId>bcprov-jdk15to18</artifactId>
    <version>1.69</version>
</dependency>
<dependency>
    <groupId>cn.hutool</groupId>
    <artifactId>hutool-all</artifactId>
    <version>5.8.10</version>
</dependency>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

代码

import cn.hutool.core.util.ArrayUtil;
import cn.hutool.core.util.HexUtil;
import cn.hutool.crypto.BCUtil;
import cn.hutool.crypto.SmUtil;
import cn.hutool.crypto.asymmetric.KeyType;
import cn.hutool.crypto.asymmetric.SM2;
import cn.hutool.core.codec.Base64;
import org.bouncycastle.asn1.*;
import org.bouncycastle.asn1.gm.GMNamedCurves;
import org.bouncycastle.jcajce.provider.asymmetric.ec.BCECPublicKey;
import org.bouncycastle.math.ec.ECPoint;

import java.io.IOException;
import java.math.BigInteger;
import java.util.Arrays;

public class SM2Util {

    private static final int C1_LEN = 65;
    private static final int C3_LEN = 32;

    /**
     * 将c1c3c2转成标准的ASN1格式
     */
    public static byte[] changeC1C3C2ToAsn1(byte[] c1c3c2) throws IOException {
        byte[] c1 = Arrays.copyOfRange(c1c3c2, 0, C1_LEN);
        byte[] c3 = Arrays.copyOfRange(c1c3c2, C1_LEN, C1_LEN + C3_LEN);
        byte[] c2 = Arrays.copyOfRange(c1c3c2, C1_LEN + C3_LEN, c1c3c2.length);
        byte[] c1X = Arrays.copyOfRange(c1, 1, 33);
        byte[] c1Y = Arrays.copyOfRange(c1, 33, 65);

        BigInteger r = new BigInteger(1, c1X);
        BigInteger s = new BigInteger(1, c1Y);

        ASN1Integer x = new ASN1Integer(r);
        ASN1Integer y = new ASN1Integer(s);
        DEROctetString derDig = new DEROctetString(c3);
        DEROctetString derEnc = new DEROctetString(c2);
        ASN1EncodableVector v = new ASN1EncodableVector();
        v.add(x);
        v.add(y);
        v.add(derDig);
        v.add(derEnc);
        DERSequence seq = new DERSequence(v);
        return seq.getEncoded(ASN1Encoding.DER);
    }

    /**
     * 将ASN1格式转成c1c3c2
     */
    public static byte[] changeAsn1ToC1C3C2(byte[] asn1) throws IOException {
        ASN1InputStream aIn = new ASN1InputStream(asn1);
        ASN1Sequence seq = (ASN1Sequence) aIn.readObject();
        BigInteger x = ASN1Integer.getInstance(seq.getObjectAt(0)).getValue();
        BigInteger y = ASN1Integer.getInstance(seq.getObjectAt(1)).getValue();
        byte[] c3 = ASN1OctetString.getInstance(seq.getObjectAt(2)).getOctets();
        byte[] c2 = ASN1OctetString.getInstance(seq.getObjectAt(3)).getOctets();

        ECPoint c1Point =  GMNamedCurves.getByName("sm2p256v1").getCurve().createPoint(x, y);
        byte[] c1 = c1Point.getEncoded(false);
        return ArrayUtil.addAll(c1, c3, c2);
    }

    public static void main(String[] args) throws IOException {
        //需要加密的明文
        String text = "1111";
        //创建sm2 对象
        SM2 sm2 = SmUtil.sm2();
        //生成公钥
        byte[] publicKey = ((BCECPublicKey) sm2.getPublicKey()).getQ().getEncoded(false);
        //生成私钥
        byte[] privateKey = BCUtil.encodeECPrivateKey(sm2.getPrivateKey());
        //打印当前的公私秘钥
        System.out.println("公钥: " + HexUtil.encodeHexStr(publicKey));
        System.out.println("私钥: " + HexUtil.encodeHexStr(privateKey));

        SM2 sm2Test = SmUtil.sm2(privateKey, publicKey);
        byte[] encrypt = sm2Test.encrypt(text, KeyType.PublicKey);
        byte[] bytes = changeC1C3C2ToAsn1(encrypt);
        String encryptData = Base64.encode(bytes);
        System.out.println("加密后:"+encryptData);

        byte[] asn1 = Base64.decode(encryptData);
        byte[] c1c3c2 = changeAsn1ToC1C3C2(asn1);
        byte[] decryptData = sm2Test.decrypt(c1c3c2, KeyType.PrivateKey);
        System.out.println("解密后:"+new String(decryptData));

        byte[] sign = sm2Test.sign(text.getBytes());
        String signText = Base64.encode(sign);
        System.out.println("签名:"+ signText);
        boolean verify = sm2Test.verify(text.getBytes(), Base64.decode(signText));
        System.out.println("验签结果::"+ verify);
    }

}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/酷酷是懒虫/article/detail/998414
推荐阅读
相关标签
  

闽ICP备14008679号