mirror of
https://github.com/corda/corda.git
synced 2025-01-30 16:14:39 +00:00
This commit is contained in:
parent
cfb28f6a1f
commit
07d9a1ead8
@ -2,7 +2,7 @@ package net.corda.nodeapi.internal.crypto
|
||||
|
||||
import net.corda.core.CordaOID
|
||||
import net.corda.core.crypto.Crypto
|
||||
import net.corda.core.crypto.random63BitValue
|
||||
import net.corda.core.crypto.newSecureRandom
|
||||
import net.corda.core.internal.*
|
||||
import net.corda.core.utilities.days
|
||||
import net.corda.core.utilities.millis
|
||||
@ -35,6 +35,8 @@ import java.time.Instant
|
||||
import java.time.temporal.ChronoUnit
|
||||
import java.util.*
|
||||
import javax.security.auth.x500.X500Principal
|
||||
import kotlin.experimental.and
|
||||
import kotlin.experimental.or
|
||||
|
||||
object X509Utilities {
|
||||
val DEFAULT_IDENTITY_SIGNATURE_SCHEME = Crypto.EDDSA_ED25519_SHA512
|
||||
@ -57,6 +59,8 @@ object X509Utilities {
|
||||
// future and stick to [A-Za-z0-9].
|
||||
const val DISTRIBUTED_NOTARY_ALIAS_PREFIX = "distributed-notary"
|
||||
|
||||
private const val CERTIFICATE_SERIAL_NUMBER_LENGTH = 16
|
||||
|
||||
val DEFAULT_VALIDITY_WINDOW = Pair(0.millis, 3650.days)
|
||||
|
||||
/**
|
||||
@ -166,7 +170,7 @@ object X509Utilities {
|
||||
nameConstraints: NameConstraints? = null,
|
||||
crlDistPoint: String? = null,
|
||||
crlIssuer: X500Name? = null): X509v3CertificateBuilder {
|
||||
val serial = BigInteger.valueOf(random63BitValue())
|
||||
val serial = generateCertificateSerialNumber()
|
||||
val keyPurposes = DERSequence(ASN1EncodableVector().apply { certificateType.purposes.forEach { add(it) } })
|
||||
val subjectPublicKeyInfo = SubjectPublicKeyInfo.getInstance(ASN1Sequence.getInstance(subjectPublicKey.encoded))
|
||||
val role = certificateType.role
|
||||
@ -346,6 +350,15 @@ object X509Utilities {
|
||||
builder.addExtension(Extension.cRLDistributionPoints, false, CRLDistPoint(arrayOf(distPoint)))
|
||||
}
|
||||
}
|
||||
|
||||
@Suppress("MagicNumber")
|
||||
private fun generateCertificateSerialNumber(): BigInteger {
|
||||
val bytes = ByteArray(CERTIFICATE_SERIAL_NUMBER_LENGTH)
|
||||
newSecureRandom().nextBytes(bytes)
|
||||
// Set highest byte to 01xxxxxx to ensure positive sign and constant bit length.
|
||||
bytes[0] = bytes[0].and(0x3F).or(0x40)
|
||||
return BigInteger(bytes)
|
||||
}
|
||||
}
|
||||
|
||||
// Assuming cert type to role is 1:1
|
||||
|
@ -452,4 +452,16 @@ class X509UtilitiesTest {
|
||||
assertEquals(childKeyPair.public, reloadedPublicKey)
|
||||
assertEquals(childKeyPair.private, reloadedPrivateKey)
|
||||
}
|
||||
|
||||
@Test(timeout = 300_000)
|
||||
fun `check certificate serial number`() {
|
||||
val keyPair = generateKeyPair()
|
||||
val subject = X500Principal("CN=Test,O=R3 Ltd,L=London,C=GB")
|
||||
val cert = X509Utilities.createSelfSignedCACertificate(subject, keyPair)
|
||||
assertTrue(cert.serialNumber.signum() > 0)
|
||||
assertEquals(127, cert.serialNumber.bitLength())
|
||||
val serialized = X509Utilities.buildCertPath(cert).encoded
|
||||
val deserialized = X509CertificateFactory().delegate.generateCertPath(serialized.inputStream()).x509Certificates.first()
|
||||
assertEquals(cert.serialNumber, deserialized.serialNumber)
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user