MAGIC - move x509 related to smx509 package

This commit is contained in:
emmansun 2021-02-13 18:11:03 +08:00
parent 371ea2f4b3
commit 8e3dc1f490
4 changed files with 32 additions and 27 deletions

View File

@ -118,7 +118,7 @@ var (
} }
) )
// Inverse, implements invertible interface, need to test this function's correctness // Inverse, implements invertible interface, used by Sign()
// n-2 = // n-2 =
// 1111111111111111111111111111111011111111111111111111111111111111 // 1111111111111111111111111111111011111111111111111111111111111111
// 1111111111111111111111111111111111111111111111111111111111111111 // 1111111111111111111111111111111111111111111111111111111111111111

View File

@ -43,6 +43,10 @@ type PrivateKey struct {
ecdsa.PrivateKey ecdsa.PrivateKey
} }
type ecdsaSignature struct {
R, S *big.Int
}
// Sign signs digest with priv, reading randomness from rand. The opts argument // Sign signs digest with priv, reading randomness from rand. The opts argument
// is not currently used but, in keeping with the crypto.Signer interface, // is not currently used but, in keeping with the crypto.Signer interface,
// should be the hash function used to digest the message. // should be the hash function used to digest the message.
@ -59,6 +63,16 @@ func (priv *PrivateKey) Sign(rand io.Reader, digest []byte, opts crypto.SignerOp
return asn1.Marshal(ecdsaSignature{r, s}) return asn1.Marshal(ecdsaSignature{r, s})
} }
// SignWithSM2 signs uid, msg with SignWithSM2 method.
func (priv *PrivateKey) SignWithSM2(rand io.Reader, uid, msg []byte) ([]byte, error) {
r, s, err := SignWithSM2(rand, &priv.PrivateKey, uid, msg)
if err != nil {
return nil, err
}
return asn1.Marshal(ecdsaSignature{r, s})
}
var ( var (
one = new(big.Int).SetInt64(1) one = new(big.Int).SetInt64(1)
initonce sync.Once initonce sync.Once

View File

@ -1,4 +1,4 @@
package sm2 package smx509
import ( import (
"crypto" "crypto"
@ -16,7 +16,7 @@ import (
"strconv" "strconv"
"strings" "strings"
"github.com/emmansun/gmsm/sm3" "github.com/emmansun/gmsm/sm2"
) )
// pkixPublicKey reflects a PKIX public key structure. See SubjectPublicKeyInfo // pkixPublicKey reflects a PKIX public key structure. See SubjectPublicKeyInfo
@ -38,12 +38,10 @@ type pkcs1PublicKey struct {
E int E int
} }
type dsaSignature struct { type ecdsaSignature struct {
R, S *big.Int R, S *big.Int
} }
type ecdsaSignature dsaSignature
// http://gmssl.org/docs/oid.html // http://gmssl.org/docs/oid.html
var ( var (
oidNamedCurveP224 = asn1.ObjectIdentifier{1, 3, 132, 0, 33} oidNamedCurveP224 = asn1.ObjectIdentifier{1, 3, 132, 0, 33}
@ -67,7 +65,7 @@ func oidFromNamedCurve(curve elliptic.Curve) (asn1.ObjectIdentifier, bool) {
return oidNamedCurveP384, true return oidNamedCurveP384, true
case elliptic.P521(): case elliptic.P521():
return oidNamedCurveP521, true return oidNamedCurveP521, true
case P256(): case sm2.P256():
return oidNamedCurveP256SM2, true return oidNamedCurveP256SM2, true
} }
@ -85,7 +83,7 @@ func namedCurveFromOID(oid asn1.ObjectIdentifier) elliptic.Curve {
case oid.Equal(oidNamedCurveP521): case oid.Equal(oidNamedCurveP521):
return elliptic.P521() return elliptic.P521()
case oid.Equal(oidNamedCurveP256SM2): case oid.Equal(oidNamedCurveP256SM2):
return P256() return sm2.P256()
} }
return nil return nil
} }
@ -124,7 +122,7 @@ func ParsePKIXPublicKey(derBytes []byte) (interface{}, error) {
if !namedCurveOID.Equal(oidNamedCurveP256SM2) { if !namedCurveOID.Equal(oidNamedCurveP256SM2) {
return x509.ParsePKIXPublicKey(derBytes) return x509.ParsePKIXPublicKey(derBytes)
} }
namedCurve := P256() namedCurve := sm2.P256()
x, y := elliptic.Unmarshal(namedCurve, asn1Data) x, y := elliptic.Unmarshal(namedCurve, asn1Data)
if x == nil { if x == nil {
return nil, errors.New("x509: failed to unmarshal elliptic curve point") return nil, errors.New("x509: failed to unmarshal elliptic curve point")
@ -145,7 +143,7 @@ func ParsePKIXPublicKey(derBytes []byte) (interface{}, error) {
// This kind of key is commonly encoded in PEM blocks of type "PUBLIC KEY". // This kind of key is commonly encoded in PEM blocks of type "PUBLIC KEY".
func MarshalPKIXPublicKey(pub interface{}) ([]byte, error) { func MarshalPKIXPublicKey(pub interface{}) ([]byte, error) {
ecdPub, ok := pub.(*ecdsa.PublicKey) ecdPub, ok := pub.(*ecdsa.PublicKey)
if !ok || ecdPub.Curve != P256() { if !ok || ecdPub.Curve != sm2.P256() {
return x509.MarshalPKIXPublicKey(pub) return x509.MarshalPKIXPublicKey(pub)
} }
@ -197,7 +195,7 @@ func CreateCertificateRequest(rand io.Reader, template *x509.CertificateRequest,
if !ok { if !ok {
return nil, errors.New("x509: certificate private key does not implement crypto.Signer") return nil, errors.New("x509: certificate private key does not implement crypto.Signer")
} }
privKey, ok := key.(*PrivateKey) privKey, ok := key.(*sm2.PrivateKey)
if !ok { if !ok {
return x509.CreateCertificateRequest(rand, template, priv) return x509.CreateCertificateRequest(rand, template, priv)
} }
@ -338,17 +336,8 @@ func CreateCertificateRequest(rand io.Reader, template *x509.CertificateRequest,
tbsCSR.Raw = tbsCSRContents tbsCSR.Raw = tbsCSRContents
signed := tbsCSRContents signed := tbsCSRContents
za, err := CalculateZA(&privKey.PublicKey, defaultUID) //Emman, use template.Subject as UID?
if err != nil {
return
}
h := sm3.New()
h.Write(za)
h.Write(signed)
signed = h.Sum(nil)
var signature []byte signature, err := privKey.SignWithSM2(rand, nil, signed)
signature, err = privKey.Sign(rand, signed, nil)
if err != nil { if err != nil {
return return
} }
@ -739,7 +728,7 @@ func getPublicKeyAlgorithmFromOID(oid asn1.ObjectIdentifier) x509.PublicKeyAlgor
func CheckSignature(c *x509.CertificateRequest) error { func CheckSignature(c *x509.CertificateRequest) error {
if c.PublicKeyAlgorithm == x509.ECDSA { if c.PublicKeyAlgorithm == x509.ECDSA {
pub, ok := c.PublicKey.(*ecdsa.PublicKey) pub, ok := c.PublicKey.(*ecdsa.PublicKey)
if ok && strings.EqualFold(P256().Params().Name, pub.Curve.Params().Name) { if ok && strings.EqualFold(sm2.P256().Params().Name, pub.Curve.Params().Name) {
return checkSignature(c, pub) return checkSignature(c, pub)
} }
} }
@ -759,7 +748,7 @@ func checkSignature(c *x509.CertificateRequest, publicKey *ecdsa.PublicKey) (err
if ecdsaSig.R.Sign() <= 0 || ecdsaSig.S.Sign() <= 0 { if ecdsaSig.R.Sign() <= 0 || ecdsaSig.S.Sign() <= 0 {
return errors.New("x509: ECDSA signature contained zero or negative values") return errors.New("x509: ECDSA signature contained zero or negative values")
} }
if !VerifyWithSM2(publicKey, nil, signed, ecdsaSig.R, ecdsaSig.S) { if !sm2.VerifyWithSM2(publicKey, nil, signed, ecdsaSig.R, ecdsaSig.S) {
return errors.New("x509: ECDSA verification failure") return errors.New("x509: ECDSA verification failure")
} }
return return

View File

@ -1,4 +1,4 @@
package sm2 package smx509
import ( import (
"crypto/ecdsa" "crypto/ecdsa"
@ -13,6 +13,8 @@ import (
"fmt" "fmt"
"strings" "strings"
"testing" "testing"
"github.com/emmansun/gmsm/sm2"
) )
const publicKeyPemFromAliKms = `-----BEGIN PUBLIC KEY----- const publicKeyPemFromAliKms = `-----BEGIN PUBLIC KEY-----
@ -70,7 +72,7 @@ func TestParseCertificateRequest(t *testing.T) {
} }
func TestCreateCertificateRequest(t *testing.T) { func TestCreateCertificateRequest(t *testing.T) {
priv, _ := GenerateKey(rand.Reader) priv, _ := sm2.GenerateKey(rand.Reader)
names := pkix.Name{CommonName: "TestName"} names := pkix.Name{CommonName: "TestName"}
var template = x509.CertificateRequest{Subject: names} var template = x509.CertificateRequest{Subject: names}
csrblock, err := CreateCertificateRequest(rand.Reader, &template, priv) csrblock, err := CreateCertificateRequest(rand.Reader, &template, priv)
@ -104,7 +106,7 @@ func TestSignByAliVerifyAtLocal(t *testing.T) {
pub, err := getPublicKey([]byte(publicKeyPemFromAliKmsForSign)) pub, err := getPublicKey([]byte(publicKeyPemFromAliKmsForSign))
pub1 := pub.(*ecdsa.PublicKey) pub1 := pub.(*ecdsa.PublicKey)
hashValue, _ := base64.StdEncoding.DecodeString(hashBase64) hashValue, _ := base64.StdEncoding.DecodeString(hashBase64)
result := Verify(pub1, hashValue, rs.R, rs.S) result := sm2.Verify(pub1, hashValue, rs.R, rs.S)
if !result { if !result {
t.Error("Verify fail") t.Error("Verify fail")
} }
@ -116,7 +118,7 @@ func TestParsePKIXPublicKey(t *testing.T) {
t.Fatal(err) t.Fatal(err)
} }
pub1 := pub.(*ecdsa.PublicKey) pub1 := pub.(*ecdsa.PublicKey)
encrypted, err := Encrypt(rand.Reader, pub1, []byte("testfile")) encrypted, err := sm2.Encrypt(rand.Reader, pub1, []byte("testfile"))
if err != nil { if err != nil {
t.Fatal(err) t.Fatal(err)
} }