Supposed that the 33 bytes encoded Public Key can be created like this:
Security.addProvider(provider)
val generator = KeyPairGenerator.getInstance("ECDSA")
val ecSpec = ECNamedCurveTable.getParameterSpec("secp256r1")
generator.initialize(ecSpec)
val keyPair = generator.generateKeyPair()
val privateKey = keyPair.private as ECPrivateKey
val publicKey = keyPair.public as ECPublicKey
val publicEncoded = publicKey.q.getEncoded(true)
How can I reconstruct it again on the other side (when I am having only the 33 bytes sent from here)?
I was trying below code:
val publicKey =KeyFactory.getInstance("EC").generatePublic(X509EncodedKeySpec(publicEncoded))
But I guess this is totally wrong, as I am getting the:
java.security.spec.InvalidKeySpecException: java.lang.RuntimeException: error:0c000079:ASN.1 encoding routines:OPENSSL_internal:HEADER_TOO_LONG
I was trying also:
val generator = KeyPairGenerator.getInstance("ECDSA")
val ecPublicKey = generator
.generatePublic(X509EncodedKeySpec((publicEncoded))) as ECPublicKey
But the error is:
java.security.spec.InvalidKeySpecException: encoded key spec not recognised
How to achieve my goal?
This should do the job:
import org.bouncycastle.jce.ECNamedCurveTable
import org.bouncycastle.jce.spec.ECPublicKeySpec
fun publicKeyFromCompressed(compressedPublicKey: ByteArray): PublicKey {
val ecSpec = ECNamedCurveTable.getParameterSpec("secp256r1")
val point = ecSpec.curve.decodePoint(compressedPublicKey)
val publicKeySpec = ECPublicKeySpec(point, ecSpec)
val keyFactory = KeyFactory.getInstance("ECDSA")
val publicKey = keyFactory.generatePublic(publicKeySpec)
return publicKey
}