Skip to content
ecdsa.com
Java (JDK 16+)Java

Error message

java.security.InvalidAlgorithmParameterException: Curve not supported: secp256k1 (1.3.132.0.10)

Also printed as

  • Legacy SunEC curve disabled

Thrown by `KeyPairGenerator.initialize`, `KeyFactory.generatePublic/Private` (wrapped in `InvalidKeySpecException`) and `Signature.initVerify`, depending on where the curve first appears. JDK 15 had already disabled these curves by default (JDK-8237219) with the message "Legacy SunEC curve disabled", re-enabled by `-Djdk.sunec.disableNative=false`; JDK 14 and earlier supported them.

Java (JDK 16+) — KeyPairGenerator / KeyFactory / Signature with the SunEC provider

What it means

The JDK knows the name secp256k1 (the curve used by Bitcoin and Ethereum) — it even resolves it to its OID 1.3.132.0.10 — but its built-in SunEC provider no longer implements it. JDK 16 removed the legacy curves together with the native EC library (release note "Removal of Legacy Elliptic Curves", JDK-8235710) and kept only curves with modern implementations: P-256, P-384, P-521, X25519/X448 and Ed25519/Ed448. Code that worked on Java 8 or 11 fails here after an upgrade.

Why it happens

How to fix it

  1. 1.

    Use the Bouncy Castle provider

    Bouncy Castle implements secp256k1 in pure Java. Register it and request it explicitly with `"BC"`.

    java
    import java.security.*;
    import java.security.spec.ECGenParameterSpec;
    import org.bouncycastle.jce.provider.BouncyCastleProvider;
    
    Security.addProvider(new BouncyCastleProvider());
    KeyPairGenerator generator = KeyPairGenerator.getInstance("EC", "BC");
    generator.initialize(new ECGenParameterSpec("secp256k1"));
    KeyPair pair = generator.generateKeyPair();
    
    Signature signature = Signature.getInstance("SHA256withECDSA", "BC");
  2. 2.

    For Ethereum work, use a library built for it

    web3j and similar libraries handle secp256k1, recovery ids and EIP-191 prefixes for you, which plain JCA does not.

    java
    // Ethereum signing/recovery: web3j implements secp256k1 itself (on top of Bouncy Castle).
    org.web3j.crypto.ECKeyPair keyPair = org.web3j.crypto.Keys.createEcKeyPair();
    org.web3j.crypto.Sign.SignatureData sig = org.web3j.crypto.Sign.signPrefixedMessage(message, keyPair);

Related errors

Browse the full signature error database