2

I want to use bouncycastle to specify the 32bytes private key to generate the public key corresponding to secp256k1, but I only see that bouncycastle generates the keypair directly. I need to know the base point G of the elliptic curve. How can I modify this code to achieve it?

private static ECKeyPair create(KeyPair keyPair) {
        BCECPrivateKey privateKey = (BCECPrivateKey) keyPair.getPrivate();
        BCECPublicKey publicKey = (BCECPublicKey) keyPair.getPublic();
        BigInteger privateKeyVal = privateKey.getD();

        byte[] publicKeyBytes = publicKey.getQ().getEncoded(false);
        BigInteger publicKeyVal = new BigInteger(1, Arrays.copyOfRange(publicKeyBytes, 1, publicKeyBytes.length));

        return new ECKeyPair(privateKeyVal, publicKeyVal);
    }
    public static ECKeyPair createECKeyPair() throws NoSuchProviderException, NoSuchAlgorithmException,
            InvalidAlgorithmParameterException {
        //Add bouncy castle as key pair gen provider
        Security.addProvider(new BouncyCastleProvider());
        //Generate key pair
        KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance("ECDSA", "BC");
        ECGenParameterSpec ecGenParameterSpec = new ECGenParameterSpec("secp256k1");
        keyPairGenerator.initialize(ecGenParameterSpec, new SecureRandom());
        //Convert KeyPair to ECKeyPair, to store keys as BigIntegers
        return ECKeyPair.create(keyPairGenerator.generateKeyPair());
    }
Oiiiwk
  • 31
  • 5

1 Answers1

2

You' re probably using web3j because your create-method belongs to org.web3j.crypto.ECKeyPair. This class provides appropriate create-overloads for your purpose which expect the raw private key either as BigInteger or as byte array (the latter requires the web3j utilitiy classes in addition to web3j):

import org.web3j.crypto.ECKeyPair;
import java.math.BigInteger;
...
byte[] privateKey = hexStringToByteArray("a1e3ce382dafebc4ed9a9efc7d771f669745e2a88b33f2b5eb4efa8c47721346"); // e.g. from //kjur.github.io/jsrsasign/sample/sample-ecdsa.html
ECKeyPair ec =  ECKeyPair.create(new BigInteger(1, privateKey));
//ECKeyPair ec =  ECKeyPair.create(privateKey); // needs web3j utilitiy classes
System.out.println("Raw private key: " + ec.getPrivateKey().toString(16));
System.out.println("Raw public  key: " + ec.getPublicKey().toString(16));

Since ECKeyPair is implemented for Secp256k1, no curve parameters need to be specified. Note, that web3j requires BouncyCastle under the hood (although it's not explicitly used in the code above). In the example I created the byte array from a hex string for simplicity (here).

Topaco
  • 40,594
  • 4
  • 35
  • 62