mirror of
https://github.com/emmansun/gmsm.git
synced 2025-04-27 04:36:19 +08:00
smx509: avoid crypto/rand.Int to generate serial number #308
This commit is contained in:
parent
d433e416fa
commit
89962cf1e3
@ -26,7 +26,6 @@ import (
|
|||||||
"crypto/ecdsa"
|
"crypto/ecdsa"
|
||||||
"crypto/ed25519"
|
"crypto/ed25519"
|
||||||
"crypto/elliptic"
|
"crypto/elliptic"
|
||||||
cryptorand "crypto/rand"
|
|
||||||
"crypto/rsa"
|
"crypto/rsa"
|
||||||
"crypto/sha1"
|
"crypto/sha1"
|
||||||
"crypto/x509"
|
"crypto/x509"
|
||||||
@ -118,7 +117,7 @@ func marshalPublicKey(pub any) (publicKeyBytes []byte, publicKeyAlgorithm pkix.A
|
|||||||
case ed25519.PublicKey:
|
case ed25519.PublicKey:
|
||||||
publicKeyBytes = pub
|
publicKeyBytes = pub
|
||||||
publicKeyAlgorithm.Algorithm = oidPublicKeyEd25519
|
publicKeyAlgorithm.Algorithm = oidPublicKeyEd25519
|
||||||
case *sdkecdh.PublicKey:
|
case *sdkecdh.PublicKey:
|
||||||
publicKeyBytes = pub.Bytes()
|
publicKeyBytes = pub.Bytes()
|
||||||
if pub.Curve() == sdkecdh.X25519() {
|
if pub.Curve() == sdkecdh.X25519() {
|
||||||
publicKeyAlgorithm.Algorithm = oidPublicKeyX25519
|
publicKeyAlgorithm.Algorithm = oidPublicKeyX25519
|
||||||
@ -1542,25 +1541,19 @@ func CreateCertificate(rand io.Reader, template, parent, pub, priv any) ([]byte,
|
|||||||
|
|
||||||
serialNumber := realTemplate.SerialNumber
|
serialNumber := realTemplate.SerialNumber
|
||||||
if serialNumber == nil {
|
if serialNumber == nil {
|
||||||
// Generate a serial number following RFC 5280 Section 4.1.2.2 if one is not provided.
|
// Generate a serial number following RFC 5280, Section 4.1.2.2 if one
|
||||||
// Requirements:
|
// is not provided. The serial number must be positive and at most 20
|
||||||
// - serial number must be positive
|
// octets *when encoded*.
|
||||||
// - at most 20 octets when encoded
|
serialBytes := make([]byte, 20)
|
||||||
maxSerial := big.NewInt(1).Lsh(big.NewInt(1), 20*8)
|
if _, err := io.ReadFull(rand, serialBytes); err != nil {
|
||||||
for {
|
return nil, err
|
||||||
var err error
|
|
||||||
serialNumber, err = cryptorand.Int(rand, maxSerial)
|
|
||||||
if err != nil {
|
|
||||||
return nil, err
|
|
||||||
}
|
|
||||||
// If the serial is exactly 20 octets, check if the high bit of the first byte is set.
|
|
||||||
// If so, generate a new serial, since it will be padded with a leading 0 byte during
|
|
||||||
// encoding so that the serial is not interpreted as a negative integer, making it
|
|
||||||
// 21 octets.
|
|
||||||
if serialBytes := serialNumber.Bytes(); len(serialBytes) > 0 && (len(serialBytes) < 20 || serialBytes[0]&0x80 == 0) {
|
|
||||||
break
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
// If the top bit is set, the serial will be padded with a leading zero
|
||||||
|
// byte during encoding, so that it's not interpreted as a negative
|
||||||
|
// integer. This padding would make the serial 21 octets so we clear the
|
||||||
|
// top bit to ensure the correct length in all cases.
|
||||||
|
serialBytes[0] &= 0b0111_1111
|
||||||
|
serialNumber = new(big.Int).SetBytes(serialBytes)
|
||||||
}
|
}
|
||||||
|
|
||||||
// RFC 5280 Section 4.1.2.2: serial number must be positive
|
// RFC 5280 Section 4.1.2.2: serial number must be positive
|
||||||
|
Loading…
x
Reference in New Issue
Block a user