Skip to content

JcaPGPKeyConverter incompatible with Thales JCA LunaProvider and RSA key pair generation #2195

Open

Description

@scordio

I'm working with a Thales Luna Network HSM and would like to use its LunaProvider as the implementation for JcaOpenPGPKeyGenerator.

When trying to generate an RSA key pair with the following:

OpenPGPKey key = new JcaOpenPGPKeyGenerator(4, LunaProvider.getInstance())
	.withPrimaryKey(generator -> generator.generateRsaKeyPair(4096))
	.build()

it fails with:

com.safenetinc.luna.exception.LunaException: Cannot access sensitive attributes...
	at com.safenetinc.luna.provider.key.LunaPrivateKeyRsa.getPrivateExponent(LunaPrivateKeyRsa.java:37)
	at org.bouncycastle.openpgp.operator.jcajce.JcaPGPKeyConverter.getPrivateBCPGKey(Unknown Source)
	at org.bouncycastle.openpgp.operator.jcajce.JcaPGPKeyConverter.getPGPPrivateKey(Unknown Source)
	at org.bouncycastle.openpgp.operator.jcajce.JcaPGPKeyPair.getPrivateKey(Unknown Source)
	at org.bouncycastle.openpgp.operator.jcajce.JcaPGPKeyPair.<init>(Unknown Source)
	at org.bouncycastle.openpgp.operator.jcajce.JcaPGPKeyPairGeneratorProvider$JcaPGPKeyPairGenerator.generateRsaKeyPair(Unknown Source)
	at org.bouncycastle.openpgp.operator.PGPKeyPairGenerator.generateRsaKeyPair(Unknown Source)
	at <lambda>
	...

This is because LunaPrivateKeyRsa throws a new LunaException("Cannot access sensitive attributes...") in all methods exposing sensitive parts of the key:

  • getCrtCoefficient()
  • getPrimeExponentP()
  • getPrimeExponentQ()
  • getPrimeP()
  • getPrimeQ()
  • getPrivateExponent()

and JcaPGPKeyConverter calls some of them at:

return new RSASecretBCPGKey(rsK.getPrivateExponent(), rsK.getPrimeP(), rsK.getPrimeQ());

Dependencies

  • com.safenet-inc:luna-provider:10.4.1-7 (not available on Maven Central)
  • org.bouncycastle:bcpg-jdk18on:1.82

Activity

  1. changed the title [-]`JcaPGPKeyConverter` incompatible with Thales JCA `LunaProvider`[/-] [+]`JcaPGPKeyConverter` incompatible with Thales JCA `LunaProvider` and RSA key pair generation[/+] on Nov 10, 2025
  2. dghgit commented on Nov 12, 2025

    @dghgit
    Contributor

    It's a HSM key, it's not going to provide the information required to produce a PGP encoding. Try using JcaPGPPrivateKey directly, you'll need to calculate the keyID for the public key as but you should be able to do that using the converter.

  3. vanitasvitae commented on Nov 28, 2025

    @vanitasvitae
    Contributor

    it's not going to provide the information required to produce a PGP encoding.

    That's not totally correct.

    Regarding HSM/TPM keys, I'm considering adding support for https://www.ietf.org/archive/id/draft-dkg-openpgp-hardware-secrets-02.html

    With this protocol extension it would be possible to create secret key packets which do not contain actual secret key material.
    Instead, the secret key packet would hint that the private key is stored on some hardware device.

    There is a chance that the OpenPGP WG might adopt the draft for an official RFC.

    GnuPG already has a similar mechanism (GNU_DUMMY_S2K) that is already present in BC, although not yet utilized.
    Adding hardware key support to BC requires some smaller changes, which I'm currently exploring.

  4. scordio commented on Oct 22, 2026

    @scordio
    Author

    Hi all, can I help somehow to move this topic forward?

    We're considering overriding parts of BouncyCastle to make this work at a lower level, but I'd be much happier if we could just wire the vendor JCA without any customizations on top of BC.

  5. dghgit commented on Oct 22, 2026

    @dghgit
    Contributor

    Did you try using JcaPGPPrivateKey directly after generating the key pair with the HSM provider?

  6. scordio commented on Oct 22, 2026

    @scordio
    Author

    Do you mean generating the RSA key without BC involvement? No, I didn't understand that last time from your message, but I'll try and let you know. Thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    support requestCommunity assistance requested

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions