From a39c73ca12dabba01412083afbf0b58dfb42a79e Mon Sep 17 00:00:00 2001 From: Ashley Hughes Date: Sat, 22 Feb 2014 15:29:19 +0000 Subject: [PATCH] first go at saving IDs correctly --- .../keychain/pgp/PgpKeyOperation.java | 74 ++++++++++++++++--- 1 file changed, 62 insertions(+), 12 deletions(-) diff --git a/OpenPGP-Keychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpKeyOperation.java b/OpenPGP-Keychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpKeyOperation.java index cc9384821..f3b289f66 100644 --- a/OpenPGP-Keychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpKeyOperation.java +++ b/OpenPGP-Keychain/src/main/java/org/sufficientlysecure/keychain/pgp/PgpKeyOperation.java @@ -28,6 +28,7 @@ import java.security.SignatureException; import java.util.ArrayList; import java.util.Date; import java.util.GregorianCalendar; +import java.util.Iterator; import java.util.TimeZone; import org.spongycastle.bcpg.CompressionAlgorithmTags; @@ -68,6 +69,7 @@ import org.sufficientlysecure.keychain.util.Primes; import org.sufficientlysecure.keychain.util.ProgressDialogUpdater; import android.content.Context; +import android.util.Pair; public class PgpKeyOperation { private final Context mContext; @@ -361,6 +363,21 @@ public class PgpKeyOperation { if (mKR == null) buildNewSecretKey(userIds, keys, keysExpiryDates, keysUsages, newPassPhrase, oldPassPhrase); //new Keyring + /* + IDs - + remove deleted ids + if the primary ID changed we need to: + remove all of the IDs from the keyring, saving their certifications + add them all in again, updating certs of IDs which have changed + else + remove changed IDs and add in with new certs + + Keys + remove deleted keys + if a key is modified, re-sign it + do we need to remove and add in? + */ + masterKey = mKR.getSecretKey(); PGPPublicKey masterPublicKey = masterKey.getPublicKey(); @@ -374,22 +391,55 @@ public class PgpKeyOperation { updateProgress(R.string.progress_certifying_master_key, 20, 100); + for (String delID : deletedIDs) { + masterPublicKey = PGPPublicKey.removeCertification(masterPublicKey, delID); + } + int user_id_index = 0; - for (String userId : userIds) { - if (!OriginalIDs.get(user_id_index).equals(userIds.get(user_id_index))) { - PGPContentSignerBuilder signerBuilder = new JcaPGPContentSignerBuilder( - masterPublicKey.getAlgorithm(), HashAlgorithmTags.SHA1) - .setProvider(Constants.BOUNCY_CASTLE_PROVIDER_NAME); - PGPSignatureGenerator sGen = new PGPSignatureGenerator(signerBuilder); + if (primaryIDChanged) { + ArrayList> sigList = new ArrayList>(); + for (String userId : userIds) { + String orig_id = OriginalIDs.get(user_id_index); + if (orig_id.equals(userId)) { + Iterator orig_sigs = masterPublicKey.getSignaturesForID(orig_id); //TODO: make sure this iterator only has signatures we are interested in + while (orig_sigs.hasNext()) { + PGPSignature orig_sig = orig_sigs.next(); + sigList.add(new Pair(orig_id, orig_sig)); + } + } else { + PGPContentSignerBuilder signerBuilder = new JcaPGPContentSignerBuilder( + masterPublicKey.getAlgorithm(), HashAlgorithmTags.SHA1) + .setProvider(Constants.BOUNCY_CASTLE_PROVIDER_NAME); + PGPSignatureGenerator sGen = new PGPSignatureGenerator(signerBuilder); - sGen.init(PGPSignature.POSITIVE_CERTIFICATION, masterPrivateKey); + sGen.init(PGPSignature.POSITIVE_CERTIFICATION, masterPrivateKey); - PGPSignature certification = sGen.generateCertification(userId, masterPublicKey); - - //masterPublicKey = PGPPublicKey.removeCertification(); - masterPublicKey = PGPPublicKey.addCertification(masterPublicKey, userId, certification); + PGPSignature certification = sGen.generateCertification(userId, masterPublicKey); + sigList.add(new Pair(userId, certification)); + } + masterPublicKey = PGPPublicKey.removeCertification(masterPublicKey, orig_id); + user_id_index++; + } + for (Pair to_add : sigList) { + masterPublicKey = PGPPublicKey.addCertification(masterPublicKey, to_add.first, to_add.second); + } + } else { + for (String userId : userIds) { + String orig_id = OriginalIDs.get(user_id_index); + if (!orig_id.equals(userId)) { + PGPContentSignerBuilder signerBuilder = new JcaPGPContentSignerBuilder( + masterPublicKey.getAlgorithm(), HashAlgorithmTags.SHA1) + .setProvider(Constants.BOUNCY_CASTLE_PROVIDER_NAME); + PGPSignatureGenerator sGen = new PGPSignatureGenerator(signerBuilder); + + sGen.init(PGPSignature.POSITIVE_CERTIFICATION, masterPrivateKey); + + PGPSignature certification = sGen.generateCertification(userId, masterPublicKey); + masterPublicKey = PGPPublicKey.removeCertification(masterPublicKey, orig_id); + masterPublicKey = PGPPublicKey.addCertification(masterPublicKey, userId, certification); + } + user_id_index++; } - user_id_index++; } PGPKeyPair masterKeyPair = new PGPKeyPair(masterPublicKey, masterPrivateKey);