aboutsummaryrefslogtreecommitdiffstats
path: root/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp
diff options
context:
space:
mode:
Diffstat (limited to 'OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp')
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpDecryptVerifyOperation.java33
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpSignEncryptOperation.java9
-rw-r--r--OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/UncachedKeyRing.java37
3 files changed, 54 insertions, 25 deletions
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpDecryptVerifyOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpDecryptVerifyOperation.java
index 0709d4f62..2d28f70e0 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpDecryptVerifyOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpDecryptVerifyOperation.java
@@ -346,14 +346,14 @@ public class PgpDecryptVerifyOperation extends BaseOperation<PgpDecryptVerifyInp
if (!"".equals(originalFilename)) {
log.add(LogType.MSG_DC_CLEAR_META_FILE, indent + 1, originalFilename);
}
- log.add(LogType.MSG_DC_CLEAR_META_MIME, indent + 1,
- mimeType);
log.add(LogType.MSG_DC_CLEAR_META_TIME, indent + 1,
new Date(literalData.getModificationTime().getTime()).toString());
// return here if we want to decrypt the metadata only
if (input.isDecryptMetadataOnly()) {
+ log.add(LogType.MSG_DC_CLEAR_META_MIME, indent + 1, mimeType);
+
// this operation skips the entire stream to find the data length!
Long originalSize = literalData.findDataLength();
@@ -387,6 +387,7 @@ public class PgpDecryptVerifyOperation extends BaseOperation<PgpDecryptVerifyInp
long wholeSize = 0; // TODO inputData.getSize() - inputData.getStreamPosition();
int length;
byte[] buffer = new byte[1 << 16];
+ byte[] firstBytes = new byte[48];
while ((length = dataIn.read(buffer)) > 0) {
// Log.d(Constants.TAG, "read bytes: " + length);
if (out != null) {
@@ -396,6 +397,11 @@ public class PgpDecryptVerifyOperation extends BaseOperation<PgpDecryptVerifyInp
// update signature buffer if signature is also present
signatureChecker.updateSignatureData(buffer, 0, length);
+ // note down first couple of bytes for "magic bytes" file type detection
+ if (alreadyWritten == 0) {
+ System.arraycopy(buffer, 0, firstBytes, 0, length > firstBytes.length ? firstBytes.length : length);
+ }
+
alreadyWritten += length;
// noinspection ConstantConditions, TODO progress
if (wholeSize > 0) {
@@ -408,6 +414,17 @@ public class PgpDecryptVerifyOperation extends BaseOperation<PgpDecryptVerifyInp
}
}
+ // special treatment to detect pgp mime types
+ if (matchesPrefix(firstBytes, "-----BEGIN PGP PUBLIC KEY BLOCK-----")
+ || matchesPrefix(firstBytes, "-----BEGIN PGP PRIVATE KEY BLOCK-----")) {
+ mimeType = "application/pgp-keys";
+ } else if (matchesPrefix(firstBytes, "-----BEGIN PGP MESSAGE-----")) {
+ // this is NOT pgp/encrypted, see RFC 3156!
+ mimeType = "application/pgp-message";
+ }
+
+ log.add(LogType.MSG_DC_CLEAR_META_MIME, indent + 1, mimeType);
+
metadata = new OpenPgpMetadata(
originalFilename, mimeType, literalData.getModificationTime().getTime(), alreadyWritten, charset);
@@ -940,4 +957,16 @@ public class PgpDecryptVerifyOperation extends BaseOperation<PgpDecryptVerifyInp
return nl.getBytes();
}
+ /// Convenience method - Trivially checks if a byte array matches the bytes of a plain text string
+ // Assumes data.length >= needle.length()
+ static boolean matchesPrefix(byte[] data, String needle) {
+ byte[] needleBytes = needle.getBytes();
+ for (int i = 0; i < needle.length(); i++) {
+ if (data[i] != needleBytes[i]) {
+ return false;
+ }
+ }
+ return true;
+ }
+
}
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpSignEncryptOperation.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpSignEncryptOperation.java
index 406c64ae8..ecc190d97 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpSignEncryptOperation.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpSignEncryptOperation.java
@@ -53,6 +53,7 @@ import org.sufficientlysecure.keychain.util.Log;
import org.sufficientlysecure.keychain.util.Passphrase;
import org.sufficientlysecure.keychain.util.ProgressScaler;
+import java.io.BufferedInputStream;
import java.io.BufferedOutputStream;
import java.io.BufferedReader;
import java.io.ByteArrayOutputStream;
@@ -361,7 +362,7 @@ public class PgpSignEncryptOperation extends BaseOperation {
long alreadyWritten = 0;
int length;
byte[] buffer = new byte[1 << 16];
- InputStream in = inputData.getInputStream();
+ InputStream in = new BufferedInputStream(inputData.getInputStream());
while ((length = in.read(buffer)) > 0) {
pOut.write(buffer, 0, length);
@@ -389,7 +390,7 @@ public class PgpSignEncryptOperation extends BaseOperation {
// write -----BEGIN PGP SIGNED MESSAGE-----
armorOut.beginClearText(input.getSignatureHashAlgorithm());
- InputStream in = inputData.getInputStream();
+ InputStream in = new BufferedInputStream(inputData.getInputStream());
final BufferedReader reader = new BufferedReader(new InputStreamReader(in));
// update signature buffer with first line
@@ -421,7 +422,7 @@ public class PgpSignEncryptOperation extends BaseOperation {
updateProgress(R.string.progress_signing, 8, 100);
log.add(LogType.MSG_PSE_SIGNING_DETACHED, indent);
- InputStream in = inputData.getInputStream();
+ InputStream in = new BufferedInputStream(inputData.getInputStream());
// handle output stream separately for detached signatures
detachedByteOut = new ByteArrayOutputStream();
@@ -458,7 +459,7 @@ public class PgpSignEncryptOperation extends BaseOperation {
updateProgress(R.string.progress_signing, 8, 100);
log.add(LogType.MSG_PSE_SIGNING, indent);
- InputStream in = inputData.getInputStream();
+ InputStream in = new BufferedInputStream(inputData.getInputStream());
if (enableCompression) {
compressGen = new PGPCompressedDataGenerator(input.getCompressionAlgorithm());
diff --git a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/UncachedKeyRing.java b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/UncachedKeyRing.java
index 96778649c..c967a5abc 100644
--- a/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/UncachedKeyRing.java
+++ b/OpenKeychain/src/main/java/org/sufficientlysecure/keychain/pgp/UncachedKeyRing.java
@@ -18,6 +18,23 @@
package org.sufficientlysecure.keychain.pgp;
+
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Calendar;
+import java.util.Comparator;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.Set;
+import java.util.TimeZone;
+import java.util.TreeSet;
+
import org.spongycastle.bcpg.ArmoredOutputStream;
import org.spongycastle.bcpg.PublicKeyAlgorithmTags;
import org.spongycastle.bcpg.SignatureSubpacketTags;
@@ -43,23 +60,6 @@ import org.sufficientlysecure.keychain.util.IterableIterator;
import org.sufficientlysecure.keychain.util.Log;
import org.sufficientlysecure.keychain.util.Utf8Util;
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.io.Serializable;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Calendar;
-import java.util.Comparator;
-import java.util.Date;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.Set;
-import java.util.TimeZone;
-import java.util.TreeSet;
-
/** Wrapper around PGPKeyRing class, to be constructed from bytes.
*
* This class and its relatives UncachedPublicKey and UncachedSecretKey are
@@ -78,8 +78,7 @@ import java.util.TreeSet;
* @see org.sufficientlysecure.keychain.pgp.UncachedSecretKey
*
*/
-@SuppressWarnings("unchecked")
-public class UncachedKeyRing implements Serializable {
+public class UncachedKeyRing {
final PGPKeyRing mRing;
final boolean mIsSecret;