#java #cryptography #bouncycastle #gnupg
#java #криптография #bouncycastle #gnupg
Вопрос:
Я пытаюсь загрузить секретные ключи из D:UsersxxxxxAppDataRoaminggnupgprivate-keys-v1.d использование надувного замка bcprov-jdk15on-1.66.jar .
import java.io.BufferedInputStream;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import org.bouncycastle.gpg.SExprParser;
import org.bouncycastle.openpgp.PGPException;
import org.bouncycastle.openpgp.PGPSecretKey;
import org.bouncycastle.openpgp.operator.PBEProtectionRemoverFactory;
import org.bouncycastle.openpgp.operator.PGPDigestCalculatorProvider;
import org.bouncycastle.openpgp.operator.jcajce.JcaKeyFingerprintCalculator;
import org.bouncycastle.openpgp.operator.jcajce.JcaPGPDigestCalculatorProviderBuilder;
import org.bouncycastle.openpgp.operator.jcajce.JcePBEProtectionRemoverFactory;
import org.bouncycastle.util.encoders.Hex;
public class LoadKey {
public static void main(String[] args) throws IOException, PGPException {
String filePath = "D:\Users\XXXX\AppData\Roaming\gnupg\private-keys-v1.d\4B8379C14DED7818D546E3C4AF7F1D0DF5716BCD.key";
String pass = "siv_test";
PGPDigestCalculatorProvider calculatorProvider = new JcaPGPDigestCalculatorProviderBuilder()
.build();
PBEProtectionRemoverFactory passphraseProvider = new JcePBEProtectionRemoverFactory(
pass.toCharArray());
InputStream in = new FileInputStream(filePath);
PGPSecretKey key =
new SExprParser(calculatorProvider).parseSecretKey(
new BufferedInputStream(in), passphraseProvider,
new JcaKeyFingerprintCalculator());
System.out.println("Found key "
Hex.toHexString(key.getPublicKey().getFingerprint()));
}
}
Но я получаю
Исключение в потоке «main» java.io.IOException: обнаружен неизвестный символ: K в org.bouncycastle.gpg.SXprUtils.skipOpenParenthesis(неизвестный источник) в org.bouncycastle.gpg.SExprParser.parseSecretKey(неизвестный источник)
gpg (GnuPG) 2.2.23
libgcrypt 1.8.6
Ответ №1:
Мне кажется, что SExprParse принимает только «необработанные» ключи pgp, а не «PEM».
Ключ в моем примере взят из надувного замка SExprTest.java итак, это образец ключа с паролем «fred«.
Поскольку ключ находится в двоичной форме, я использую a ByteArrayInputStream
для обработки ключа, это ссылка на полный тест: https://github.com/bcgit/bc-java/blob/master/pg/src/test/java/org/bouncycastle/openpgp/test/SExprTest.java.
Программа успешно запущена и в конце выдает секретный ключ:
Found key 228f5c0cd3e1d2716760770be5ac9684b1a77195
Возможно, один из наших экспертов по надувному замку сможет объяснить поведение немного лучше…
Вот код:
import org.bouncycastle.gpg.SExprParser;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.bouncycastle.openpgp.PGPException;
import org.bouncycastle.openpgp.PGPSecretKey;
import org.bouncycastle.openpgp.operator.PBEProtectionRemoverFactory;
import org.bouncycastle.openpgp.operator.PGPDigestCalculatorProvider;
import org.bouncycastle.openpgp.operator.jcajce.JcaKeyFingerprintCalculator;
import org.bouncycastle.openpgp.operator.jcajce.JcaPGPDigestCalculatorProviderBuilder;
import org.bouncycastle.openpgp.operator.jcajce.JcePBEProtectionRemoverFactory;
import org.bouncycastle.util.encoders.Base64;
import org.bouncycastle.util.encoders.Hex;
import java.io.*;
import java.security.Security;
public class LoadKeySo4 {
public static void main(String[] args) throws IOException, PGPException {
Security.addProvider(new BouncyCastleProvider());
//String filePath = "D:\Users\XXXX\AppData\Roaming\gnupg\private-keys-v1.d\4B8379C14DED7818D546E3C4AF7F1D0DF5716BCD.key";
//String pass = "siv_test";
byte[] key1 = Base64.decode(
"KDIxOnByb3RlY3RlZC1wcml2YXRlLWtleSgzOnJzYSgxOm4yNTc6AOpclatE"
"WCIXSUA2y44L/jPGE1lU3d75nMN5 iJK/vXFGmQdvZWhewX2LSJ5vwpcLcQ1"
"u3QXRbOcY0o jRAER2vHZMEfyHfHir6QDibVTO5IOjLettW054hew/HoFbA2"
"v3t0BB2HERWMFO6WLrC7wBVpgL85m85VhE/OmZGIOY7bapQtULoTQQ5Fwr0n"
" zG3gujxDcmpcTouz0DPtVLvMERnHMtJ4GEccWfiFrGUnLbBnYCnnsNoV/0m"
"f/GseRltCnxPS2Fl rhdkPmxC0Dkv6naV NMiaZVk5FYdtY66xATvETv xTa"
"X8xHIhJc4CrR/e4T0VPBh/94o5nHL1cT6HcpKDE6ZTM6AQABKSg5OnByb3Rl"
"Y3RlZDI1Om9wZW5wZ3AtczJrMy1zaGExLWFlcy1jYmMoKDQ6c2hhMTg6vqXu"
"vvqQtUw4OjI3OTYxMzQ0KTE2OlYbNG/073BvJLzSjbvoxQYpNzM2OkcNABDe"
"gU7iUAJwVxNszEG ackC6qk7Y dQ6NN4Avy9pkGo Rufs0G4yjHhVQMkH0QF"
"Wrzf5GOvsvrJQyJGVLn2amz5KxU onNv66UVi4D3LlCOghDcGoe/V7hY zsh"
"GN7elPhnBYbk7X1Jb5D03YrCOOCTnGLTLMc7E5qy4YSyRWMzAGGj/jkcY/B "
"ZEeLkTlHsnnukIMb24 1/sZrsV57AaVPRZwgzInxDGC9Tkg4j6fsHvvVw6ZD"
"cm ET/YGOf1dhMKEq/7GXcd5qeEpMBFi 6p2PrPJUwUHu/PIOs1SCIYlrhGR"
"iifAHtOIdFGefo E1v6kKZMO FgLTeiGYN6T6vjkG7FMiWwnmamF6qNd1D5i"
"TS2E4uiS5Z3QuwyXJfGkYYDjEmV5rVSol95Kd4wpebC7mFNbOk zA4TB5Ytb"
"5KN/w2lSW4btuB/pD/akfg6xJQ9BREv1vpO4CtK d8VLCPHI7et1tKjwJNxd"
"obw9P4HOBIPYdzbHARpAfZRLQlLRNcYp8DbHfzmDhIEPymO6 3CCtdfRE7xY"
"c0SMpFFYGX17WGlmjdOYWtbqYrhDQ3ylzD3vrIQr12ZZXw00xSJkNk4aJ8Lx"
"SihOXTuLiHhueckfCCbkWPfdJQg1ukjRiNgHdEF 7rk/2aMDsSYULJqtjSed"
"CDi9tLqawmCz405E W Htbrp2yv7ktST2IaV56JQB4Yay8WAlnngoBtdlSyA"
"wFVFm5VrCeZ5ckdUfK1qSezd32uQlb27XCZYGiaco5AWkhBOrdPoiw4Z14Pf"
"z6xhhV vA X6lm9k70iG7RO9vf3V EAbKktFos72rGJGhWOZgv5xr8DRjbIf"
"/dOQsgceYg4xrTzn/SjOSNmTQu Q1Uo5jjtMozgXawJNFPKcZ28DLTxdHQl"
"a7jZK/FiiXXBL8J/VbN9DWZq7IOUMEhRym8KcAoyC7wQgpua2qhp8EXX7Qqd"
"7dU4EcdWzzz/lF8pKDEyOnByb3RlY3RlZC1hdDE1OjIwMTgwNTI4VDAyMjIw"
"MikpKQ==");
String pass = "fred";
PGPDigestCalculatorProvider calculatorProvider = new JcaPGPDigestCalculatorProviderBuilder()
.build();
PBEProtectionRemoverFactory passphraseProvider = new JcePBEProtectionRemoverFactory(
pass.toCharArray());
//InputStream in = new FileInputStream(filePath);
InputStream in = new ByteArrayInputStream(key1);
PGPSecretKey key =
new SExprParser(calculatorProvider).parseSecretKey(
new BufferedInputStream(in), passphraseProvider,
new JcaKeyFingerprintCalculator());
System.out.println("Found key "
Hex.toHexString(key.getPublicKey().getFingerprint()));
}
}
Комментарии:
1. Здравствуйте, Майкл Фер, большое вам спасибо за ваш ответ. Но наша идея состоит в том, чтобы загрузить закрытый ключ для данного пользователя. Мой код отлично работает с GNUPG версии 2.1.X, поскольку он выдает исключение для GNUPG версии 2.2.X.
2. lists.gnupg.org/pipermail/gnupg-devel/2017-December/033295.html
3. Может быть, вы могли бы отредактировать свой вопрос и добавить образец ключа с GNUPG версии 2.2.X вместе с парольной фразой?