gpt4 book ai didi

java - 让 GPG 解密在 Java 中工作(Bouncy CaSTLe)

转载 作者:搜寻专家 更新时间:2023-10-30 19:58:53 26 4
gpt4 key购买 nike

首先让我说我对这一切都非常陌生。我想做的是在 Java 中使用 gpg 来解密加密文件。

我成功完成的事情:

  • 有一位同事使用我的公钥和他的私钥加密文件并成功解密。

  • 反其道而行之

  • 如果另一位同事尝试解密不适合他的文件:失败(如预期)

我的 key 是这样生成的...

(gpg --version 告诉我我正在使用 1.4.5 而我正在使用 Bouncy CaSTLe 1.47)

gpg --gen-ley

选择选项“DSA 和 Elgamal(默认)”

填写其他字段并生成 key 。

文件是用我的公钥和另一个人的私钥加密的。我想解密它。我编写了以下 Java 代码来完成此操作。我正在使用几种已弃用的方法,但我无法弄清楚如何正确实现使用未弃用版本所需的工厂方法,因此,如果有人对我应该使用的那些方法的实现有想法,那将是不错的奖金。

    Security.addProvider(new BouncyCastleProvider());

PGPSecretKeyRingCollection secretKeyRing = new PGPSecretKeyRingCollection(new FileInputStream(new File("test-files/secring.gpg")));
PGPSecretKeyRing pgpSecretKeyRing = (PGPSecretKeyRing) secretKeyRing.getKeyRings().next();
PGPSecretKey secretKey = pgpSecretKeyRing.getSecretKey();
PGPPrivateKey privateKey = secretKey.extractPrivateKey("mypassword".toCharArray(), "BC");

System.out.println(privateKey.getKey().getAlgorithm());
System.out.println(privateKey.getKey().getFormat());

PGPObjectFactory pgpF = new PGPObjectFactory(
new FileInputStream(new File("test-files/test-file.txt.gpg")));
Object pgpObj = pgpF.nextObject();
PGPEncryptedDataList encryptedDataList = (PGPEncryptedDataList) pgpObj;

Iterator objectsIterator = encryptedDataList.getEncryptedDataObjects();

PGPPublicKeyEncryptedData publicKeyEncryptedData = (PGPPublicKeyEncryptedData) objectsIterator.next();
InputStream inputStream = publicKeyEncryptedData.getDataStream(privateKey, "BC");

因此,当我运行这段代码时,我了解到我的 key 的算法和格式如下:

算法:DSA格式:PKCS#8

然后它在最后一行中断:

Exception in thread "main" org.bouncycastle.openpgp.PGPException: error setting asymmetric cipher
at org.bouncycastle.openpgp.operator.jcajce.JcePublicKeyDataDecryptorFactoryBuilder.decryptSessionData(Unknown Source)
at org.bouncycastle.openpgp.operator.jcajce.JcePublicKeyDataDecryptorFactoryBuilder.access$000(Unknown Source)
at org.bouncycastle.openpgp.operator.jcajce.JcePublicKeyDataDecryptorFactoryBuilder$2.recoverSessionData(Unknown Source)
at org.bouncycastle.openpgp.PGPPublicKeyEncryptedData.getDataStream(Unknown Source)
at org.bouncycastle.openpgp.PGPPublicKeyEncryptedData.getDataStream(Unknown Source)
at org.bouncycastle.openpgp.PGPPublicKeyEncryptedData.getDataStream(Unknown Source)
at org.bouncycastle.openpgp.PGPPublicKeyEncryptedData.getDataStream(Unknown Source)
at TestBouncyCastle.main(TestBouncyCastle.java:74)

引起:java.security.InvalidKeyException:传递给 ElGamal 的未知 key 类型 在 org.bouncycaSTLe.jcajce.provider.asymmetric.elgamal.CipherSpi.engineInit(未知来源) 在 org.bouncycaSTLe.jcajce.provider.asymmetric.elgamal.CipherSpi.engineInit(未知来源) 在 javax.crypto.Cipher.init(DashoA13*..) 在 javax.crypto.Cipher.init(DashoA13*..) ... 还有 8 个

我对这里的很多建议持开放态度,从“不要使用 gpg,改用 x”到“不要使用充气城堡,改用 x”到介于两者之间的任何建议。谢谢!

最佳答案

如果有人有兴趣知道如何使用 bouncy caSTLe openPGP 库加密和解密 gpg 文件,请查看以下 java 代码:

以下是您需要的 4 种方法:

以下方法将从 .asc 文件中读取并导入您的 key :

public static PGPSecretKey readSecretKeyFromCol(InputStream in, long keyId) throws IOException, PGPException {
in = PGPUtil.getDecoderStream(in);
PGPSecretKeyRingCollection pgpSec = new PGPSecretKeyRingCollection(in, new BcKeyFingerprintCalculator());

PGPSecretKey key = pgpSec.getSecretKey(keyId);

if (key == null) {
throw new IllegalArgumentException("Can't find encryption key in key ring.");
}
return key;
}

