I'm trying sign a pdf, and my code signed the pdf but, when I open the document in Adobe I have this response: and I don't know what happens.
Certificate generator
public static BigInteger generateSerial() {
SecureRandom random = new SecureRandom();
return BigInteger.valueOf(Math.abs(random.nextLong()));
}
public static X509Certificate CeriticateGenerator(PublicKey publicKey, PrivateKey privateKey) throws OperatorCreationException, CertificateException, CertIOException {
Date startDate = new Date(System.currentTimeMillis());
Date expiryDate = new Date(System.currentTimeMillis() + 365 * 24 * 60 * 60 * 1000);
X500Name issuser=new X500Name("cn=Rubrica");
X500Name subject=new X500Name("cn=Rubrica");
X509v3CertificateBuilder certGen = new JcaX509v3CertificateBuilder(issuser,
generateSerial(),
startDate,
expiryDate,
subject,
publicKey).addExtension(Extension.subjectKeyIdentifier, false, createSubjectKeyId(publicKey))
.addExtension(Extension.authorityKeyIdentifier, false, createAuthorityKeyId(publicKey))
.addExtension(Extension.basicConstraints, true, new BasicConstraints(true));
ContentSigner sigGen = new JcaContentSignerBuilder("SHA512withRSA").setProvider("BC").build(privateKey);
return new JcaX509CertificateConverter()
.setProvider(new BouncyCastleProvider()).getCertificate(certGen.build(sigGen));
}
private static SubjectKeyIdentifier createSubjectKeyId(final PublicKey publicKey) throws OperatorCreationException {
final SubjectPublicKeyInfo publicKeyInfo = SubjectPublicKeyInfo.getInstance(publicKey.getEncoded());
final DigestCalculator digCalc =
new BcDigestCalculatorProvider().get(new AlgorithmIdentifier(OIWObjectIdentifiers.idSHA1));
return new X509ExtensionUtils(digCalc).createSubjectKeyIdentifier(publicKeyInfo);
}
/**
* Creates the hash value of the authority public key.
*
* #param publicKey of the authority certificate
*
* #return AuthorityKeyIdentifier hash
*
* #throws OperatorCreationException
*/
private static AuthorityKeyIdentifier createAuthorityKeyId(final PublicKey publicKey)
throws OperatorCreationException
{
final SubjectPublicKeyInfo publicKeyInfo = SubjectPublicKeyInfo.getInstance(publicKey.getEncoded());
final DigestCalculator digCalc =
new BcDigestCalculatorProvider().get(new AlgorithmIdentifier(OIWObjectIdentifiers.idSHA1));
return new X509ExtensionUtils(digCalc).createAuthorityKeyIdentifier(publicKeyInfo);
}
this is the interface Signature
public class PDBOXsignerManager implements SignatureInterface{
private PrivateKey privateKey;
private Certificate[] certificateChain;
PDBOXsignerManager(KeyStore keyStore, String password, String appCertificateAlias) {
try {
this.certificateChain = Optional.ofNullable(keyStore.getCertificateChain(appCertificateAlias))
.orElseThrow(() -> (new IOException("Could not find a proper certificate chain")));
this.privateKey = (PrivateKey) keyStore.getKey(appCertificateAlias, password.toCharArray());
Certificate certificate = this.certificateChain[0];
if (certificate instanceof X509Certificate) {
((X509Certificate) certificate).checkValidity();
}
} catch (KeyStoreException | IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (UnrecoverableKeyException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (CertificateExpiredException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (CertificateNotYetValidException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
#Override
public byte[] sign(InputStream content) throws IOException {
try {
CMSSignedDataGenerator gen = new CMSSignedDataGenerator();
X509Certificate cert = (X509Certificate) this.certificateChain[0];
ContentSigner ECDSASigner = new JcaContentSignerBuilder("SHA512withRSA").build(this.privateKey);
gen.addSignerInfoGenerator(new JcaSignerInfoGeneratorBuilder(new JcaDigestCalculatorProviderBuilder().build()).build(ECDSASigner, cert));
gen.addCertificates(new JcaCertStore(Arrays.asList(this.certificateChain)));
CMSProcessableInputStream msg = new CMSProcessableInputStream(content);
CMSSignedData signedData = gen.generate(msg, false);
return signedData.getEncoded();
} catch (GeneralSecurityException | CMSException | OperatorCreationException e) {
//throw new IOException cause a SignatureInterface, but keep the stacktrace
throw new IOException(e);
}
}
}
this the class signer
public class PDBOXSigner extends PDBOXsignerManager
{
PDBOXSigner(KeyStore keyStore, String password, String appCertificateAlias) {
super(keyStore, password, appCertificateAlias);
}
public void signDetached( PDDocument document, OutputStream output, String name, String reason) {
PDSignature pdSignature = new PDSignature();
pdSignature.setFilter(PDSignature.FILTER_ADOBE_PPKLITE);
pdSignature.setSubFilter(PDSignature.SUBFILTER_ADBE_PKCS7_SHA1);
pdSignature.setName(name);
pdSignature.setReason(reason);
// Se le agrega la fecha de firma necesaria para validar la misma
pdSignature.setSignDate(Calendar.getInstance());
// Registro del diccionario de firmas y y la interfaz de firma
try {
SignatureOptions signatureOptions = new SignatureOptions();
// Size can vary, but should be enough for purpose.
signatureOptions.setPreferredSignatureSize(SignatureOptions.DEFAULT_SIGNATURE_SIZE * 2);
// register signature dictionary and sign interface
document.addSignature(pdSignature, this, signatureOptions);
// write incremental (only for signing purpose)
document.saveIncremental(output);
output.flush();
output.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
I created the certificates and key pair with java and bouncycastle, i don't now if is the problem or what am I doing wrong?
The mistake was to use SUBFILTER_ADBE_PKCS7_SHA1 instead of the SUBFILTER_ADBE_PKCS7_DETACHED that is used in the official example. SUBFILTER_ADBE_PKCS7_SHA1 shouldn't be used for signing, it is deprecated in PDF 2.0.
Related
My program is able to create and write to a file using the path-file:
private static final String PUBLIC_KEY_FILE = "WebContent/Config/MyPublic.key";
private static final String PRIVATE_KEY_FILE = "WebContent/Config/MyPrivate.key";
And the correct files are generated within the folders according to the path declared above.
But then a FileNotFoundException error occurs when I try to read from those files using the path files:
private String REAL_PUBLIC_PATH = getServletContext().getRealPath("/WebContent/Config/MyPublic.key");
private String REAL_PRIVATE_PATH = getServletContext().getRealPath("/WebContent/Config/MyPrivate.key");
This is the lines of code that is causing the error:
PublicKey pubKey = readPublicKeyFromFile(this.REAL_PUBLIC_PATH);
PrivateKey privKey = readPrivateKeyFromFile(this.REAL_PRIVATE_PATH);
Which is tied to the variables REAL_PUBLIC_PATH and REAL_PUBLIC_PATH. Meaning there's something wrong with how the path file is being read.
My folder structure goes:
> MyProject
>Web-Content
>Config
>MyPublic.key
>MyPrivate.key
>WEB-INF
>META-INF
My full class code is below for context:
public class RSAEncryptionHelper extends HttpServlet {
private static final String PUBLIC_KEY_FILE = "WebContent/Config/MyPublic.key";
private static final String PRIVATE_KEY_FILE = "WebContent/Config/MyPrivate.key";
private String REAL_PUBLIC_PATH = getServletContext().getRealPath("/WebContent/Config/MyPublic.key");
private String REAL_PRIVATE_PATH = getServletContext().getRealPath("/WebContent/Config/MyPrivate.key");
public static void main(String[] args) throws IOException{
try
{
System.out.println("--GENERATE PUBLIC and PRIVATE KEY --");
KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance("RSA");
keyPairGenerator.initialize(2048); //1024 for normal securities
KeyPair keyPair = keyPairGenerator.generateKeyPair();
PublicKey publicKey = keyPair.getPublic();
PrivateKey privateKey = keyPair.getPrivate();
System.out.println("\n--PULLING OUT PARAMETERS WHICH MAKES KEYPAIR--\n");
KeyFactory keyFactory = KeyFactory.getInstance("RSA");
RSAPublicKeySpec rsaPubKeySpec = keyFactory.getKeySpec(publicKey, RSAPublicKeySpec.class);
RSAPrivateKeySpec rsaPrivKeySpec = keyFactory.getKeySpec(privateKey, RSAPrivateKeySpec.class);
System.out.println("\n--SAVING PUBLIC KEY AND PRIVATE KEY TO FILES--\n");
RSAEncryptionHelper rsaObj = new RSAEncryptionHelper();
rsaObj.saveKeys(PUBLIC_KEY_FILE, rsaPubKeySpec.getModulus(), rsaPubKeySpec.getPublicExponent());
rsaObj.saveKeys(PRIVATE_KEY_FILE, rsaPrivKeySpec.getModulus(), rsaPrivKeySpec.getPrivateExponent());
}
catch (NoSuchAlgorithmException | InvalidKeySpecException e)
{
System.out.println(e);
}
}
private void saveKeys(String fileName, BigInteger mod, BigInteger exp) throws IOException {
FileOutputStream fos = null;
ObjectOutputStream oos = null;
try
{
System.out.println("Generating: " + fileName + "...");
fos = new FileOutputStream(fileName);
oos = new ObjectOutputStream(new BufferedOutputStream(fos));
oos.writeObject(mod);
oos.writeObject(exp);
System.out.println(fileName + "generated successfully");;
}
catch (Exception e)
{
e.printStackTrace();
}
finally
{
if (oos!=null)
{
oos.close();
if (fos!= null)
{
fos.close();
}
}
}
}
public PublicKey readPublicKeyFromFile(String fileName) throws IOException{
FileInputStream fis = null;
ObjectInputStream ois = null;
PublicKey publicKey = null;
try
{
fis = new FileInputStream(new File(fileName));
ois = new ObjectInputStream(fis);
BigInteger modulus = (BigInteger) ois.readObject();
BigInteger exponent = (BigInteger) ois.readObject();
//Get Public Key
RSAPublicKeySpec rsaPublicKeySpec = new RSAPublicKeySpec(modulus, exponent);
KeyFactory fact = KeyFactory.getInstance("RSA");
publicKey = fact.generatePublic(rsaPublicKeySpec);
return publicKey;
}
catch (IOException e)
{
e.printStackTrace();
}
catch (ClassNotFoundException e)
{
e.printStackTrace();
}
catch (NoSuchAlgorithmException e)
{
e.printStackTrace();
}
catch (InvalidKeySpecException e)
{
e.printStackTrace();
}
finally
{
if (ois != null)
{
ois.close();
if (fis != null)
{
fis.close();
}
}
}
return publicKey;
}
public PrivateKey readPrivateKeyFromFile(String fileName) throws IOException{
FileInputStream fis = null;
ObjectInputStream ois = null;
PrivateKey privateKey = null;
try
{
fis = new FileInputStream(new File(fileName));
ois = new ObjectInputStream(fis);
BigInteger modulus = (BigInteger) ois.readObject();
BigInteger exponent = (BigInteger) ois.readObject();
//Get Public Key
RSAPrivateKeySpec rsaPrivateKeySpec = new RSAPrivateKeySpec(modulus, exponent);
KeyFactory fact = KeyFactory.getInstance("RSA");
privateKey = fact.generatePrivate(rsaPrivateKeySpec);
return privateKey;
}
catch (IOException e)
{
e.printStackTrace();
}
catch (ClassNotFoundException e)
{
e.printStackTrace();
}
catch (NoSuchAlgorithmException e)
{
e.printStackTrace();
}
catch (InvalidKeySpecException e)
{
e.printStackTrace();
}
finally
{
if (ois != null)
{
ois.close();
if (fis != null)
{
fis.close();
}
}
}
return privateKey;
}
public byte[] encryptData(String data) throws IOException {
System.out.println("\n--ENCRYPTION STARTED--");
System.out.println("Data Before Encryption: " + data);
byte[] dataToEncrypt = data.getBytes();
byte[] encryptedData = null;
try
{
PublicKey pubKey = readPublicKeyFromFile(this.REAL_PUBLIC_PATH);
Cipher cipher = Cipher.getInstance("RSA");
cipher.init(Cipher.ENCRYPT_MODE, pubKey);
encryptedData = cipher.doFinal(dataToEncrypt);
System.out.println("Encrypted Data: " + encryptedData);
}
catch (IOException e)
{
e.printStackTrace();
}
catch (NoSuchAlgorithmException e)
{
e.printStackTrace();
}
catch (InvalidKeyException e)
{
e.printStackTrace();
}
catch (IllegalBlockSizeException e)
{
e.printStackTrace();
}
catch (BadPaddingException e)
{
e.printStackTrace();
}
catch (NoSuchPaddingException e)
{
e.printStackTrace();
}
System.out.println("--ENCRYPTION COMPLETED--");
return encryptedData;
}
public String decryptData(byte[] data) throws IOException {
System.out.println("\n--DECRYPTION STARTED--");
byte[] decryptedData = null;
String decData = "";
try
{
PrivateKey privateKey = readPrivateKeyFromFile(this.REAL_PRIVATE_PATH);
Cipher cipher = Cipher.getInstance("RSA");
cipher.init(Cipher.DECRYPT_MODE, privateKey);
decryptedData = cipher.doFinal(data);
decData = new String(decryptedData);
System.out.println("Decrypted Data: " + decData);
return decData;
}
catch (IOException e)
{
e.printStackTrace();
}
catch (NoSuchAlgorithmException e)
{
e.printStackTrace();
}
catch (NoSuchPaddingException e)
{
e.printStackTrace();
}
catch (InvalidKeyException e)
{
e.printStackTrace();
}
catch ( IllegalBlockSizeException e)
{
e.printStackTrace();
}
catch (BadPaddingException e)
{
e.printStackTrace();
}
System.out.println("--DECRYPTION COMPLETED--");
return decData;
}
}
Do your keys already exist before you run the program? if not, then getRealPath to a file that doesn't exist isn't going to work.
But that shouldn't matter because if you can access the files using private static final String PUBLIC_KEY_FILE, why not use that same path to read the files.
So instead of this:
PrivateKey privateKey = readPrivateKeyFromFile(this.REAL_PRIVATE_PATH);
Why not do this?
PrivateKey privateKey = readPrivateKeyFromFile(this.PRIVATE_KEY_FILE);
If you've sucessfully written to a file using PRIVATE_KEY_FILE path, you can also read from the same path.
I'm signing a CSR to an intermediate certificate, both of which were generated using OpenSSL. The signing code uses Java Bouncy Castle APIs, and the code successfully generates a cert. When inspecting the cert, everything appears fine. The issuer and other data show up correctly in the dump.
However, when executing an openssl verify command, it fails with:
error 20 at 0 depth lookup:unable to get local issuer certificate
Signing an OpenSSL generated CSR to this same intermediate certificate verifies correctly.
The verify is successful when checked with the Java code:
cert.verify(cacert.getPublicKey())
-----BEGIN CERTIFICATE-----
MIIDEjCCArmgAwIBAgIFAJl/JBYwCgYIKoZIzj0EAwIwdTETMBEGA1UEDRMKMTUw
MzkxNzkxNDEVMBMGA1UEAwwMcGh5enpsaXRlLTAxMQ4wDAYDVQQLDAVQaHl6ejEd
MBsGA1UECgwUTWltb3NhIE5ldHdvcmtzLCBJbmMxCzAJBgNVBAgMAkNBMQswCQYD
VQQGEwJVUzAeFw0xNzA4MzAwMDA4MzhaFw0yNzAzMzEwMDA4MzhaMIG8Me0wGwYD
VQQKExRNaW1vc2EgTmV0d39ya3MsIEluYzEjMCEGA2UEAxMaMDEyMzcyOEI4MDAw
MTAwMTA3QkM0RkREQUMxEzARBgNVBAUTCjMwNzE1NDE4MjIxGjAYBgNVBCoTETIw
OmI1OmM2OjBmOmQ7OjNiMRowGAYDVQQEExEyMDpiNTpjNjowZjpkNjozETEaMBgG
A1UEKRMRMjA5YjU6YzY6MGY6ZDY6M2MxDTALBgNVBAwTBDMzMzkwWTATBgcqhkjO
PQIBBggqhkjOPQMBBwNCAARUdhMYLbb94GlWSh8b01lVfKL7+6sCw7hZdiMy9JIF
YBnTjLyGm1HjoRKl6ItuEzjdNFXMnFlMMuCbUTsij4L2o4HtMIHqMAwGA1UdEwQF
MAMBAf8wHQYDVR0OBBYEFPjbF9wIOB3uq2C7Yf6l8iMSU7SDMIGlBgNVHSMEgZ0w
gZqAFAshdhvN+xIrKpHeFG4o/TrJt6i/oXykejB4MQswCQYDVQQGEwJVUzELMAkG
A1UECBMCQ0ExHTAbBgNVBAoTFE1pbW9zYSBOZXR3b3JrcywgSW5jMQ4wDAYDVQQL
EwVQaHl6ejEYMBYGA1UEAxMPaW50ZXJjZWRpYRXlMTMzMRMwEQYDVQQNEwoxNDEy
OTU0Nzk1ggQFoABWMBMGA1UdEQQMMAqICCsGAQQBgtJcMAoGCCqGSM49BAMCA0cA
MEQCIFK2FycAFextGiAQPozuT2LFR/AtPDHpGyXn6z3ccUCVAiBFkwn/YBVz5yof
r5YHxgoz0LIJ+XUqLACNTHJhHstDCA==
-----END CERTIFICATE-----
public static X509Certificate certFromFile(String path) {
X509Certificate cert;
try {
CertificateFactory fact = CertificateFactory.getInstance("X.509");
FileInputStream is = new FileInputStream(path);
cert = (X509Certificate) fact.generateCertificate(is);
} catch (CertificateException | FileNotFoundException e) {
String error = e.getMessage();
System.err.println(error);
return null;
}
return cert;
}
public static String DumpCert(X509Certificate cert) {
ByteArrayOutputStream out = new ByteArrayOutputStream();
try {
out.write("-----BEGIN CERTIFICATE-----\n".getBytes());
out.write(Base64.encode(cert.getEncoded()));
out.write("\n-----END CERTIFICATE-----\n".getBytes());
out.close();
} catch (IOException | CertificateEncodingException e) {
System.out.println(e.getMessage());
}
String certpem = null;
try {
certpem = new String(out.toByteArray(), "ISO-8859-1");
} catch (UnsupportedEncodingException e) {
System.out.println(e.getMessage());
}
return certpem;
}
public static ContentSigner createSigner(PrivateKey privateKey) {
try {
ContentSigner sig = new JcaContentSignerBuilder("SHA256withECDSA").build(privateKey);
return sig;
} catch (Exception e) {
throw new RuntimeException("Could not create content signer.", e);
}
}
public static String signCSR(PKCS10CertificationRequest csr, GeneralName san, int validity,
X509Certificate cacert, KeyStore keystore, String alias) throws Exception {
Date from = new Date();
Date to = new Date(System.currentTimeMillis() + (validity * 86400000L));
PrivateKey cakey = null;
try {
cakey = (PrivateKey) keystore.getKey(alias, null);
} catch (Exception e) {
System.out.println(e.getMessage());
}
GeneralNames subjectAltNames = new GeneralNames(san);
org.bouncycastle.asn1.x500.X500Name csrSubject = csr.getSubject();
X500Name issuer = new X500Name(cacert.getSubjectX500Principal().getName());
X500Name caName = X500Name.getInstance(PrincipalUtil.getIssuerX509Principal(cacert).getEncoded());
GeneralNames gn = new GeneralNames(new GeneralName(caName));
BigInteger serial = new BigInteger(32, new SecureRandom());
SubjectPublicKeyInfo keyinfo = csr.getSubjectPublicKeyInfo();
DigestCalculator digCalc = new BcDigestCalculatorProvider().get(new AlgorithmIdentifier(OIWObjectIdentifiers.idSHA1));
X509ExtensionUtils x509ExtensionUtils = new X509ExtensionUtils(digCalc);
X509v3CertificateBuilder certgen = new X509v3CertificateBuilder(issuer, serial, from, to, csrSubject, keyinfo);
BigInteger serialcert = cacert.getSerialNumber();
Boolean buildCACert = true;
PublicKey caKey = cacert.getPublicKey();
SubjectPublicKeyInfo keyinfoCA = SubjectPublicKeyInfo.getInstance(caKey.getEncoded());
AuthorityKeyIdentifier akiMain = x509ExtensionUtils.createAuthorityKeyIdentifier(keyinfoCA);
AuthorityKeyIdentifier aki = new AuthorityKeyIdentifier(akiMain.getKeyIdentifier(), gn, serialcert);
certgen.addExtension(Extension.basicConstraints, false, new BasicConstraints(buildCACert));
certgen.addExtension(Extension.subjectKeyIdentifier, false, x509ExtensionUtils.createSubjectKeyIdentifier(keyinfo));
certgen.addExtension(Extension.authorityKeyIdentifier, false, aki);
certgen.addExtension(Extension.subjectAlternativeName, false, subjectAltNames);
ContentSigner signer = createSigner(cakey);
X509CertificateHolder holder = certgen.build(signer);
X509Certificate cert = null;
try {
CertificateFactory certFactory = CertificateFactory.getInstance("X.509");
InputStream in = new ByteArrayInputStream(holder.getEncoded());
cert = (X509Certificate) certFactory.generateCertificate(in);
} catch (CertificateException | IOException e) {
System.out.println(e.getMessage());
}
return DumpCert(cert);
}
public static GeneralName getSubjectAlternativeName(PKCS10CertificationRequest csr) {
org.bouncycastle.asn1.pkcs.Attribute[] certAttributes = csr.getAttributes();
for (org.bouncycastle.asn1.pkcs.Attribute attribute : certAttributes) {
if (attribute.getAttrType().equals(PKCSObjectIdentifiers.pkcs_9_at_extensionRequest)) {
Extensions extensions = Extensions.getInstance(attribute.getAttrValues().getObjectAt(0));
GeneralNames gns = GeneralNames.fromExtensions(extensions, Extension.subjectAlternativeName);
GeneralName name = gns.getNames()[0];
return name;
}
}
return null;
}
public static String PrepAndSignCSR(String raw_csr, String certPath, String keystore) {
KeyStore ks = null;
Object parsedObject = null;
String alias = "alias";
String s = null;
X509Certificate caCert = null;
StringReader sr = new StringReader(raw_csr);
PEMParser pemParser = new PEMParser(sr);
try {
parsedObject = pemParser.readObject();
System.out.println("PemParser returned : " + parsedObject);
} catch (IOException e) {
String error = e.getMessage();
System.err.println(error);
}
PKCS10CertificationRequest CSR = (PKCS10CertificationRequest) parsedObject;
caCert = certFromFile(certPath);
try {
ks = KeyStore.getInstance("ncipher.sworld", "nCipherKM");
FileInputStream in = new FileInputStream(keystore);
ks.load(in, null);
} catch (KeyStoreException |
NoSuchAlgorithmException |
CertificateException |
IOException |
NoSuchProviderException e) {
System.err.println(e.getMessage());
}
GeneralName san = getSubjectAlternativeName(CSR);
try {
String cert = signCSR(CSR, san, 3500, caCert, ks, alias);
return cert;
} catch (Exception e) {
String error = e.getMessage();
System.err.println(error);
}
return null;
}
public static void main(String[] args) {
.
.
.
String fini = PrepAndSignCSR(csr, caCertPath, keystore);
System.out.println(fini);
}
}
After some debug sessions within openssl, I found the issuer name was not matching. Replaced this line with getEncoded...
X500Name issuer = newX500Name(cacert.getSubjectX500Principal().getName());
X500Name issuer = X500Name.getInstance(cacert.getSubjectX500Principal().getEncoded());
The signed certs are now verifying with openssl verify command.
You're comparing apples and oranges.
java.security.cert.Certificate.verify() does nothing more than check the digital signature against the supplied public key.
openssl x509 verify checks the entire certificate chain, looks for the trust anchor, and verifies the digital signature and expiry dates of every certificate in the chain.
You need to specify the -CAfile or -CApath options to openssl. See the man page.
I know it's not secure to store a String into Keystore but I need it at this point. I am super new to cryptography and asymmetric in particular.
I am trying to store a String (and the private key) in the keystore using RSA algorithm. This is what I did so far and it worked but is this the easiest way to do it?
NOTE 1: I support only API 21 and newer so should I use keystore or keychain instead?
NOTE 2: It does not work on API 23 M it give an error when casting the private key to RSAPrivateKey
public static final String TAG = KeyStoreManager.class.getName();
static final String CIPHER_TYPE = "RSA/ECB/PKCS1Padding";
static final String CIPHER_PROVIDER = "AndroidOpenSSL";
public static final String PHRASE_ALIAS = "phrase";
public static final String ANDROID_KEY_STORE = "AndroidKeyStore";
public static final String MIHAIL_GUTAN_X500 = "CN=some name";
public static boolean setKeyStoreString(String fileName, String strToStore, String alias, Context context) {
try {
KeyStore keyStore = KeyStore.getInstance(ANDROID_KEY_STORE);
keyStore.load(null);
int nBefore = keyStore.size();
// Create the keys if necessary
if (!keyStore.containsAlias(alias)) {
Calendar notBefore = Calendar.getInstance();
Calendar notAfter = Calendar.getInstance();
notAfter.add(Calendar.YEAR, 1);
KeyPairGenerator generator = KeyPairGenerator.getInstance(
KeyProperties.KEY_ALGORITHM_RSA, ANDROID_KEY_STORE);
KeyPairGeneratorSpec spec = new KeyPairGeneratorSpec.Builder(context)
.setAlias(alias)
.setKeyType(KeyProperties.KEY_ALGORITHM_RSA)
.setKeySize(2048)
.setSubject(new X500Principal(MIHAIL_GUTAN_X500))
.setSerialNumber(BigInteger.ONE)
.setStartDate(notBefore.getTime())
.setEndDate(notAfter.getTime())
.build();
generator.initialize(spec);
KeyPair keyPair = generator.generateKeyPair(); // needs to be here
Log.v(TAG, "The keypair" + keyPair.toString());
}
int nAfter = keyStore.size();
Log.v(TAG, "Before = " + nBefore + " After = " + nAfter);
// Retrieve the keys
KeyStore.PrivateKeyEntry privateKeyEntry = (KeyStore.PrivateKeyEntry) keyStore.getEntry(alias, null);
RSAPrivateKey privateKey = (RSAPrivateKey) privateKeyEntry.getPrivateKey();
RSAPublicKey publicKey = (RSAPublicKey) privateKeyEntry.getCertificate().getPublicKey();
Log.v(TAG, "private key = " + privateKey.toString());
Log.v(TAG, "public key = " + publicKey.toString());
// Encrypt the text
String dataDirectory = context.getApplicationInfo().dataDir;
String filesDirectory = context.getFilesDir().getAbsolutePath();
String encryptedDataFilePath = filesDirectory + File.separator + fileName;
Log.v(TAG, "strPhrase = " + strToStore);
Log.v(TAG, "dataDirectory = " + dataDirectory);
Log.v(TAG, "filesDirectory = " + filesDirectory);
Log.v(TAG, "encryptedDataFilePath = " + encryptedDataFilePath);
Cipher inCipher = Cipher.getInstance(CIPHER_TYPE, CIPHER_PROVIDER);
inCipher.init(Cipher.ENCRYPT_MODE, publicKey);
CipherOutputStream cipherOutputStream =
new CipherOutputStream(
new FileOutputStream(encryptedDataFilePath), inCipher);
cipherOutputStream.write(strToStore.getBytes("UTF-8"));
cipherOutputStream.close();
return true;
} catch (NoSuchAlgorithmException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (NoSuchProviderException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (InvalidAlgorithmParameterException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (KeyStoreException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (CertificateException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (IOException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (UnrecoverableEntryException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (NoSuchPaddingException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (InvalidKeyException e) {
Log.e(TAG, Log.getStackTraceString(e));
} catch (UnsupportedOperationException e) {
Log.e(TAG, Log.getStackTraceString(e));
}
return false;
}
then I retrieve the string:
public static String getKeyStoreString(String fileName, String alias, Context context) {
KeyStore keyStore;
String recoveredSecret = "";
String filesDirectory = context.getFilesDir().getAbsolutePath();
String encryptedDataFilePath = filesDirectory + File.separator + fileName;
try {
keyStore = KeyStore.getInstance(ANDROID_KEY_STORE);
keyStore.load(null);
// Retrieve the keys
KeyStore.PrivateKeyEntry privateKeyEntry = (KeyStore.PrivateKeyEntry)
keyStore.getEntry(alias, null);
RSAPrivateKey privateKey = (RSAPrivateKey) privateKeyEntry.getPrivateKey();
Cipher outCipher = Cipher.getInstance(CIPHER_TYPE, CIPHER_PROVIDER);
outCipher.init(Cipher.DECRYPT_MODE, privateKey);
CipherInputStream cipherInputStream = new CipherInputStream(
new FileInputStream(encryptedDataFilePath), outCipher);
byte[] roundTrippedBytes = new byte[1000];
int index = 0;
int nextByte;
while ((nextByte = cipherInputStream.read()) != -1) {
roundTrippedBytes[index] = (byte) nextByte;
index++;
}
recoveredSecret = new String(roundTrippedBytes, 0, index, "UTF-8");
Log.e(TAG, "round tripped string = " + recoveredSecret);
} catch (KeyStoreException e) {
e.printStackTrace();
} catch (UnrecoverableEntryException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (CertificateException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} catch (NoSuchProviderException e) {
e.printStackTrace();
} catch (NoSuchPaddingException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
} catch (NullPointerException e) {
e.printStackTrace();
}
Log.e(TAG, "recovered: " + recoveredSecret);
return recoveredSecret;
}
I am attempting to implement HMAC using SHA-1 as the base. Using SHA-1 algorithm from bouncy castle, and implement the HMAC computation. Also to use SHA-1 to hash the input password to get the key for the HMAC algorithm. I've been trying to do this for a few hours but I really have a poor understanding of HMAC. If anyone has any tips on how to do this it would be appreciated. My code below is my implementation of SHA1, via a library function call, I'm essentially just trying to implement it with HMAC.
public class HMACSHA1 {
static byte[] password;
static byte[] fileName = null;
static byte[] input = new byte[16];
static String File;
public static void main(String[] args) {
Security.addProvider(Security.getProvider("BC"));
if(args.length != 2){
System.out.println("Invalid input");
System.exit(-1);
}
File = args[1];
try {
password = args[0].getBytes("UTF-8");
} catch (UnsupportedEncodingException e) {
// TODO Auto-generated catch block
e.printStackTrace();
System.out.println("Unable to read password");
System.exit(-1);
}
InputStream inputstream = null;
try {
inputstream = new FileInputStream(File);
} catch (FileNotFoundException e2) {
e2.printStackTrace();
System.out.println("No input found\n");
System.exit(-1);
}
MessageDigest hash = null;
MessageDigest key = null;
try {
hash = MessageDigest.getInstance("SHA-1", "BC");
key = MessageDigest.getInstance("SHA-1", "BC");
} catch (NoSuchAlgorithmException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (NoSuchProviderException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
key.update(password);
byte[] HMACKey = key.digest();
byte[] digest = null;
int reader = 0;
while (reader != -1){
try {
reader = inputstream.read(input);
} catch (IOException e2) {
e2.printStackTrace();
}
hash.update(input);
digest = hash.digest();
System.out.println(new String(Hex.encode(digest)));
}
}
}
I am not familiar with Bouncy Castle, but you can work out the HMAC-SHA1 without external libraries using only what is provided with Java SE:
import java.security.NoSuchAlgorithmException;
import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec;
public String getHmacSha1(byte[] key, byte[] input) throws NoSuchAlgorithmException {
SecretKeySpec signingKey = new SecretKeySpec(key, "HmacSHA1");
Mac mac = null;
mac = Mac.getInstance("HmacSHA1");
mac.init(signingKey);
byte[] digest = mac.doFinal(input);
return Hex.encodeHexString(digest);
}
This is available since Java 1.4 according to the API.
i am using GPG4Win for encrypt the file and then BouncyCastle for decrypt file but code is not working
suppose i use BouncyCastle code for encrypt file and then use BouncyCastle decryption code its able to decrypt file and GPG4win also able to decrypt the file.
all code in java
suppose file is encrypted by BouncyCastle its decrypt by GPG4win and BouncyCastle
org.bouncycastle.openpgp.PGPException: Exception starting decryption
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 com.pgp.util.KeyBasedFileProcessorUtil.decryptFile(KeyBasedFileProcessorUtil.java:183)
at com.pgp.encrypt.PGPDecryption.main(PGPDecryption.java:49)
Caused by: java.security.InvalidKeyException: Illegal key size
at javax.crypto.Cipher.a(DashoA13*..)
at javax.crypto.Cipher.init(DashoA13*..)
at javax.crypto.Cipher.init(DashoA13*..)
... 5 more
org.bouncycastle.openpgp.PGPException: Exception starting decryption
java.security.InvalidKeyException: Illegal key size
at javax.crypto.Cipher.a(DashoA13*..)
at javax.crypto.Cipher.init(DashoA13*..)
at javax.crypto.Cipher.init(DashoA13*..)
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 com.pgp.util.KeyBasedFileProcessorUtil.decryptFile(KeyBasedFileProcessorUtil.java:183)
at com.pgp.encrypt.PGPDecryption.main(PGPDecryption.java:49)
my code is
import org.bouncycastle.bcpg.ArmoredOutputStream;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import org.bouncycastle.openpgp.PGPCompressedData;
import org.bouncycastle.openpgp.PGPCompressedDataGenerator;
import org.bouncycastle.openpgp.PGPEncryptedData;
import org.bouncycastle.openpgp.PGPEncryptedDataGenerator;
import org.bouncycastle.openpgp.PGPEncryptedDataList;
import org.bouncycastle.openpgp.PGPException;
import org.bouncycastle.openpgp.PGPLiteralData;
import org.bouncycastle.openpgp.PGPObjectFactory;
import org.bouncycastle.openpgp.PGPOnePassSignatureList;
import org.bouncycastle.openpgp.PGPPrivateKey;
import org.bouncycastle.openpgp.PGPPublicKey;
import org.bouncycastle.openpgp.PGPPublicKeyEncryptedData;
import org.bouncycastle.openpgp.PGPPublicKeyRing;
import org.bouncycastle.openpgp.PGPPublicKeyRingCollection;
import org.bouncycastle.openpgp.PGPSecretKey;
import org.bouncycastle.openpgp.PGPSecretKeyRingCollection;
import org.bouncycastle.openpgp.PGPUtil;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.security.NoSuchProviderException;
import java.security.SecureRandom;
import java.security.Security;
import java.util.Iterator;
import java.io.*;
/**
* A simple utility class that encrypts/decrypts public key based
* encryption files.
* <p>
* To encrypt a file: KeyBasedFileProcessor -e [-a|-ai] fileName publicKeyFile.<br>
* If -a is specified the output file will be "ascii-armored".
* If -i is specified the output file will be have integrity checking added.
* <p>
* To decrypt: KeyBasedFileProcessor -d fileName secretKeyFile passPhrase.
* <p>
* Note 1: this example will silently overwrite files, nor does it pay any attention to
* the specification of "_CONSOLE" in the filename. It also expects that a single pass phrase
* will have been used.
* <p>
* Note 2: if an empty file name has been specified in the literal data object contained in the
* encrypted packet a file with the name filename.out will be generated in the current working directory.
*/
public class KeyBasedFileProcessorUtil
{
/**
* A simple routine that opens a key ring file and loads the first available key suitable for
* encryption.
*
* #param in
* #return
* #throws IOException
* #throws PGPException
*/
public static PGPPublicKey readPublicKey(
InputStream in)
throws IOException, PGPException
{
in = PGPUtil.getDecoderStream(in);
PGPPublicKeyRingCollection pgpPub = new PGPPublicKeyRingCollection(in);
//
// we just loop through the collection till we find a key suitable for encryption, in the real
// world you would probably want to be a bit smarter about this.
//
//
// iterate through the key rings.
//
Iterator rIt = pgpPub.getKeyRings();
while (rIt.hasNext())
{
PGPPublicKeyRing kRing = (PGPPublicKeyRing)rIt.next();
Iterator kIt = kRing.getPublicKeys();
while (kIt.hasNext())
{
PGPPublicKey k = (PGPPublicKey)kIt.next();
if (k.isEncryptionKey())
{
return k;
}
}
}
throw new IllegalArgumentException("Can't find encryption key in key ring.");
}
/**
* Search a secret key ring collection for a secret key corresponding to
* keyID if it exists.
*
* #param pgpSec a secret key ring collection.
* #param keyID keyID we want.
* #param pass passphrase to decrypt secret key with.
* #return
* #throws PGPException
* #throws NoSuchProviderException
*/
public static PGPPrivateKey findSecretKey(
PGPSecretKeyRingCollection pgpSec,
long keyID,
char[] pass)
throws PGPException, NoSuchProviderException
{
PGPSecretKey pgpSecKey = pgpSec.getSecretKey(keyID);
if (pgpSecKey == null)
{
return null;
}
return pgpSecKey.extractPrivateKey(pass, "BC");
}
/**
* decrypt the passed in message stream
*/
public static void decryptFile(
InputStream in,
InputStream keyIn,
char[] passwd,
String defaultFileName)
throws Exception
{
System.out.println("File Decrypting");
System.out.println("File absulatePath :-");
in = PGPUtil.getDecoderStream(in);
try
{
PGPObjectFactory pgpF = new PGPObjectFactory(in);
PGPEncryptedDataList enc;
Object o = pgpF.nextObject();
//
// the first object might be a PGP marker packet.
//
if (o instanceof PGPEncryptedDataList)
{
enc = (PGPEncryptedDataList)o;
}
else
{
enc = (PGPEncryptedDataList)pgpF.nextObject();
}
//
// find the secret key
//
System.out.println("find the secret key");
Iterator it = enc.getEncryptedDataObjects();
PGPPrivateKey sKey = null;
PGPPublicKeyEncryptedData pbe = null;
PGPSecretKeyRingCollection pgpSec = new PGPSecretKeyRingCollection(
PGPUtil.getDecoderStream(keyIn));
while (sKey == null && it.hasNext())
{
pbe = (PGPPublicKeyEncryptedData)it.next();
sKey = findSecretKey(pgpSec, pbe.getKeyID(), passwd);
}
if (sKey == null)
{
System.out.println("--------------------");
System.out.println("secret key for message not found.");
throw new IllegalArgumentException("secret key for message not found.");
}
System.out.println("secret key for message found.");
InputStream clear = pbe.getDataStream(sKey, "BC");
PGPObjectFactory plainFact = new PGPObjectFactory(clear);
Object message = plainFact.nextObject();
if (message instanceof PGPCompressedData)
{
PGPCompressedData cData = (PGPCompressedData)message;
PGPObjectFactory pgpFact = new PGPObjectFactory(cData.getDataStream());
message = pgpFact.nextObject();
}
if (message instanceof PGPLiteralData)
{
PGPLiteralData ld = (PGPLiteralData)message;
String outFileName = ld.getFileName();
if (ld.getFileName().length() == 0)
{
outFileName = defaultFileName;
}
InputStream unc = ld.getInputStream();
int ch;
while ((ch = unc.read()) >= 0)
{
fOut.write(ch);
}
}
else if (message instanceof PGPOnePassSignatureList)
{
System.out.println("encrypted message contains a signed message - not literal data.");
throw new PGPException("encrypted message contains a signed message - not literal data.");
}
else
{
throw new PGPException("message is not a simple encrypted file - type unknown.");
}
if (pbe.isIntegrityProtected())
{
if (!pbe.verify())
{
System.err.println("message failed integrity check");
}
else
{
System.err.println("message integrity check passed");
}
}
else
{
System.err.println("no message integrity check");
}
}
catch (PGPException e)
{
e.printStackTrace();
System.err.println(e);
if (e.getUnderlyingException() != null)
{
e.getUnderlyingException().printStackTrace();
}
}
}
/*
private static void decryptFile(
InputStream in,
InputStream keyIn,
char[] passwd)
throws Exception
{
in = PGPUtil.getDecoderStream(in);
try
{
PGPObjectFactory pgpF = new PGPObjectFactory(in);
PGPEncryptedDataList enc;
Object o = pgpF.nextObject();
//
// the first object might be a PGP marker packet.
//
if (o instanceof PGPEncryptedDataList)
{
enc = (PGPEncryptedDataList)o;
}
else
{
enc = (PGPEncryptedDataList)pgpF.nextObject();
}
//
// find the secret key
//
Iterator it = enc.getEncryptedDataObjects();
PGPPrivateKey sKey = null;
PGPPublicKeyEncryptedData pbe = null;
while (sKey == null && it.hasNext())
{
pbe = (PGPPublicKeyEncryptedData)it.next();
sKey = findSecretKey(keyIn, pbe.getKeyID(), passwd);
}
if (sKey == null)
{
throw new IllegalArgumentException("secret key for message not found.");
}
InputStream clear = pbe.getDataStream(sKey, "BC");
PGPObjectFactory plainFact = new PGPObjectFactory(clear);
PGPCompressedData cData = (PGPCompressedData)plainFact.nextObject();
InputStream compressedStream = new BufferedInputStream(cData.getDataStream());
PGPObjectFactory pgpFact = new PGPObjectFactory(compressedStream);
Object message = pgpFact.nextObject();
if (message instanceof PGPLiteralData)
{
PGPLiteralData ld = (PGPLiteralData)message;
FileOutputStream fOut = new FileOutputStream(ld.getFileName());
BufferedOutputStream bOut = new BufferedOutputStream(fOut);
InputStream unc = ld.getInputStream();
int ch;
while ((ch = unc.read()) >= 0)
{
bOut.write(ch);
}
bOut.close();
}
else if (message instanceof PGPOnePassSignatureList)
{
throw new PGPException("encrypted message contains a signed message - not literal data.");
}
else
{
throw new PGPException("message is not a simple encrypted file - type unknown.");
}
if (pbe.isIntegrityProtected())
{
if (!pbe.verify())
{
System.err.println("message failed integrity check");
}
else
{
System.err.println("message integrity check passed");
}
}
else
{
System.err.println("no message integrity check");
}
}
catch (PGPException e)
{
System.err.println(e);
if (e.getUnderlyingException() != null)
{
e.getUnderlyingException().printStackTrace();
}
}
}
*/
public static void encryptFile(
OutputStream out,
String fileName,
PGPPublicKey encKey,
boolean armor,
boolean withIntegrityCheck)
throws IOException, NoSuchProviderException
{
if (armor)
{
out = new ArmoredOutputStream(out);
}
try
{
ByteArrayOutputStream bOut = new ByteArrayOutputStream();
PGPCompressedDataGenerator comData = new PGPCompressedDataGenerator(1);
PGPUtil.writeFileToLiteralData(comData.open(bOut), PGPLiteralData.BINARY, new File(fileName));
comData.close();
PGPEncryptedDataGenerator cPk = new PGPEncryptedDataGenerator(PGPEncryptedData.CAST5, withIntegrityCheck, new SecureRandom(), "BC");
cPk.addMethod(encKey);
byte[] bytes = bOut.toByteArray();
OutputStream cOut = cPk.open(out, bytes.length);
cOut.write(bytes);
cOut.close();
out.close();
}
catch (PGPException e)
{
System.err.println(e);
if (e.getUnderlyingException() != null)
{
e.getUnderlyingException().printStackTrace();
}
}
}
public static void encryptFile1(
OutputStream out,
String fileName,
PGPPrivateKey encKey,
boolean armor,
boolean withIntegrityCheck)
throws IOException, NoSuchProviderException
{
if (armor)
{
out = new ArmoredOutputStream(out);
}
try
{
ByteArrayOutputStream bOut = new ByteArrayOutputStream();
PGPCompressedDataGenerator comData = new PGPCompressedDataGenerator(1);
PGPUtil.writeFileToLiteralData(comData.open(bOut), PGPLiteralData.BINARY, new File(fileName));
comData.close();
PGPEncryptedDataGenerator cPk = new PGPEncryptedDataGenerator(PGPEncryptedData.CAST5, withIntegrityCheck, new SecureRandom(), "BC");
cPk.addMethod((PGPPublicKey) encKey.getKey());
byte[] bytes = bOut.toByteArray();
OutputStream cOut = cPk.open(out, bytes.length);
cOut.write(bytes);
cOut.close();
out.close();
}
catch (PGPException e)
{
System.err.println(e);
if (e.getUnderlyingException() != null)
{
e.getUnderlyingException().printStackTrace();
}
}
}
}
Decryption classs
public class PGPDecryption {
/**
*
* #param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
Properties prop=new Properties();
try {
prop.load(new FileInputStream("config.prop"));
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
FileInputStream keyOut=null;
FileOutputStream out =null;
Security.addProvider(new BouncyCastleProvider());
try {
System.out.println(prop.getProperty(Constant.PRIVATE_KEY));
keyOut = new FileInputStream(prop.getProperty(Constant.PRIVATE_KEY));
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
try {
KeyBasedFileProcessorUtil.decryptFile(new FileInputStream(prop.getProperty(Constant.ENCRYPT_FILE_PATH)), keyOut, prop.getProperty(Constant.PRIVATE_FILE_PASS).toCharArray(), prop.getProperty(Constant.DECRYPT_FILE_OUTPUT_PATH));
System.out.println("Decrypted File created with name of "+prop.getProperty(Constant.DECRYPT_FILE_OUTPUT_PATH));
} catch (NoSuchProviderException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
Encryption class
public class PGPEncryption {
public static void main(String[] args) {
// TODO Auto-generated method stub
Properties prop=new Properties();
try {
File f=new File("config.prop");
System.out.println(f.getAbsolutePath());
prop.load(new FileInputStream(f));
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
FileInputStream keyIn=null;
FileOutputStream out =null;
Security.addProvider(new BouncyCastleProvider());
try {
System.out.println(prop.getProperty(Constant.PUBLIC_KEY));
keyIn = new FileInputStream(prop.getProperty(Constant.PUBLIC_KEY));
System.out.println("Encrypt File Path :-"+prop.getProperty(Constant.ENCRYPT_FILE_PATH));
out= new FileOutputStream(new File(prop.getProperty(Constant.ENCRYPT_FILE_PATH)));
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
boolean armor = false;
boolean integrityCheck = false;
PGPPublicKey pubKey = null;
try {
System.out.println("Reading public key.........");
pubKey = KeyBasedFileProcessorUtil.readPublicKey(keyIn);
System.out.println("Public Key found...........");
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (PGPException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
try {
System.out.println("File Encrypting............");
KeyBasedFileProcessorUtil.encryptFile(out, prop.getProperty(Constant.SOURCE_FILE_PATH), pubKey, armor, integrityCheck);
System.out.println("Encrypted File created with name of "+prop.getProperty(Constant.ENCRYPT_FILE_PATH));
} catch (NoSuchProviderException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
please help me i want to decrypt the file those encrypted by GPG4win
To solve this problem now, i am using Cryptix OpenPGP.
its working properly without any error or exception.
link to download Cryptix lib
http://www.cryptix.org/
in that download two project library
Cryptix OpenPGP
Cryptix JCE