1
0
Fork 0
mirror of https://github.com/pgpainless/pgpainless.git synced 2024-12-23 11:27:57 +01:00

Implement certifying of certifications

This commit is contained in:
Paul Schaub 2022-05-11 12:27:11 +02:00
parent fa5ddfd112
commit d2b48e83d9
8 changed files with 277 additions and 31 deletions

View file

@ -10,8 +10,8 @@ public class Trustworthiness {
private final int depth; private final int depth;
public static final int THRESHOLD_FULLY_CONVINCED = 120; public static final int THRESHOLD_FULLY_CONVINCED = 120;
public static final int THRESHOLD_MARGINALLY_CONVINCED = 60; public static final int MARGINALLY_CONVINCED = 60;
public static final int THRESHOLD_NOT_TRUSTED = 0; public static final int NOT_TRUSTED = 0;
public Trustworthiness(int amount, int depth) { public Trustworthiness(int amount, int depth) {
this.amount = capAmount(amount); this.amount = capAmount(amount);
@ -26,6 +26,30 @@ public class Trustworthiness {
return depth; return depth;
} }
public boolean isNotTrusted() {
return getAmount() == NOT_TRUSTED;
}
public boolean isMarginallyTrusted() {
return getAmount() > NOT_TRUSTED;
}
public boolean isFullyTrusted() {
return getAmount() >= THRESHOLD_FULLY_CONVINCED;
}
public boolean isIntroducer() {
return getDepth() >= 1;
}
public boolean canIntroduce(int otherDepth) {
return getDepth() > otherDepth;
}
public boolean canIntroduce(Trustworthiness other) {
return canIntroduce(other.getDepth());
}
/** /**
* This means that we are fully convinced of the trustworthiness of the key. * This means that we are fully convinced of the trustworthiness of the key.
* *
@ -41,7 +65,7 @@ public class Trustworthiness {
* @return builder * @return builder
*/ */
public static Builder marginallyTrusted() { public static Builder marginallyTrusted() {
return new Builder(THRESHOLD_MARGINALLY_CONVINCED); return new Builder(MARGINALLY_CONVINCED);
} }
/** /**
@ -51,7 +75,7 @@ public class Trustworthiness {
* @return builder * @return builder
*/ */
public static Builder untrusted() { public static Builder untrusted() {
return new Builder(THRESHOLD_NOT_TRUSTED); return new Builder(NOT_TRUSTED);
} }
public static final class Builder { public static final class Builder {

View file

@ -19,7 +19,7 @@ import org.pgpainless.key.OpenPgpFingerprint;
import org.pgpainless.key.info.KeyRingInfo; import org.pgpainless.key.info.KeyRingInfo;
import org.pgpainless.key.protection.SecretKeyRingProtector; import org.pgpainless.key.protection.SecretKeyRingProtector;
import org.pgpainless.key.util.KeyRingUtils; import org.pgpainless.key.util.KeyRingUtils;
import org.pgpainless.signature.builder.DirectKeySignatureBuilder; import org.pgpainless.signature.builder.ThirdPartyDirectKeySignatureBuilder;
import org.pgpainless.signature.builder.ThirdPartyCertificationSignatureBuilder; import org.pgpainless.signature.builder.ThirdPartyCertificationSignatureBuilder;
import org.pgpainless.signature.subpackets.CertificationSubpackets; import org.pgpainless.signature.subpackets.CertificationSubpackets;
import org.pgpainless.util.DateUtil; import org.pgpainless.util.DateUtil;
@ -28,20 +28,60 @@ import javax.annotation.Nonnull;
import javax.annotation.Nullable; import javax.annotation.Nullable;
import java.util.Date; import java.util.Date;
/**
* API for creating certifications and delegations (Signatures) on keys.
* This API can be used to sign another persons OpenPGP key.
*
* A certification over a user-id is thereby used to attest, that the user believes that the user-id really belongs
* to the owner of the certificate.
* A delegation over a key can be used to delegate trust by marking the certificate as a trusted introducer.
*/
public class CertifyCertificate { public class CertifyCertificate {
/**
* Create a certification over a User-Id.
* By default, this method will use {@link CertificationType#GENERIC} to create the signature.
* If you need to create another type of certification, use
* {@link #userIdOnCertificate(String, PGPPublicKeyRing, CertificationType)} instead.
*
* @param userId user-id to certify
* @param certificate certificate
* @return API
*/
CertificationOnUserId userIdOnCertificate(@Nonnull String userId, @Nonnull PGPPublicKeyRing certificate) { CertificationOnUserId userIdOnCertificate(@Nonnull String userId, @Nonnull PGPPublicKeyRing certificate) {
return new CertificationOnUserId(userId, certificate, CertificationType.GENERIC); return new CertificationOnUserId(userId, certificate, CertificationType.GENERIC);
} }
/**
* Create a certification of the given {@link CertificationType} over a User-Id.
*
* @param userid user-id to certify
* @param certificate certificate
* @param certificationType type of signature
* @return API
*/
CertificationOnUserId userIdOnCertificate(@Nonnull String userid, @Nonnull PGPPublicKeyRing certificate, @Nonnull CertificationType certificationType) { CertificationOnUserId userIdOnCertificate(@Nonnull String userid, @Nonnull PGPPublicKeyRing certificate, @Nonnull CertificationType certificationType) {
return new CertificationOnUserId(userid, certificate, certificationType); return new CertificationOnUserId(userid, certificate, certificationType);
} }
/**
* Create a delegation (direct key signature) over a certificate.
*
* @param certificate certificate
* @return API
*/
DelegationOnCertificate certificate(@Nonnull PGPPublicKeyRing certificate) { DelegationOnCertificate certificate(@Nonnull PGPPublicKeyRing certificate) {
return certificate(certificate, null); return certificate(certificate, null);
} }
/**
* Create a delegation (direct key signature) containing a {@link org.bouncycastle.bcpg.sig.TrustSignature} packet
* over a certificate.
*
* @param certificate certificate
* @param trustworthiness trustworthiness of the certificate
* @return API
*/
DelegationOnCertificate certificate(@Nonnull PGPPublicKeyRing certificate, @Nullable Trustworthiness trustworthiness) { DelegationOnCertificate certificate(@Nonnull PGPPublicKeyRing certificate, @Nullable Trustworthiness trustworthiness) {
return new DelegationOnCertificate(certificate, trustworthiness); return new DelegationOnCertificate(certificate, trustworthiness);
} }
@ -58,8 +98,16 @@ public class CertifyCertificate {
this.certificationType = certificationType; this.certificationType = certificationType;
} }
/**
* Create the certification using the given key.
*
* @param certificationKey key used to create the certification
* @param protector protector to unlock the certification key
* @return API
* @throws PGPException in case of an OpenPGP related error
*/
CertificationOnUserIdWithSubpackets withKey(@Nonnull PGPSecretKeyRing certificationKey, @Nonnull SecretKeyRingProtector protector) throws PGPException { CertificationOnUserIdWithSubpackets withKey(@Nonnull PGPSecretKeyRing certificationKey, @Nonnull SecretKeyRingProtector protector) throws PGPException {
PGPSecretKey secretKey = getCertificationSecretKey(certificationKey); PGPSecretKey secretKey = getCertifyingSecretKey(certificationKey);
ThirdPartyCertificationSignatureBuilder sigBuilder = new ThirdPartyCertificationSignatureBuilder( ThirdPartyCertificationSignatureBuilder sigBuilder = new ThirdPartyCertificationSignatureBuilder(
certificationType.asSignatureType(), secretKey, protector); certificationType.asSignatureType(), secretKey, protector);
@ -80,11 +128,24 @@ public class CertifyCertificate {
this.sigBuilder = sigBuilder; this.sigBuilder = sigBuilder;
} }
public CertificationResult withSubpackets(@Nonnull CertificationSubpackets.Callback subpacketCallback) throws PGPException { /**
* Apply the given signature subpackets and build the certification.
*
* @param subpacketCallback callback to modify the signatures subpackets
* @return result
* @throws PGPException in case of an OpenPGP related error
*/
public CertificationResult buildWithSubpackets(@Nonnull CertificationSubpackets.Callback subpacketCallback) throws PGPException {
sigBuilder.applyCallback(subpacketCallback); sigBuilder.applyCallback(subpacketCallback);
return build(); return build();
} }
/**
* Build the certification signature.
*
* @return result
* @throws PGPException in case of an OpenPGP related error
*/
public CertificationResult build() throws PGPException { public CertificationResult build() throws PGPException {
PGPSignature signature = sigBuilder.build(certificate, userId); PGPSignature signature = sigBuilder.build(certificate, userId);
PGPPublicKeyRing certifiedCertificate = KeyRingUtils.injectCertification(certificate, userId, signature); PGPPublicKeyRing certifiedCertificate = KeyRingUtils.injectCertification(certificate, userId, signature);
@ -102,10 +163,18 @@ public class CertifyCertificate {
this.trustworthiness = trustworthiness; this.trustworthiness = trustworthiness;
} }
/**
* Build the delegation using the given certification key.
*
* @param certificationKey key to create the certification with
* @param protector protector to unlock the certification key
* @return API
* @throws PGPException in case of an OpenPGP related error
*/
public DelegationOnCertificateWithSubpackets withKey(@Nonnull PGPSecretKeyRing certificationKey, @Nonnull SecretKeyRingProtector protector) throws PGPException { public DelegationOnCertificateWithSubpackets withKey(@Nonnull PGPSecretKeyRing certificationKey, @Nonnull SecretKeyRingProtector protector) throws PGPException {
PGPSecretKey secretKey = getCertificationSecretKey(certificationKey); PGPSecretKey secretKey = getCertifyingSecretKey(certificationKey);
DirectKeySignatureBuilder sigBuilder = new DirectKeySignatureBuilder(secretKey, protector); ThirdPartyDirectKeySignatureBuilder sigBuilder = new ThirdPartyDirectKeySignatureBuilder(secretKey, protector);
if (trustworthiness != null) { if (trustworthiness != null) {
sigBuilder.getHashedSubpackets().setTrust(true, trustworthiness.getDepth(), trustworthiness.getAmount()); sigBuilder.getHashedSubpackets().setTrust(true, trustworthiness.getDepth(), trustworthiness.getAmount());
} }
@ -116,18 +185,31 @@ public class CertifyCertificate {
public static class DelegationOnCertificateWithSubpackets { public static class DelegationOnCertificateWithSubpackets {
private final PGPPublicKeyRing certificate; private final PGPPublicKeyRing certificate;
private final DirectKeySignatureBuilder sigBuilder; private final ThirdPartyDirectKeySignatureBuilder sigBuilder;
public DelegationOnCertificateWithSubpackets(@Nonnull PGPPublicKeyRing certificate, @Nonnull DirectKeySignatureBuilder sigBuilder) { DelegationOnCertificateWithSubpackets(@Nonnull PGPPublicKeyRing certificate, @Nonnull ThirdPartyDirectKeySignatureBuilder sigBuilder) {
this.certificate = certificate; this.certificate = certificate;
this.sigBuilder = sigBuilder; this.sigBuilder = sigBuilder;
} }
public CertificationResult withSubpackets(@Nonnull CertificationSubpackets.Callback subpacketsCallback) throws PGPException { /**
* Apply the given signature subpackets and build the delegation signature.
*
* @param subpacketsCallback callback to modify the signatures subpackets
* @return result
* @throws PGPException in case of an OpenPGP related error
*/
public CertificationResult buildWithSubpackets(@Nonnull CertificationSubpackets.Callback subpacketsCallback) throws PGPException {
sigBuilder.applyCallback(subpacketsCallback); sigBuilder.applyCallback(subpacketsCallback);
return build(); return build();
} }
/**
* Build the delegation signature.
*
* @return result
* @throws PGPException in case of an OpenPGP related error
*/
public CertificationResult build() throws PGPException { public CertificationResult build() throws PGPException {
PGPPublicKey delegatedKey = certificate.getPublicKey(); PGPPublicKey delegatedKey = certificate.getPublicKey();
PGPSignature delegation = sigBuilder.build(delegatedKey); PGPSignature delegation = sigBuilder.build(delegatedKey);
@ -146,18 +228,28 @@ public class CertifyCertificate {
this.certification = certification; this.certification = certification;
} }
/**
* Return the signature.
*
* @return signature
*/
@Nonnull @Nonnull
public PGPSignature getCertification() { public PGPSignature getCertification() {
return certification; return certification;
} }
/**
* Return the certificate, which now contains the signature.
*
* @return certificate + signature
*/
@Nonnull @Nonnull
public PGPPublicKeyRing getCertifiedCertificate() { public PGPPublicKeyRing getCertifiedCertificate() {
return certificate; return certificate;
} }
} }
private static PGPSecretKey getCertificationSecretKey(PGPSecretKeyRing certificationKey) { private static PGPSecretKey getCertifyingSecretKey(PGPSecretKeyRing certificationKey) {
Date now = DateUtil.now(); Date now = DateUtil.now();
KeyRingInfo info = PGPainless.inspectKeyRing(certificationKey, now); KeyRingInfo info = PGPainless.inspectKeyRing(certificationKey, now);
@ -179,5 +271,4 @@ public class CertifyCertificate {
} }
return secretKey; return secretKey;
} }
} }

View file

@ -56,10 +56,9 @@ import org.pgpainless.key.protection.fixes.S2KUsageFix;
import org.pgpainless.key.protection.passphrase_provider.SolitaryPassphraseProvider; import org.pgpainless.key.protection.passphrase_provider.SolitaryPassphraseProvider;
import org.pgpainless.key.util.KeyRingUtils; import org.pgpainless.key.util.KeyRingUtils;
import org.pgpainless.key.util.RevocationAttributes; import org.pgpainless.key.util.RevocationAttributes;
import org.pgpainless.signature.builder.DirectKeySignatureBuilder; import org.pgpainless.signature.builder.DirectKeySelfSignatureBuilder;
import org.pgpainless.signature.builder.RevocationSignatureBuilder; import org.pgpainless.signature.builder.RevocationSignatureBuilder;
import org.pgpainless.signature.builder.SelfSignatureBuilder; import org.pgpainless.signature.builder.SelfSignatureBuilder;
import org.pgpainless.signature.subpackets.CertificationSubpackets;
import org.pgpainless.signature.subpackets.RevocationSignatureSubpackets; import org.pgpainless.signature.subpackets.RevocationSignatureSubpackets;
import org.pgpainless.signature.subpackets.SelfSignatureSubpackets; import org.pgpainless.signature.subpackets.SelfSignatureSubpackets;
import org.pgpainless.signature.subpackets.SignatureSubpackets; import org.pgpainless.signature.subpackets.SignatureSubpackets;
@ -613,12 +612,10 @@ public class SecretKeyRingEditor implements SecretKeyRingEditorInterface {
PGPPublicKey publicKey = primaryKey.getPublicKey(); PGPPublicKey publicKey = primaryKey.getPublicKey();
final Date keyCreationTime = publicKey.getCreationTime(); final Date keyCreationTime = publicKey.getCreationTime();
DirectKeySignatureBuilder builder = new DirectKeySignatureBuilder(primaryKey, secretKeyRingProtector, prevDirectKeySig); DirectKeySelfSignatureBuilder builder = new DirectKeySelfSignatureBuilder(primaryKey, secretKeyRingProtector, prevDirectKeySig);
System.out.println("FIXME"); // will cause checkstyle warning so I remember builder.applyCallback(new SelfSignatureSubpackets.Callback() {
/*
builder.applyCallback(new CertificationSubpackets.Callback() {
@Override @Override
public void modifyHashedSubpackets(CertificationSubpackets hashedSubpackets) { public void modifyHashedSubpackets(SelfSignatureSubpackets hashedSubpackets) {
if (expiration != null) { if (expiration != null) {
hashedSubpackets.setKeyExpirationTime(keyCreationTime, expiration); hashedSubpackets.setKeyExpirationTime(keyCreationTime, expiration);
} else { } else {
@ -626,7 +623,6 @@ public class SecretKeyRingEditor implements SecretKeyRingEditorInterface {
} }
} }
}); });
*/
return builder.build(publicKey); return builder.build(publicKey);
} }

View file

@ -0,0 +1,57 @@
// SPDX-FileCopyrightText: 2021 Paul Schaub <vanitasvitae@fsfe.org>
//
// SPDX-License-Identifier: Apache-2.0
package org.pgpainless.signature.builder;
import javax.annotation.Nullable;
import org.bouncycastle.openpgp.PGPException;
import org.bouncycastle.openpgp.PGPPublicKey;
import org.bouncycastle.openpgp.PGPSecretKey;
import org.bouncycastle.openpgp.PGPSignature;
import org.bouncycastle.openpgp.PGPSignatureGenerator;
import org.pgpainless.algorithm.SignatureType;
import org.pgpainless.key.protection.SecretKeyRingProtector;
import org.pgpainless.signature.subpackets.SelfSignatureSubpackets;
public class DirectKeySelfSignatureBuilder extends AbstractSignatureBuilder<DirectKeySelfSignatureBuilder> {
public DirectKeySelfSignatureBuilder(PGPSecretKey certificationKey, SecretKeyRingProtector protector, PGPSignature archetypeSignature)
throws PGPException {
super(certificationKey, protector, archetypeSignature);
}
public DirectKeySelfSignatureBuilder(PGPSecretKey signingKey, SecretKeyRingProtector protector) throws PGPException {
super(SignatureType.DIRECT_KEY, signingKey, protector);
}
public SelfSignatureSubpackets getHashedSubpackets() {
return hashedSubpackets;
}
public SelfSignatureSubpackets getUnhashedSubpackets() {
return unhashedSubpackets;
}
public void applyCallback(@Nullable SelfSignatureSubpackets.Callback callback) {
if (callback != null) {
callback.modifyHashedSubpackets(getHashedSubpackets());
callback.modifyUnhashedSubpackets(getUnhashedSubpackets());
}
}
public PGPSignature build(PGPPublicKey key) throws PGPException {
PGPSignatureGenerator signatureGenerator = buildAndInitSignatureGenerator();
if (key.getKeyID() != publicSigningKey.getKeyID()) {
return signatureGenerator.generateCertification(publicSigningKey, key);
} else {
return signatureGenerator.generateCertification(key);
}
}
@Override
protected boolean isValidSignatureType(SignatureType type) {
return type == SignatureType.DIRECT_KEY;
}
}

View file

@ -15,14 +15,14 @@ import org.pgpainless.algorithm.SignatureType;
import org.pgpainless.key.protection.SecretKeyRingProtector; import org.pgpainless.key.protection.SecretKeyRingProtector;
import org.pgpainless.signature.subpackets.CertificationSubpackets; import org.pgpainless.signature.subpackets.CertificationSubpackets;
public class DirectKeySignatureBuilder extends AbstractSignatureBuilder<DirectKeySignatureBuilder> { public class ThirdPartyDirectKeySignatureBuilder extends AbstractSignatureBuilder<ThirdPartyDirectKeySignatureBuilder> {
public DirectKeySignatureBuilder(PGPSecretKey certificationKey, SecretKeyRingProtector protector, PGPSignature archetypeSignature) public ThirdPartyDirectKeySignatureBuilder(PGPSecretKey certificationKey, SecretKeyRingProtector protector, PGPSignature archetypeSignature)
throws PGPException { throws PGPException {
super(certificationKey, protector, archetypeSignature); super(certificationKey, protector, archetypeSignature);
} }
public DirectKeySignatureBuilder(PGPSecretKey signingKey, SecretKeyRingProtector protector) throws PGPException { public ThirdPartyDirectKeySignatureBuilder(PGPSecretKey signingKey, SecretKeyRingProtector protector) throws PGPException {
super(SignatureType.DIRECT_KEY, signingKey, protector); super(SignatureType.DIRECT_KEY, signingKey, protector);
} }

View file

@ -0,0 +1,74 @@
// SPDX-FileCopyrightText: 2022 Paul Schaub <vanitasvitae@fsfe.org>
//
// SPDX-License-Identifier: Apache-2.0
package org.pgpainless.algorithm;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;
import org.junit.jupiter.api.Test;
public class TrustworthinessTest {
@Test
public void fullyTrustedIntroducer() {
Trustworthiness it = Trustworthiness.fullyTrusted().introducer();
assertTrue(it.isFullyTrusted());
assertFalse(it.isNotTrusted());
assertTrue(it.isIntroducer());
assertFalse(it.canIntroduce(it));
}
@Test
public void marginallyTrustedIntroducer() {
Trustworthiness it = Trustworthiness.marginallyTrusted().introducer();
assertFalse(it.isFullyTrusted());
assertTrue(it.isMarginallyTrusted());
assertFalse(it.isNotTrusted());
assertTrue(it.isIntroducer());
assertFalse(it.canIntroduce(2));
}
@Test
public void nonTrustedIntroducer() {
Trustworthiness it = Trustworthiness.untrusted().introducer();
assertTrue(it.isNotTrusted());
assertFalse(it.isMarginallyTrusted());
assertFalse(it.isFullyTrusted());
assertTrue(it.isIntroducer());
}
@Test
public void trustedMetaIntroducer() {
Trustworthiness it = Trustworthiness.fullyTrusted().metaIntroducer();
assertTrue(it.isFullyTrusted());
assertTrue(it.isIntroducer());
Trustworthiness that = Trustworthiness.fullyTrusted().introducer();
assertTrue(it.canIntroduce(that));
assertFalse(that.canIntroduce(it));
}
@Test
public void invalidArguments() {
assertThrows(IllegalArgumentException.class, () -> new Trustworthiness(300, 1));
assertThrows(IllegalArgumentException.class, () -> new Trustworthiness(60, 300));
assertThrows(IllegalArgumentException.class, () -> new Trustworthiness(-4, 1));
assertThrows(IllegalArgumentException.class, () -> new Trustworthiness(120, -1));
}
@Test
public void inBetweenValues() {
Trustworthiness it = new Trustworthiness(30, 1);
assertTrue(it.isMarginallyTrusted());
assertFalse(it.isFullyTrusted());
it = new Trustworthiness(140, 1);
assertTrue(it.isFullyTrusted());
}
}

View file

@ -14,6 +14,7 @@ import java.security.InvalidAlgorithmParameterException;
import java.security.NoSuchAlgorithmException; import java.security.NoSuchAlgorithmException;
import java.util.List; import java.util.List;
import org.bouncycastle.bcpg.sig.TrustSignature;
import org.bouncycastle.openpgp.PGPException; import org.bouncycastle.openpgp.PGPException;
import org.bouncycastle.openpgp.PGPPublicKey; import org.bouncycastle.openpgp.PGPPublicKey;
import org.bouncycastle.openpgp.PGPPublicKeyRing; import org.bouncycastle.openpgp.PGPPublicKeyRing;
@ -84,6 +85,12 @@ public class CertifyCertificateTest {
assertNotNull(signature); assertNotNull(signature);
assertEquals(SignatureType.DIRECT_KEY, SignatureType.valueOf(signature.getSignatureType())); assertEquals(SignatureType.DIRECT_KEY, SignatureType.valueOf(signature.getSignatureType()));
assertEquals(alice.getPublicKey().getKeyID(), signature.getKeyID()); assertEquals(alice.getPublicKey().getKeyID(), signature.getKeyID());
TrustSignature trustSignaturePacket = signature.getHashedSubPackets().getTrust();
assertNotNull(trustSignaturePacket);
Trustworthiness trustworthiness = new Trustworthiness(trustSignaturePacket.getTrustAmount(), trustSignaturePacket.getDepth());
assertTrue(trustworthiness.isFullyTrusted());
assertTrue(trustworthiness.isIntroducer());
assertFalse(trustworthiness.canIntroduce(1));
assertTrue(SignatureVerifier.verifyDirectKeySignature( assertTrue(SignatureVerifier.verifyDirectKeySignature(
signature, alice.getPublicKey(), bob.getPublicKey(), PGPainless.getPolicy(), DateUtil.now())); signature, alice.getPublicKey(), bob.getPublicKey(), PGPainless.getPolicy(), DateUtil.now()));

View file

@ -29,19 +29,17 @@ import org.pgpainless.key.util.KeyRingUtils;
import org.pgpainless.signature.subpackets.SelfSignatureSubpackets; import org.pgpainless.signature.subpackets.SelfSignatureSubpackets;
import org.pgpainless.signature.subpackets.SignatureSubpacketsUtil; import org.pgpainless.signature.subpackets.SignatureSubpacketsUtil;
public class DirectKeySignatureBuilderTest { public class ThirdPartyDirectKeySignatureBuilderTest {
@Test @Test
public void testDirectKeySignatureBuilding() throws PGPException, InvalidAlgorithmParameterException, NoSuchAlgorithmException, InterruptedException { public void testDirectKeySignatureBuilding() throws PGPException, InvalidAlgorithmParameterException, NoSuchAlgorithmException, InterruptedException {
PGPSecretKeyRing secretKeys = PGPainless.generateKeyRing() PGPSecretKeyRing secretKeys = PGPainless.generateKeyRing()
.modernKeyRing("Alice"); .modernKeyRing("Alice");
DirectKeySignatureBuilder dsb = new DirectKeySignatureBuilder( DirectKeySelfSignatureBuilder dsb = new DirectKeySelfSignatureBuilder(
secretKeys.getSecretKey(), secretKeys.getSecretKey(),
SecretKeyRingProtector.unprotectedKeys()); SecretKeyRingProtector.unprotectedKeys());
System.out.println("FIXME"); // will cause checkstyle warning, so I remember
/*
dsb.applyCallback(new SelfSignatureSubpackets.Callback() { dsb.applyCallback(new SelfSignatureSubpackets.Callback() {
@Override @Override
public void modifyHashedSubpackets(SelfSignatureSubpackets hashedSubpackets) { public void modifyHashedSubpackets(SelfSignatureSubpackets hashedSubpackets) {
@ -52,7 +50,6 @@ public class DirectKeySignatureBuilderTest {
hashedSubpackets.setFeatures(Feature.MODIFICATION_DETECTION); hashedSubpackets.setFeatures(Feature.MODIFICATION_DETECTION);
} }
}); });
*/
Thread.sleep(1000); Thread.sleep(1000);