以下方法将从 .asc 文件中读取并导入您的公钥:

@SuppressWarnings("rawtypes")
public static PGPPublicKey readPublicKeyFromCol(InputStream in) throws IOException, PGPException {
in = PGPUtil.getDecoderStream(in);
PGPPublicKeyRingCollection pgpPub = new PGPPublicKeyRingCollection(in, new BcKeyFingerprintCalculator());
PGPPublicKey key = null;
Iterator rIt = pgpPub.getKeyRings();
while (key == null && rIt.hasNext()) {
PGPPublicKeyRing kRing = (PGPPublicKeyRing) rIt.next();
Iterator kIt = kRing.getPublicKeys();
while (key == null && kIt.hasNext()) {
PGPPublicKey k = (PGPPublicKey) kIt.next();
if (k.isEncryptionKey()) {
key = k;
}
}
}
if (key == null) {
throw new IllegalArgumentException("Can't find encryption key in key ring.");
}
return key;
}

以下2种解密和加密gpg文件的方法:

public void decryptFile(InputStream in, InputStream secKeyIn, InputStream pubKeyIn, char[] pass) throws IOException, PGPException, InvalidCipherTextException {
Security.addProvider(new BouncyCastleProvider());

PGPPublicKey pubKey = readPublicKeyFromCol(pubKeyIn);

PGPSecretKey secKey = readSecretKeyFromCol(secKeyIn, pubKey.getKeyID());

in = PGPUtil.getDecoderStream(in);

JcaPGPObjectFactory pgpFact;


PGPObjectFactory pgpF = new PGPObjectFactory(in, new BcKeyFingerprintCalculator());

Object o = pgpF.nextObject();
PGPEncryptedDataList encList;

if (o instanceof PGPEncryptedDataList) {

encList = (PGPEncryptedDataList) o;

} else {

encList = (PGPEncryptedDataList) pgpF.nextObject();

}

Iterator<PGPPublicKeyEncryptedData> itt = encList.getEncryptedDataObjects();
PGPPrivateKey sKey = null;
PGPPublicKeyEncryptedData encP = null;
while (sKey == null && itt.hasNext()) {
encP = itt.next();
secKey = readSecretKeyFromCol(new FileInputStream("PrivateKey.asc"), encP.getKeyID());
sKey = secKey.extractPrivateKey(new BcPBESecretKeyDecryptorBuilder(new BcPGPDigestCalculatorProvider()).build(pass));
}
if (sKey == null) {
throw new IllegalArgumentException("Secret key for message not found.");
}

InputStream clear = encP.getDataStream(new BcPublicKeyDataDecryptorFactory(sKey));

pgpFact = new JcaPGPObjectFactory(clear);

PGPCompressedData c1 = (PGPCompressedData) pgpFact.nextObject();

pgpFact = new JcaPGPObjectFactory(c1.getDataStream());

PGPLiteralData ld = (PGPLiteralData) pgpFact.nextObject();
ByteArrayOutputStream bOut = new ByteArrayOutputStream();

InputStream inLd = ld.getDataStream();

int ch;
while ((ch = inLd.read()) >= 0) {
bOut.write(ch);
}

//System.out.println(bOut.toString());

bOut.writeTo(new FileOutputStream(ld.getFileName()));
//return bOut;

}

public static void encryptFile(OutputStream out, String fileName, PGPPublicKey encKey) throws IOException, NoSuchProviderException, PGPException {
Security.addProvider(new BouncyCastleProvider());

ByteArrayOutputStream bOut = new ByteArrayOutputStream();

PGPCompressedDataGenerator comData = new PGPCompressedDataGenerator(PGPCompressedData.ZIP);

PGPUtil.writeFileToLiteralData(comData.open(bOut), PGPLiteralData.BINARY, new File(fileName));

comData.close();

PGPEncryptedDataGenerator cPk = new PGPEncryptedDataGenerator(new BcPGPDataEncryptorBuilder(SymmetricKeyAlgorithmTags.TRIPLE_DES).setSecureRandom(new SecureRandom()));

cPk.addMethod(new BcPublicKeyKeyEncryptionMethodGenerator(encKey));

byte[] bytes = bOut.toByteArray();

OutputStream cOut = cPk.open(out, bytes.length);

cOut.write(bytes);

cOut.close();

out.close();
}

现在这里是如何调用/运行上面的:

try {
decryptFile(new FileInputStream("encryptedFile.gpg"), new FileInputStream("PrivateKey.asc"), new FileInputStream("PublicKey.asc"), "yourKeyPassword".toCharArray());

PGPPublicKey pubKey = readPublicKeyFromCol(new FileInputStream("PublicKey.asc"));

encryptFile(new FileOutputStream("encryptedFileOutput.gpg"), "fileToEncrypt.txt", pubKey);




} catch (PGPException e) {
fail("exception: " + e.getMessage(), e.getUnderlyingException());
}

关于java - 让 GPG 解密在 Java 中工作(Bouncy CaSTLe),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14993223/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com