Пример #1
0
 internal PgpSecretKey(
     SecretKeyPacket secret,
     PgpPublicKey pub)
 {
     this.secret = secret;
     this.pub    = pub;
 }
Пример #2
0
        public string SignText(string strMessage, ulong lSignatureKeyID, string strPassphrase)
        {
            SignaturePacket spSign = new SignaturePacket();

            strMessage = Radix64.TrimMessage(strMessage);

            TransportableSecretKey tskKey = skrKeyRing.Find(lSignatureKeyID);
            SecretKeyPacket        skpKey = tskKey.FindKey(AsymActions.Sign);

            spSign.HashAlgorithm      = HashAlgorithms.SHA1;
            spSign.Format             = PacketFormats.New;
            spSign.KeyID              = skpKey.PublicKey.KeyID;
            spSign.TimeCreated        = DateTime.Now;
            spSign.SignatureAlgorithm = skpKey.PublicKey.Algorithm;
            spSign.SignatureType      = SignatureTypes.TextSignature;
            spSign.Version            = SignaturePacketVersionNumbers.v4;

            byte[] bMessage = System.Text.Encoding.UTF8.GetBytes(strMessage);
            spSign.Sign(bMessage, skpKey, strPassphrase);
            byte[] bSignature   = spSign.Generate();
            string strSignature = Radix64.Encode(bSignature, true);
            string strFinal     = Armor.WrapCleartextSignature(strMessage, strSignature);

            return(strFinal);
        }
Пример #3
0
 internal PgpSecretKey(
     SecretKeyPacket	secret,
     PgpPublicKey	pub)
 {
     this.secret = secret;
     this.pub = pub;
 }
Пример #4
0
        /// <summary>
        /// Return a copy of the passed in secret key, encrypted using a new password
        /// and the passed in algorithm.
        /// </summary>
        /// <param name="key">The PgpSecretKey to be copied.</param>
        /// <param name="oldPassPhrase">The current password for the key.</param>
        /// <param name="newPassPhrase">The new password for the key.</param>
        /// <param name="newEncAlgorithm">The algorithm to be used for the encryption.</param>
        /// <param name="rand">Source of randomness.</param>
        public static PgpSecretKey CopyWithNewPassword(IPgpSecretKey key, char[] oldPassPhrase, char[] newPassPhrase, SymmetricKeyAlgorithmTag newEncAlgorithm, SecureRandom rand)
        {
            var rawKeyData = key.ExtractKeyData(oldPassPhrase);
            var s2KUsage   = key.SecretPacket.S2KUsage;

            byte[] iv  = null;
            S2k    s2K = null;

            byte[] keyData;

            if (newEncAlgorithm == SymmetricKeyAlgorithmTag.Null)
            {
                s2KUsage = SecretKeyPacket.UsageNone;
                if (key.SecretPacket.S2KUsage == SecretKeyPacket.UsageSha1)   // SHA-1 hash, need to rewrite Checksum
                {
                    keyData = new byte[rawKeyData.Length - 18];

                    Array.Copy(rawKeyData, 0, keyData, 0, keyData.Length - 2);

                    var check = Checksum(false, keyData, keyData.Length - 2);

                    keyData[keyData.Length - 2] = check[0];
                    keyData[keyData.Length - 1] = check[1];
                }
                else
                {
                    keyData = rawKeyData;
                }
            }
            else
            {
                try
                {
                    keyData = EncryptKeyData(rawKeyData, newEncAlgorithm, newPassPhrase, rand, out s2K, out iv);
                }
                catch (PgpException)
                {
                    throw;
                }
                catch (Exception e)
                {
                    throw new PgpException("Exception encrypting key", e);
                }
            }

            SecretKeyPacket secret;

            if (key.SecretPacket is SecretSubkeyPacket)
            {
                secret = new SecretSubkeyPacket(key.SecretPacket.PublicKeyPacket,
                                                newEncAlgorithm, s2KUsage, s2K, iv, keyData);
            }
            else
            {
                secret = new SecretKeyPacket(key.SecretPacket.PublicKeyPacket,
                                             newEncAlgorithm, s2KUsage, s2K, iv, keyData);
            }

            return(new PgpSecretKey(secret, key.PublicKey));
        }
Пример #5
0
        public void SignKeyBindingSignature(PublicKeyPacket pkpPrimaryKey, SecretKeyPacket skpPrimaryKey, string strPassphrase)
        {
            byte[] bSubKey = new byte[pkpSubkey.Body.Length + 3];
            bSubKey[0] = 0x99;
            bSubKey[1] = (byte)((pkpSubkey.Body.Length >> 8) & 0xFF);
            bSubKey[2] = (byte)(pkpSubkey.Body.Length & 0xFF);
            Array.Copy(pkpSubkey.Body, 0, bSubKey, 3, pkpSubkey.Body.Length);

            byte[] bPrimaryKey = new byte[pkpPrimaryKey.Body.Length + 3];
            bPrimaryKey[0] = 0x99;
            bPrimaryKey[1] = (byte)((pkpPrimaryKey.Body.Length >> 8) & 0xFF);
            bPrimaryKey[2] = (byte)(pkpPrimaryKey.Body.Length & 0xFF);
            Array.Copy(pkpPrimaryKey.Body, 0, bPrimaryKey, 3, pkpPrimaryKey.Body.Length);

            byte[] bData = new byte[bPrimaryKey.Length + bSubKey.Length];
            Array.Copy(bSubKey, 0, bData, 0, bSubKey.Length);
            Array.Copy(bPrimaryKey, 0, bData, bSubKey.Length, bPrimaryKey.Length);

            SignaturePacket spKeyBindingSig = new SignaturePacket();

            spKeyBindingSig.Version       = SignaturePacketVersionNumbers.v4;
            spKeyBindingSig.HashAlgorithm = HashAlgorithms.SHA1;
            spKeyBindingSig.KeyID         = pkpPrimaryKey.KeyID;
            spKeyBindingSig.SignatureType = SignatureTypes.SubkeyBindingSignature;

            spKeyBindingSig.Sign(bData, skpPrimaryKey, strPassphrase);
            this.KeyBindingSignature = spKeyBindingSig;
        }
        /// <summary>
        /// Creates a new Certification for the UserID.
        /// </summary>
        /// <param name="spSignature">A signaturepacket that has been
        /// prepared for being signed. Things like signature subpackets
        /// MUST already be in place. Only the signature type is
        /// automatically set to UserIDCertification.</param>
        /// <param name="skpKey">A secret key that is used to signed the
        /// certification.</param>
        /// <param name="strPassphrase">The passphrase that fits to the
        /// given secret key packet.</param>
        /// <param name="pkpKey">The public key to which the userid that
        /// is to be signed belongs.</param>
        public void Sign(SignaturePacket spSignature, SecretKeyPacket skpKey, string strPassphrase, PublicKeyPacket pkpKey)
        {
            if (spSignature.Version == SignaturePacketVersionNumbers.v4)
            {
                byte[] bKey = new byte[pkpKey.Body.Length + 3];
                bKey[0] = 0x99;
                bKey[1] = (byte)((pkpKey.Body.Length >> 8) & 0xFF);
                bKey[2] = (byte)(pkpKey.Body.Length & 0xFF);
                Array.Copy(pkpKey.Body, 0, bKey, 3, pkpKey.Body.Length);

                byte[] bUserID = new byte[UserID.Body.Length + 5];
                bUserID[0] = 0xb4;
                bUserID[1] = (byte)((UserID.Body.Length >> 24) & 0xFF);
                bUserID[2] = (byte)((UserID.Body.Length >> 16) & 0xFF);
                bUserID[3] = (byte)((UserID.Body.Length >> 8) & 0xFF);
                bUserID[4] = (byte)(UserID.Body.Length & 0xFF);
                Array.Copy(UserID.Body, 0, bUserID, 5, UserID.Body.Length);

                byte[] bData = new byte[bUserID.Length + bKey.Length];
                Array.Copy(bKey, 0, bData, 0, bKey.Length);
                Array.Copy(bUserID, 0, bData, bKey.Length, bUserID.Length);

                spSignature.SignatureType = SignatureTypes.UserIDSignature;
                spSignature.Sign(bData, skpKey, strPassphrase);
                this.alCertificates.Add(spSignature);
            }
            else
            {
                throw new System.NotImplementedException("Only v4 signatures are supported so far!");
            }
        }
Пример #7
0
        /// <summary>
        /// Finds a key
        /// </summary>
        /// <param name="lKeyID"the key to be found></param>
        /// <returns>the found key</returns>
        public TransportableSecretKey Find(ulong lKeyID)
        {
            IEnumerator ieKeys = SecretKeys.GetEnumerator();

            while (ieKeys.MoveNext())
            {
                TransportableSecretKey tskKey = (TransportableSecretKey)ieKeys.Current;
                if (tskKey.PrimaryKey.PublicKey.KeyID == lKeyID)
                {
                    return(tskKey);
                }

                IEnumerator ieSubkeys = tskKey.SubKeys.GetEnumerator();
                while (ieSubkeys.MoveNext())
                {
                    if (!(ieSubkeys.Current is SecretKeyPacket))
                    {
                        throw new Exception("Expected a secret key packet, but did not find one.");
                    }

                    SecretKeyPacket skpKey = (SecretKeyPacket)ieSubkeys.Current;
                    if (skpKey.PublicKey.KeyID == lKeyID)
                    {
                        return(tskKey);
                    }
                }
            }
            return(null);
        }
Пример #8
0
        public PgpSecretKeyRing(IPacketReader packetReader)
        {
            this.keys         = new List <PgpSecretKey>();
            this.extraPubKeys = new List <PgpPublicKey>();

            PacketTag initialTag = packetReader.NextPacketTag();

            if (initialTag != PacketTag.SecretKey && initialTag != PacketTag.SecretSubkey)
            {
                throw new PgpUnexpectedPacketException();
            }

            SecretKeyPacket secret = (SecretKeyPacket)packetReader.ReadContainedPacket();

            keys.Add(new PgpSecretKey(packetReader, secret, subKey: false));

            // Read subkeys
            while (packetReader.NextPacketTag() == PacketTag.SecretSubkey || packetReader.NextPacketTag() == PacketTag.PublicSubkey)
            {
                if (packetReader.NextPacketTag() == PacketTag.SecretSubkey)
                {
                    SecretSubkeyPacket sub = (SecretSubkeyPacket)packetReader.ReadContainedPacket();
                    keys.Add(new PgpSecretKey(packetReader, sub, subKey: true));
                }
                else
                {
                    PublicSubkeyPacket sub = (PublicSubkeyPacket)packetReader.ReadContainedPacket();
                    extraPubKeys.Add(new PgpPublicKey(packetReader, sub, subKey: true));
                }
            }
        }
Пример #9
0
        public static string ClearTextSign(string strMessage, SecretKeyRing skrKeyRing)
        {
            SignaturePacket spSign = new SignaturePacket();

            strMessage = Radix64.TrimMessage(strMessage);
            QueryPassphrase qpPassphrase = new QueryPassphrase();

            qpPassphrase.ShowMyDialog(skrKeyRing);
            string strPassphrase          = qpPassphrase.Passphrase;
            TransportableSecretKey tskKey = qpPassphrase.SelectedKey;
            SecretKeyPacket        skpKey = tskKey.FindKey(AsymActions.Sign);

            Working wWorking = new Working();

            wWorking.Show();

            spSign.HashAlgorithm = HashAlgorithms.SHA1;
            spSign.Format        = PacketFormats.New;

            wWorking.Progress(10);

            SignatureSubPacket sspCreator = new SignatureSubPacket();

            sspCreator.Type  = SignatureSubPacketTypes.IssuerKeyID;
            sspCreator.KeyID = skpKey.PublicKey.KeyID;
            SignatureSubPacket sspCreationTime = new SignatureSubPacket();

            sspCreationTime.Type        = SignatureSubPacketTypes.SignatureCreationTime;
            sspCreationTime.TimeCreated = DateTime.Now;
            spSign.HashedSubPackets     = new SignatureSubPacket[2];
            spSign.HashedSubPackets[0]  = sspCreator;
            spSign.HashedSubPackets[1]  = sspCreationTime;

            wWorking.Progress(20);

            //spSign.KeyID = skpKey.PublicKey.KeyID;
            //spSign.TimeCreated = DateTime.Now;
            spSign.SignatureAlgorithm = skpKey.PublicKey.Algorithm;
            spSign.SignatureType      = SignatureTypes.TextSignature;
            spSign.Version            = SignaturePacketVersionNumbers.v4;

            wWorking.Progress(10);

            byte[] bMessage = System.Text.Encoding.UTF8.GetBytes(strMessage);
            spSign.Sign(bMessage, skpKey, strPassphrase);

            wWorking.Progress(40);
            byte[] bSignature = spSign.Generate();

            string strSignature = Radix64.Encode(bSignature, true);

            wWorking.Progress(20);

            string strFinal = Armor.WrapCleartextSignature(strMessage, strSignature);

            wWorking.Hide();

            return(strFinal);
        }
Пример #10
0
 /**
  * Construct a PgpSecretKey using the passed in private key and public key. This constructor will not add any
  * certifications but assumes that pubKey already has what is required.
  *
  * @param privKey the private key component.
  * @param pubKey the public key component.
  * @param checksumCalculator a calculator for the private key checksum
  * @param isMasterKey true if the key is a master key, false otherwise.
  * @param keyEncryptor an encryptor for the key if required (null otherwise).
  * @throws PgpException if there is an issue creating the secret key packet.
  */
 public PgpSecretKey(
     PgpPrivateKey privKey,
     PgpPublicKey pubKey,
     bool isMasterKey,
     IPbeSecretKeyEncryptor keyEncryptor)
 {
     this.pub    = pubKey;
     this.secret = buildSecretKeyPacket(isMasterKey, privKey, pubKey, keyEncryptor);
 }
        /// <summary>
        /// Generates the transportable secret key out of the properties
        /// in this.
        /// </summary>
        /// <returns>Returns a byte array containing the openpgp encoded
        /// representation of the transportable secret key.</returns>
        /// <remarks>
        /// Generates the transportable secret key out of the properties
        /// in this.
        /// </remarks>
        public byte[] Generate()
        {
            if (alUserIDs.Count == 0)
            {
                throw new Exception("A transportable secret key must have at least one userid assigned to the primary key!");
            }

            byte[] bSecretKey = skpPrimaryKey.Generate();
            byte[] bUserIDs   = new byte[0];
            byte[] bSubkeys   = new byte[0];

            IEnumerator ieUserIDs = alUserIDs.GetEnumerator();

            while (ieUserIDs.MoveNext())
            {
                if (!(ieUserIDs.Current is UserIDPacket))
                {
                    continue;
                }

                UserIDPacket uipID       = (UserIDPacket)ieUserIDs.Current;
                byte[]       bUserID     = uipID.Generate();
                byte[]       bOldUserIDs = new byte[bUserIDs.Length];
                bUserIDs.CopyTo(bOldUserIDs, 0);
                bUserIDs = new byte[bOldUserIDs.Length + bUserID.Length];

                bOldUserIDs.CopyTo(bUserIDs, 0);
                bUserID.CopyTo(bUserIDs, bOldUserIDs.Length);
            }

            IEnumerator ieSubkeys = alSubkeys.GetEnumerator();

            while (ieSubkeys.MoveNext())
            {
                if (!(ieSubkeys.Current is SecretKeyPacket))
                {
                    continue;
                }

                SecretKeyPacket skpSubkey   = (SecretKeyPacket)ieSubkeys.Current;
                byte[]          bSubkey     = skpSubkey.Generate();
                byte[]          bOldSubkeys = new byte[bSubkeys.Length];
                bSubkeys.CopyTo(bOldSubkeys, 0);
                bSubkeys = new byte[bOldSubkeys.Length + bSubkey.Length];

                bOldSubkeys.CopyTo(bSubkeys, 0);
                bSubkey.CopyTo(bSubkeys, bOldSubkeys.Length);
            }

            byte[] bReturn = new byte[bSecretKey.Length + bUserIDs.Length + bSubkeys.Length];
            bSecretKey.CopyTo(bReturn, 0);
            bUserIDs.CopyTo(bReturn, bSecretKey.Length);
            bSubkeys.CopyTo(bReturn, bSecretKey.Length + bUserIDs.Length);

            return(bReturn);
        }
Пример #12
0
        void cmdParse_Click(Object sender, System.EventArgs e)
        {
            Packet[] pKeys = Packet.ParsePackets(txtBase64Key.Text);

            string strKeys = "";

            for (int i = 0; i < pKeys.Length; i++)
            {
                /* As soon as all Packets are implemented, replace
                 * this by a simple pKeys[i].ToString();
                 * For now we need all the ifs
                 */
                if (pKeys[i] is PublicKeyPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is UserIDPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is SignaturePacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is SymmetricallyEncryptedDataPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is AsymSessionKeyPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is SymSessionKeyPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is LiteralDataPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is CompressedDataPacket)
                {
                    strKeys += pKeys[i].ToString();
                }
                else if (pKeys[i] is SecretKeyPacket)
                {
                    QueryPassphrase queryPassphrase = new QueryPassphrase();
                    queryPassphrase.ShowMyDialog();
                    string          strPassphrase = queryPassphrase.Passphrase;
                    SecretKeyPacket skpPacket     = (SecretKeyPacket)pKeys[i];
                    skpPacket.GetDecryptedKeyMaterial(strPassphrase);
                    strKeys += pKeys[i].ToString();
                }
            }
            this.txtKeyProperties.Lines = strKeys.Split('\n');
        }
Пример #13
0
 /// <summary>Copy constructor - subkey.</summary>
 private PgpSecretKey(
     SecretKeyPacket secret,
     TrustPacket trust,
     ArrayList subSigs,
     PgpPublicKey pub)
 {
     this.secret  = secret;
     this.trust   = trust;
     this.subSigs = subSigs;
     this.pub     = pub;
 }
Пример #14
0
        /// <summary>
        /// Secret key operation. Signs biHash with the keydata
        /// in the given secret key packet.
        /// </summary>
        /// <param name="biHash">The hash value of a message that is about to
        /// be signed</param>
        /// <param name="skpKey">The secret key packet with the key
        /// material for the signature</param>
        /// <param name="strPassphrase">The passphrase for the
        /// keymaterial</param>
        /// <returns>The signed hash as array of biginteger. Only return[0]
        /// contains a value: the signed hash.</returns>
        /// <remarks>No remarks</remarks>
        public override BigInteger[] Sign(BigInteger biHash, SecretKeyPacket skpKey, string strPassphrase)
        {
            //Signing and encrypting is just the same
            BigInteger[] biHashArray = { biHash };
            BigInteger   biSignature = Decrypt(biHashArray, skpKey, strPassphrase);

            BigInteger[] biReturn = new BigInteger[1];

            biReturn[0] = biSignature;
            return(biReturn);
        }
Пример #15
0
 internal PgpSecretKey(
     SecretKeyPacket secret,
     TrustPacket trust,
     IDigest sha,
     ArrayList subSigs)
 {
     this.secret  = secret;
     this.trust   = trust;
     this.subSigs = subSigs;
     this.pub     = new PgpPublicKey(secret.PublicKeyPacket, trust, subSigs);
 }
Пример #16
0
        /// <summary>
        /// Return a copy of the passed in secret key, encrypted using a new password
        /// and the passed in algorithm.
        /// </summary>
        /// <remarks>
        /// Allows the caller to handle the encoding of the passphrase to bytes.
        /// </remarks>
        /// <param name="key">The PgpSecretKey to be copied.</param>
        /// <param name="rawOldPassPhrase">The current password for the key.</param>
        /// <param name="rawNewPassPhrase">The new password for the key.</param>
        public static PgpSecretKey CopyWithNewPassword(
            PgpSecretKey key,
            ReadOnlySpan <byte> rawOldPassPhrase,
            ReadOnlySpan <byte> rawNewPassPhrase)
        {
            if (key == null)
            {
                throw new ArgumentNullException(nameof(key));
            }
            if (key.IsPrivateKeyEmpty)
            {
                throw new PgpException("no private key in this SecretKey - public key present only.");
            }

            byte[] rawKeyData = CryptoPool.Rent(key.keyPacket.KeyBytes.Length - key.keyPacket.PublicKeyLength + 0x20);
            try
            {
                S2kBasedEncryption.DecryptSecretKey(
                    rawOldPassPhrase,
                    key.keyPacket.KeyBytes.AsSpan(key.keyPacket.PublicKeyLength),
                    rawKeyData,
                    out int rawKeySize,
                    key.keyPacket.Version);

                // Use the default S2K parameters
                var s2kParameters = new S2kParameters();

                var newKeyData = new byte[S2kBasedEncryption.GetEncryptedLength(s2kParameters, rawKeySize, key.keyPacket.Version) + key.keyPacket.PublicKeyLength];
                key.keyPacket.KeyBytes.AsSpan(0, key.keyPacket.PublicKeyLength).CopyTo(newKeyData);

                S2kBasedEncryption.EncryptSecretKey(
                    rawNewPassPhrase,
                    s2kParameters,
                    rawKeyData.AsSpan(0, rawKeySize),
                    newKeyData.AsSpan(key.keyPacket.PublicKeyLength),
                    key.keyPacket.Version);

                SecretKeyPacket newKeyPacket;
                if (key.keyPacket is SecretSubkeyPacket)
                {
                    newKeyPacket = new SecretSubkeyPacket(key.Algorithm, key.CreationTime, newKeyData);
                }
                else
                {
                    newKeyPacket = new SecretKeyPacket(key.Algorithm, key.CreationTime, newKeyData);
                }

                return(new PgpSecretKey(newKeyPacket, key));
            }
            finally
            {
                CryptoPool.Return(rawKeyData);
            }
        }
Пример #17
0
        internal static PgpSecretKey DoCopyWithNewPassword(PgpSecretKey key, byte[] rawOldPassPhrase, byte[] rawNewPassPhrase, bool clearPassPhrase, SymmetricKeyAlgorithmTag newEncAlgorithm, SecureRandom rand)
        {
            if (key.IsPrivateKeyEmpty)
            {
                throw new PgpException("no private key in this SecretKey - public key present only.");
            }
            byte[] array = key.ExtractKeyData(rawOldPassPhrase, clearPassPhrase);
            int    num   = key.secret.S2kUsage;

            byte[]          iv              = null;
            S2k             s2k             = null;
            PublicKeyPacket publicKeyPacket = key.secret.PublicKeyPacket;

            byte[] array2;
            if (newEncAlgorithm == SymmetricKeyAlgorithmTag.Null)
            {
                num = 0;
                if (key.secret.S2kUsage == 254)
                {
                    array2 = new byte[array.Length - 18];
                    global::System.Array.Copy((global::System.Array)array, 0, (global::System.Array)array2, 0, array2.Length - 2);
                    byte[] array3 = Checksum(useSha1: false, array2, array2.Length - 2);
                    array2[array2.Length - 2] = array3[0];
                    array2[array2.Length - 1] = array3[1];
                }
                else
                {
                    array2 = array;
                }
            }
            else
            {
                if (num == 0)
                {
                    num = 255;
                }
                try
                {
                    array2 = ((publicKeyPacket.Version < 4) ? EncryptKeyDataV3(array, newEncAlgorithm, rawNewPassPhrase, clearPassPhrase, rand, out s2k, out iv) : EncryptKeyDataV4(array, newEncAlgorithm, HashAlgorithmTag.Sha1, rawNewPassPhrase, clearPassPhrase, rand, out s2k, out iv));
                }
                catch (PgpException ex)
                {
                    throw ex;
                }
                catch (global::System.Exception exception)
                {
                    throw new PgpException("Exception encrypting key", exception);
                }
            }
            SecretKeyPacket secretKeyPacket = ((!(key.secret is SecretSubkeyPacket)) ? new SecretKeyPacket(publicKeyPacket, newEncAlgorithm, num, s2k, iv, array2) : new SecretSubkeyPacket(publicKeyPacket, newEncAlgorithm, num, s2k, iv, array2));

            return(new PgpSecretKey(secretKeyPacket, key.pub));
        }
        public static TransportableSecretKey[] SplitKeys(string strRadix64)
        {
            ArrayList alKeys = new ArrayList();

            Packet[] pPackets = Packet.ParsePackets(strRadix64);

            byte[] bOneKey = new byte[0];
            for (int i = 0; i < pPackets.Length; i++)
            {
                if (pPackets[i] is PublicKeyPacket)
                {
                    SecretKeyPacket skpKey = (SecretKeyPacket)pPackets[i];
                    if ((skpKey.Content == ContentTypes.SecretKey) && (bOneKey.Length > 10))
                    {
                        TransportableSecretKey tskKey = new TransportableSecretKey(Radix64.Encode(bOneKey, true));
                        alKeys.Add(tskKey);
                        bOneKey = new byte[0];
                    }
                }
                byte[] bPacket = pPackets[i].Generate();
                byte[] bTmpKey = new byte[bOneKey.Length];
                bOneKey.CopyTo(bTmpKey, 0);
                bOneKey = new byte[bOneKey.Length + bPacket.Length];
                Array.Copy(bTmpKey, 0, bOneKey, 0, bTmpKey.Length);
                Array.Copy(bPacket, 0, bOneKey, bTmpKey.Length, bPacket.Length);
            }

            if (bOneKey.Length > 10)
            {
                TransportableSecretKey tskKey = new TransportableSecretKey(Radix64.Encode(bOneKey, true));
                alKeys.Add(tskKey);
            }

            TransportableSecretKey[] tskKeys = new TransportableSecretKey[alKeys.Count];
            int         iCount = 0;
            IEnumerator ieKeys = alKeys.GetEnumerator();

            while (ieKeys.MoveNext())
            {
                if (!(ieKeys.Current is TransportableSecretKey))
                {
                    continue;
                }

                tskKeys[iCount++] = (TransportableSecretKey)ieKeys.Current;
            }

            return(tskKeys);
        }
Пример #19
0
        private DSA_Secret_Key ParseSecretKey(SecretKeyPacket skpKey, string strPassphrase)
        {
            DSA_Secret_Key dskKey = new DSA_Secret_Key();

            dskKey.p = skpKey.PublicKey.KeyMaterial[0];
            dskKey.q = skpKey.PublicKey.KeyMaterial[1];
            dskKey.g = skpKey.PublicKey.KeyMaterial[2];
            dskKey.y = skpKey.PublicKey.KeyMaterial[3];

            BigInteger[] biSecretKeyMaterial = skpKey.GetDecryptedKeyMaterial(strPassphrase);

            dskKey.x = biSecretKeyMaterial[0];

            return(dskKey);
        }
Пример #20
0
        private RSA_Secret_Key ParseSecretKey(SecretKeyPacket skpKey, string strPassphrase)
        {
            RSA_Secret_Key rskKey = new RSA_Secret_Key();

            rskKey.n = skpKey.PublicKey.KeyMaterial[0];
            rskKey.e = skpKey.PublicKey.KeyMaterial[1];

            BigInteger[] biSecretKeyMaterial = skpKey.GetDecryptedKeyMaterial(strPassphrase);

            rskKey.d = biSecretKeyMaterial[0];
            rskKey.p = biSecretKeyMaterial[1];
            rskKey.q = biSecretKeyMaterial[2];
            rskKey.u = biSecretKeyMaterial[3];

            return(rskKey);
        }
Пример #21
0
 /// <summary>Copy constructor - master key.</summary>
 private PgpSecretKey(
     SecretKeyPacket secret,
     TrustPacket trust,
     ArrayList keySigs,
     ArrayList ids,
     ArrayList idTrusts,
     ArrayList idSigs,
     PgpPublicKey pub)
 {
     this.secret   = secret;
     this.trust    = trust;
     this.keySigs  = keySigs;
     this.ids      = ids;
     this.idTrusts = idTrusts;
     this.idSigs   = idSigs;
     this.pub      = pub;
 }
Пример #22
0
 internal PgpSecretKey(
     SecretKeyPacket secret,
     TrustPacket trust,
     IDigest sha,
     ArrayList keySigs,
     ArrayList ids,
     ArrayList idTrusts,
     ArrayList idSigs)
 {
     this.secret   = secret;
     this.trust    = trust;
     this.keySigs  = keySigs;
     this.ids      = ids;
     this.idTrusts = idTrusts;
     this.idSigs   = idSigs;
     this.pub      = new PgpPublicKey(secret.PublicKeyPacket, trust, keySigs, ids, idTrusts, idSigs);
 }
Пример #23
0
        }        //IL_0002: Unknown result type (might be due to invalid IL or missing references)

        //IL_000c: Expected O, but got Unknown


        public PgpSecretKeyRing(Stream inputStream)
        {
            //IL_004b: Unknown result type (might be due to invalid IL or missing references)
            keys         = Platform.CreateArrayList();
            extraPubKeys = Platform.CreateArrayList();
            BcpgInputStream bcpgInputStream = BcpgInputStream.Wrap(inputStream);
            PacketTag       packetTag       = bcpgInputStream.NextPacketTag();

            if (packetTag != PacketTag.SecretKey && packetTag != PacketTag.SecretSubkey)
            {
                int num = (int)packetTag;
                throw new IOException("secret key ring doesn't start with secret key tag: tag 0x" + num.ToString("X"));
            }
            SecretKeyPacket secretKeyPacket = (SecretKeyPacket)bcpgInputStream.ReadPacket();

            while (bcpgInputStream.NextPacketTag() == PacketTag.Experimental2)
            {
                bcpgInputStream.ReadPacket();
            }
            TrustPacket trustPk = PgpKeyRing.ReadOptionalTrustPacket(bcpgInputStream);

            global::System.Collections.IList keySigs = PgpKeyRing.ReadSignaturesAndTrust(bcpgInputStream);
            PgpKeyRing.ReadUserIDs(bcpgInputStream, out var ids, out var idTrusts, out var idSigs);
            keys.Add((object)new PgpSecretKey(secretKeyPacket, new PgpPublicKey(secretKeyPacket.PublicKeyPacket, trustPk, keySigs, ids, idTrusts, idSigs)));
            while (bcpgInputStream.NextPacketTag() == PacketTag.SecretSubkey || bcpgInputStream.NextPacketTag() == PacketTag.PublicSubkey)
            {
                if (bcpgInputStream.NextPacketTag() == PacketTag.SecretSubkey)
                {
                    SecretSubkeyPacket secretSubkeyPacket = (SecretSubkeyPacket)bcpgInputStream.ReadPacket();
                    while (bcpgInputStream.NextPacketTag() == PacketTag.Experimental2)
                    {
                        bcpgInputStream.ReadPacket();
                    }
                    TrustPacket trustPk2 = PgpKeyRing.ReadOptionalTrustPacket(bcpgInputStream);
                    global::System.Collections.IList sigs = PgpKeyRing.ReadSignaturesAndTrust(bcpgInputStream);
                    keys.Add((object)new PgpSecretKey(secretSubkeyPacket, new PgpPublicKey(secretSubkeyPacket.PublicKeyPacket, trustPk2, sigs)));
                }
                else
                {
                    PublicSubkeyPacket publicPk            = (PublicSubkeyPacket)bcpgInputStream.ReadPacket();
                    TrustPacket        trustPk3            = PgpKeyRing.ReadOptionalTrustPacket(bcpgInputStream);
                    global::System.Collections.IList sigs2 = PgpKeyRing.ReadSignaturesAndTrust(bcpgInputStream);
                    extraPubKeys.Add((object)new PgpPublicKey(publicPk, trustPk3, sigs2));
                }
            }
        }
    public PgpSecretKeyRing(Stream inputStream)
    {
        keys         = Platform.CreateArrayList();
        extraPubKeys = Platform.CreateArrayList();
        BcpgInputStream bcpgInputStream = BcpgInputStream.Wrap(inputStream);
        PacketTag       packetTag       = bcpgInputStream.NextPacketTag();

        if (packetTag != PacketTag.SecretKey && packetTag != PacketTag.SecretSubkey)
        {
            int num = (int)packetTag;
            throw new IOException("secret key ring doesn't start with secret key tag: tag 0x" + num.ToString("X"));
        }
        SecretKeyPacket secretKeyPacket = (SecretKeyPacket)bcpgInputStream.ReadPacket();

        while (bcpgInputStream.NextPacketTag() == PacketTag.Experimental2)
        {
            bcpgInputStream.ReadPacket();
        }
        TrustPacket trustPk = PgpKeyRing.ReadOptionalTrustPacket(bcpgInputStream);
        IList       keySigs = PgpKeyRing.ReadSignaturesAndTrust(bcpgInputStream);

        PgpKeyRing.ReadUserIDs(bcpgInputStream, out IList ids, out IList idTrusts, out IList idSigs);
        keys.Add(new PgpSecretKey(secretKeyPacket, new PgpPublicKey(secretKeyPacket.PublicKeyPacket, trustPk, keySigs, ids, idTrusts, idSigs)));
        while (bcpgInputStream.NextPacketTag() == PacketTag.SecretSubkey || bcpgInputStream.NextPacketTag() == PacketTag.PublicSubkey)
        {
            if (bcpgInputStream.NextPacketTag() == PacketTag.SecretSubkey)
            {
                SecretSubkeyPacket secretSubkeyPacket = (SecretSubkeyPacket)bcpgInputStream.ReadPacket();
                while (bcpgInputStream.NextPacketTag() == PacketTag.Experimental2)
                {
                    bcpgInputStream.ReadPacket();
                }
                TrustPacket trustPk2 = PgpKeyRing.ReadOptionalTrustPacket(bcpgInputStream);
                IList       sigs     = PgpKeyRing.ReadSignaturesAndTrust(bcpgInputStream);
                keys.Add(new PgpSecretKey(secretSubkeyPacket, new PgpPublicKey(secretSubkeyPacket.PublicKeyPacket, trustPk2, sigs)));
            }
            else
            {
                PublicSubkeyPacket publicPk = (PublicSubkeyPacket)bcpgInputStream.ReadPacket();
                TrustPacket        trustPk3 = PgpKeyRing.ReadOptionalTrustPacket(bcpgInputStream);
                IList sigs2 = PgpKeyRing.ReadSignaturesAndTrust(bcpgInputStream);
                extraPubKeys.Add(new PgpPublicKey(publicPk, trustPk3, sigs2));
            }
        }
    }
        /// <summary>
        /// Parses the radix64 encoded representation of a transportable secret
        /// key given as an argument to populate the parameters of this.
        /// </summary>
        /// <param name="strRadix64">Radix64 representation of an transportable
        /// secret key</param>
        /// <exception cref="System.ArgumentException">Throws an
        /// ArgumentException if the radix64 string given as a parameter is
        /// not an transportable secret key.</exception>
        /// <remarks>No remarks</remarks>
        public void Parse(string strRadix64)
        {
            Packet[] pPackets = Packet.ParsePackets(strRadix64);

            int nCurrentPacket = 0;
            int nUserIDCounter = 0;

            try {
                // First we expect a PublicKeyPacket
                if (!(pPackets[0] is SecretKeyPacket))
                {
                    throw(new ArgumentException("The given packet is not in the required transportable secret key format!"));
                }
                this.PrimaryKey = (SecretKeyPacket)pPackets[nCurrentPacket++];

                // Next we expect one or more userid packets
                while ((nCurrentPacket < pPackets.Length) && (pPackets[nCurrentPacket] is UserIDPacket))
                {
                    UserIDPacket uipUserID = (UserIDPacket)pPackets[nCurrentPacket++];
                    this.UserIDs.Add(uipUserID);
                    nUserIDCounter++;
                }

                // we want at least 1 userid packet.
                if (nUserIDCounter == 0)
                {
                    throw(new ArgumentException("The given packet is not in the required transportable secret key format!"));
                }

                // Finally we have zero or more subkeys
                while ((nCurrentPacket < pPackets.Length) && (pPackets[nCurrentPacket] is SecretKeyPacket))
                {
                    SecretKeyPacket skpSubKey = (SecretKeyPacket)pPackets[nCurrentPacket++];
                    this.SubKeys.Add(skpSubKey);
                }
            } catch (System.IndexOutOfRangeException) {
                if (nUserIDCounter == 0)
                {
                    throw(new ArgumentException("The given packet is not in the required transportable secret key format!"));
                }
            }
        }
Пример #26
0
        public void SignKeyBindingSignature(PublicKeyPacket pkpPrimaryKey, SecretKeyPacket skpPrimaryKey, string strPassphrase, DateTime expirationTime, bool revocable)
        {
            byte[] bSubKey = new byte[pkpSubkey.Body.Length + 3];
            bSubKey[0] = 0x99;
            bSubKey[1] = (byte)((pkpSubkey.Body.Length >> 8) & 0xFF);
            bSubKey[2] = (byte)(pkpSubkey.Body.Length & 0xFF);
            Array.Copy(pkpSubkey.Body, 0, bSubKey, 3, pkpSubkey.Body.Length);

            byte[] bPrimaryKey = new byte[pkpPrimaryKey.Body.Length + 3];
            bPrimaryKey[0] = 0x99;
            bPrimaryKey[1] = (byte)((pkpPrimaryKey.Body.Length >> 8) & 0xFF);
            bPrimaryKey[2] = (byte)(pkpPrimaryKey.Body.Length & 0xFF);
            Array.Copy(pkpPrimaryKey.Body, 0, bPrimaryKey, 3, pkpPrimaryKey.Body.Length);

            byte[] bData = new byte[bPrimaryKey.Length + bSubKey.Length];
            Array.Copy(bPrimaryKey, 0, bData, 0, bPrimaryKey.Length);
            Array.Copy(bSubKey, 0, bData, bPrimaryKey.Length, bSubKey.Length);

            SignaturePacket spKeyBindingSig = new SignaturePacket();

            spKeyBindingSig.Version       = SignaturePacketVersionNumbers.v4;
            spKeyBindingSig.HashAlgorithm = HashAlgorithms.SHA1;
            spKeyBindingSig.KeyID         = pkpPrimaryKey.KeyID;
            spKeyBindingSig.SignatureType = SignatureTypes.SubkeyBindingSignature;
            if (expirationTime.Ticks != 0)
            {
                SignatureSubPacket sspExpiration = new SignatureSubPacket();
                sspExpiration.Type = SignatureSubPacketTypes.KeyExpirationTime;
                sspExpiration.KeyExpirationTime = new DateTime(expirationTime.Ticks + (new DateTime(1970, 1, 2)).Ticks - pkpPrimaryKey.TimeCreated.Ticks);
                spKeyBindingSig.AddSubPacket(sspExpiration, true);
            }
            if (!revocable)
            {
                SignatureSubPacket sspRevocable = new SignatureSubPacket();
                sspRevocable.Type      = SignatureSubPacketTypes.Revocable;
                sspRevocable.Revocable = revocable;
                spKeyBindingSig.AddSubPacket(sspRevocable, true);
            }
            spKeyBindingSig.Sign(bData, skpPrimaryKey, strPassphrase);
            this.KeyBindingSignature = spKeyBindingSig;
        }
Пример #27
0
        /// <summary>
        /// Secret key operation. Decrypts biCipher with the keydata
        /// in the given secret key packet.
        /// </summary>
        /// <param name="biCipher">The ciphertext that is about to
        /// be decrypted</param>
        /// <param name="skpKey">The secret key packet with the key
        /// material for the decryption</param>
        /// <param name="strPassphrase">The passphrase for the
        /// keymaterial</param>
        /// <returns>The decrypted ciphertext.</returns>
        /// <remarks>No remarks.</remarks>
        public override BigInteger Decrypt(BigInteger[] biCipher, SecretKeyPacket skpKey, string strPassphrase)
        {
            RSA_Secret_Key skey = new RSA_Secret_Key();

            skey = ParseSecretKey(skpKey, strPassphrase);

            //check if someone mangled with the key
            if (!CheckKey(skey))
            {
                throw(new Exception("This key does not fullfill the requirements of a valid RSA key. Please check if someone messed with your keys!"));
            }

            if ((skey.d == 0) || (skey.n == 0))
            {
                throw new System.ArgumentException("This is not a valid secret key");
            }

            BigInteger biPlain = biCipher[0].modPow(skey.d, skey.n);

            return(biPlain);
        }
Пример #28
0
        private SignedMessage SignMessage(LiteralMessage lmToBeSigned, ulong lSignatureKeyID, string strPassphrase)
        {
            TransportableSecretKey tskKey    = skrKeyRing.Find(lSignatureKeyID);
            SignedMessage          smMessage = new SignedMessage();

            smMessage.MessageSigned = lmToBeSigned;
            SignaturePacket spPacket = new SignaturePacket();

            spPacket.Version = SignaturePacketVersionNumbers.v3;
            SecretKeyPacket skpKey = tskKey.FindKey(AsymActions.Sign);

            spPacket.KeyID              = skpKey.PublicKey.KeyID;
            spPacket.HashAlgorithm      = HashAlgorithms.SHA1;
            spPacket.SignatureAlgorithm = skpKey.PublicKey.Algorithm;
            spPacket.TimeCreated        = DateTime.Now;
            spPacket.SignatureType      = SignatureTypes.TextSignature;
            spPacket.Sign(lmToBeSigned.Binary, skpKey, strPassphrase);
            smMessage.Signature = spPacket;

            return(smMessage);
        }
        /// <summary>
        /// Finds a subkey (or the primary key) with the given keyid
        /// and returns it. Returns null if the the fitting key has
        /// not been found.
        /// </summary>
        /// <remarks>No remarks.</remarks>
        /// <param name="lKeyID">The keyid to be sought in the transportable
        /// secret key.</param>
        /// <returns>The subkey (or the primary key) with the given keyid.
        /// Null if the the fitting key has not been found.</returns>
        public SecretKeyPacket FindKey(ulong lKeyID)
        {
            if (skpPrimaryKey.PublicKey.KeyID == lKeyID)
            {
                return(skpPrimaryKey);
            }

            IEnumerator ieSubkeys = alSubkeys.GetEnumerator();

            while (ieSubkeys.MoveNext())
            {
                SecretKeyPacket skpKey = (SecretKeyPacket)ieSubkeys.Current;

                if (skpKey.PublicKey.KeyID == lKeyID)
                {
                    return(skpKey);
                }
            }

            return(null);
        }
Пример #30
0
        /// <summary>Create a subkey</summary>
        internal PgpSecretKey(
            PgpKeyPair keyPair,
            TrustPacket trust,
            ArrayList subSigs,
            SymmetricKeyAlgorithmTag encAlgorithm,
            char[]                                              passPhrase,
            bool useSHA1,
            SecureRandom rand)
            : this(keyPair, encAlgorithm, passPhrase, useSHA1, rand)
        {
            this.secret = new SecretSubkeyPacket(
                secret.PublicKeyPacket,
                secret.EncAlgorithm,
                secret.S2kUsage,
                secret.S2k,
                secret.GetIV(),
                secret.GetSecretKeyData());

            this.trust   = trust;
            this.subSigs = subSigs;
            this.pub     = new PgpPublicKey(keyPair.PublicKey, trust, subSigs);
        }
Пример #31
0
        public void AddUserID(ulong lKeyID, string strName, string strEmail, string strPassphrase)
        {
            TransportableSecretKey tskKey = skrKeyRing.Find(lKeyID);
            TransportablePublicKey tpkKey = pkrKeyRing.Find(lKeyID, false);

            CertifiedUserID cuiUID = new CertifiedUserID();
            UserIDPacket    uipUID = new UserIDPacket();

            uipUID.UserID = strName.Trim() + " <" + strEmail.Trim() + ">";
            cuiUID.UserID = uipUID;

            SecretKeyPacket skpSignatureKey = tskKey.FindKey(AsymActions.Sign);
            SignaturePacket spSelfSig       = new SignaturePacket();

            spSelfSig.Version       = SignaturePacketVersionNumbers.v4;
            spSelfSig.HashAlgorithm = HashAlgorithms.SHA1;
            spSelfSig.KeyID         = skpSignatureKey.PublicKey.KeyID;
            spSelfSig.TimeCreated   = DateTime.Now;
            cuiUID.Certificates     = new System.Collections.ArrayList();
            cuiUID.Sign(spSelfSig, skpSignatureKey, strPassphrase, tpkKey.PrimaryKey);

            tpkKey.Certifications.Add(cuiUID);
            tskKey.UserIDs.Add(uipUID);
        }
Пример #32
0
        internal static PgpSecretKey DoCopyWithNewPassword(
            PgpSecretKey				key,
            byte[]						rawOldPassPhrase,
            byte[]						rawNewPassPhrase,
            bool                        clearPassPhrase,
            SymmetricKeyAlgorithmTag	newEncAlgorithm,
            SecureRandom				rand)
        {
            if (key.IsPrivateKeyEmpty)
                throw new PgpException("no private key in this SecretKey - public key present only.");

            byte[]	rawKeyData = key.ExtractKeyData(rawOldPassPhrase, clearPassPhrase);
            int		s2kUsage = key.secret.S2kUsage;
            byte[]	iv = null;
            S2k		s2k = null;
            byte[]	keyData;
            PublicKeyPacket pubKeyPacket = key.secret.PublicKeyPacket;

            if (newEncAlgorithm == SymmetricKeyAlgorithmTag.Null)
            {
                s2kUsage = SecretKeyPacket.UsageNone;
                if (key.secret.S2kUsage == SecretKeyPacket.UsageSha1)   // SHA-1 hash, need to rewrite Checksum
                {
                    keyData = new byte[rawKeyData.Length - 18];

                    Array.Copy(rawKeyData, 0, keyData, 0, keyData.Length - 2);

                    byte[] check = Checksum(false, keyData, keyData.Length - 2);

                    keyData[keyData.Length - 2] = check[0];
                    keyData[keyData.Length - 1] = check[1];
                }
                else
                {
                    keyData = rawKeyData;
                }
            }
            else
            {
                if (s2kUsage == SecretKeyPacket.UsageNone)
                {
                    s2kUsage = SecretKeyPacket.UsageChecksum;
                }

                try
                {
                    if (pubKeyPacket.Version >= 4)
                    {
                        keyData = EncryptKeyDataV4(rawKeyData, newEncAlgorithm, HashAlgorithmTag.Sha1, rawNewPassPhrase, clearPassPhrase, rand, out s2k, out iv);
                    }
                    else
                    {
                        keyData = EncryptKeyDataV3(rawKeyData, newEncAlgorithm, rawNewPassPhrase, clearPassPhrase, rand, out s2k, out iv);
                    }
                }
                catch (PgpException e)
                {
                    throw e;
                }
                catch (Exception e)
                {
                    throw new PgpException("Exception encrypting key", e);
                }
            }

            SecretKeyPacket secret;
            if (key.secret is SecretSubkeyPacket)
            {
                secret = new SecretSubkeyPacket(pubKeyPacket, newEncAlgorithm, s2kUsage, s2k, iv, keyData);
            }
            else
            {
                secret = new SecretKeyPacket(pubKeyPacket, newEncAlgorithm, s2kUsage, s2k, iv, keyData);
            }

            return new PgpSecretKey(secret, key.pub);
        }
Пример #33
0
        /// <summary>
        /// Return a copy of the passed in secret key, encrypted using a new password
        /// and the passed in algorithm.
        /// </summary>
        /// <param name="key">The PgpSecretKey to be copied.</param>
        /// <param name="oldPassPhrase">The current password for the key.</param>
        /// <param name="newPassPhrase">The new password for the key.</param>
        /// <param name="newEncAlgorithm">The algorithm to be used for the encryption.</param>
        /// <param name="rand">Source of randomness.</param>
        public static PgpSecretKey CopyWithNewPassword(
            PgpSecretKey				key,
            char[]						oldPassPhrase,
            char[]						newPassPhrase,
            SymmetricKeyAlgorithmTag	newEncAlgorithm,
            SecureRandom				rand)
        {
            byte[]	rawKeyData = key.ExtractKeyData(oldPassPhrase);
            int		s2kUsage = key.secret.S2kUsage;
            byte[]	iv = null;
            S2k		s2k = null;
            byte[]	keyData;

            if (newEncAlgorithm == SymmetricKeyAlgorithmTag.Null)
            {
                s2kUsage = SecretKeyPacket.UsageNone;
                if (key.secret.S2kUsage == SecretKeyPacket.UsageSha1)   // SHA-1 hash, need to rewrite Checksum
                {
                    keyData = new byte[rawKeyData.Length - 18];

                    Array.Copy(rawKeyData, 0, keyData, 0, keyData.Length - 2);

                    byte[] check = Checksum(false, keyData, keyData.Length - 2);

                    keyData[keyData.Length - 2] = check[0];
                    keyData[keyData.Length - 1] = check[1];
                }
                else
                {
                    keyData = rawKeyData;
                }
            }
            else
            {
                IBufferedCipher c;
                try
                {
                    string cName = PgpUtilities.GetSymmetricCipherName(newEncAlgorithm);
                    c = CipherUtilities.GetCipher(cName + "/CFB/NoPadding");
                }
                catch (Exception e)
                {
                    throw new PgpException("Exception creating cipher", e);
                }

                iv = new byte[8];
                rand.NextBytes(iv);
                s2k = new S2k(HashAlgorithmTag.Sha1, iv, 0x60);
                try
                {
                    KeyParameter sKey = PgpUtilities.MakeKeyFromPassPhrase(newEncAlgorithm, s2k, newPassPhrase);
                    iv = new byte[c.GetBlockSize()];
                    rand.NextBytes(iv);
                    c.Init(true, new ParametersWithIV(sKey, iv));

                    keyData = c.DoFinal(rawKeyData);
                }
                catch (PgpException e)
                {
                    throw e;
                }
                catch (Exception e)
                {
                    throw new PgpException("Exception encrypting key", e);
                }
            }

            SecretKeyPacket secret;
            if (key.secret is SecretSubkeyPacket)
            {
                secret = new SecretSubkeyPacket(key.secret.PublicKeyPacket,
                    newEncAlgorithm, s2kUsage, s2k, iv, keyData);
            }
            else
            {
                secret = new SecretKeyPacket(key.secret.PublicKeyPacket,
                    newEncAlgorithm, s2kUsage, s2k, iv, keyData);
            }

            if (key.subSigs == null)
            {
                return new PgpSecretKey(secret, key.trust, key.keySigs, key.ids,
                    key.idTrusts, key.idSigs, key.pub);
            }

            return new PgpSecretKey(secret, key.trust, key.subSigs, key.pub);
        }
Пример #34
0
 internal PgpSecretKey(
     SecretKeyPacket	secret,
     TrustPacket		trust,
     ArrayList		keySigs,
     ArrayList		ids,
     ArrayList		idTrusts,
     ArrayList		idSigs)
 {
     this.secret = secret;
     this.trust = trust;
     this.keySigs = keySigs;
     this.ids = ids;
     this.idTrusts = idTrusts;
     this.idSigs = idSigs;
     this.pub = new PgpPublicKey(secret.PublicKeyPacket, trust, keySigs, ids, idTrusts, idSigs);
 }
Пример #35
0
        /// <summary>
        /// Creates a new Certification for the UserID.
        /// </summary>
        /// <param name="spSignature">A signaturepacket that has been
        /// prepared for being signed. Things like signature subpackets
        /// MUST already be in place. Only the signature type is
        /// automatically set to UserIDCertification.</param>
        /// <param name="skpKey">A secret key that is used to signed the
        /// certification.</param>
        /// <param name="strPassphrase">The passphrase that fits to the
        /// given secret key packet.</param>
        /// <param name="pkpKey">The public key to which the userid that
        /// is to be signed belongs.</param>
        public void Sign(SignaturePacket spSignature, SecretKeyPacket skpKey, string strPassphrase, PublicKeyPacket pkpKey)
        {
            if (spSignature.Version == SignaturePacketVersionNumbers.v4) {
                byte[] bKey = new byte[pkpKey.Body.Length + 3];
                bKey[0] = 0x99;
                bKey[1] = (byte)((pkpKey.Body.Length >> 8) & 0xFF);
                bKey[2] = (byte)(pkpKey.Body.Length & 0xFF);
                Array.Copy(pkpKey.Body, 0, bKey, 3, pkpKey.Body.Length);

                byte[] bUserID = new byte[UserID.Body.Length + 5];
                bUserID[0] = 0xb4;
                bUserID[1] = (byte)((UserID.Body.Length >> 24) & 0xFF);
                bUserID[2] = (byte)((UserID.Body.Length >> 16) & 0xFF);
                bUserID[3] = (byte)((UserID.Body.Length >> 8) & 0xFF);
                bUserID[4] = (byte)(UserID.Body.Length & 0xFF);
                Array.Copy(UserID.Body, 0, bUserID, 5, UserID.Body.Length);

                byte[] bData = new byte[bUserID.Length + bKey.Length];
                Array.Copy(bKey, 0, bData, 0, bKey.Length);
                Array.Copy(bUserID, 0, bData, bKey.Length, bUserID.Length);

                spSignature.SignatureType = SignatureTypes.UserIDSignature;
                spSignature.Sign(bData, skpKey, strPassphrase);
                this.alCertificates.Add(spSignature);
            } else {
                throw new System.NotImplementedException("Only v4 signatures are supported so far!");
            }
        }
Пример #36
0
 internal PgpSecretKey(
     SecretKeyPacket	secret,
     TrustPacket		trust,
     ArrayList		subSigs)
 {
     this.secret = secret;
     this.trust = trust;
     this.subSigs = subSigs;
     this.pub = new PgpPublicKey(secret.PublicKeyPacket, trust, subSigs);
 }
Пример #37
0
 /// <summary>Copy constructor - subkey.</summary>
 private PgpSecretKey(
     SecretKeyPacket secret,
     TrustPacket     trust,
     ArrayList       subSigs,
     PgpPublicKey    pub)
 {
     this.secret = secret;
     this.trust = trust;
     this.subSigs = subSigs;
     this.pub = pub;
 }
Пример #38
0
        internal PgpSecretKey(
            PgpPrivateKey				privKey,
            PgpPublicKey				pubKey,
            SymmetricKeyAlgorithmTag	encAlgorithm,
            byte[]						rawPassPhrase,
            bool                        clearPassPhrase,
            bool						useSha1,
            SecureRandom				rand,
            bool						isMasterKey)
        {
            BcpgObject secKey;

            this.pub = pubKey;

            switch (pubKey.Algorithm)
            {
                case PublicKeyAlgorithmTag.RsaEncrypt:
                case PublicKeyAlgorithmTag.RsaSign:
                case PublicKeyAlgorithmTag.RsaGeneral:
                    RsaPrivateCrtKeyParameters rsK = (RsaPrivateCrtKeyParameters) privKey.Key;
                    secKey = new RsaSecretBcpgKey(rsK.Exponent, rsK.P, rsK.Q);
                    break;
                case PublicKeyAlgorithmTag.Dsa:
                    DsaPrivateKeyParameters dsK = (DsaPrivateKeyParameters) privKey.Key;
                    secKey = new DsaSecretBcpgKey(dsK.X);
                    break;
                case PublicKeyAlgorithmTag.ECDH:
                case PublicKeyAlgorithmTag.ECDsa:
                    ECPrivateKeyParameters ecK = (ECPrivateKeyParameters)privKey.Key;
                    secKey = new ECSecretBcpgKey(ecK.D);
                    break;
                case PublicKeyAlgorithmTag.ElGamalEncrypt:
                case PublicKeyAlgorithmTag.ElGamalGeneral:
                    ElGamalPrivateKeyParameters esK = (ElGamalPrivateKeyParameters) privKey.Key;
                    secKey = new ElGamalSecretBcpgKey(esK.X);
                    break;
                default:
                    throw new PgpException("unknown key class");
            }

            try
            {
                MemoryStream bOut = new MemoryStream();
                BcpgOutputStream pOut = new BcpgOutputStream(bOut);

                pOut.WriteObject(secKey);

                byte[] keyData = bOut.ToArray();
                byte[] checksumData = Checksum(useSha1, keyData, keyData.Length);

                keyData = Arrays.Concatenate(keyData, checksumData);

                if (encAlgorithm == SymmetricKeyAlgorithmTag.Null)
                {
                    if (isMasterKey)
                    {
                        this.secret = new SecretKeyPacket(pub.publicPk, encAlgorithm, null, null, keyData);
                    }
                    else
                    {
                        this.secret = new SecretSubkeyPacket(pub.publicPk, encAlgorithm, null, null, keyData);
                    }
                }
                else
                {
                    S2k s2k;
                    byte[] iv;

                    byte[] encData;
                    if (pub.Version >= 4)
                    {
                        encData = EncryptKeyDataV4(keyData, encAlgorithm, HashAlgorithmTag.Sha1, rawPassPhrase, clearPassPhrase, rand, out s2k, out iv);
                    }
                    else
                    {
                        encData = EncryptKeyDataV3(keyData, encAlgorithm, rawPassPhrase, clearPassPhrase, rand, out s2k, out iv);
                    }

                    int s2kUsage = useSha1
                        ?	SecretKeyPacket.UsageSha1
                        :	SecretKeyPacket.UsageChecksum;

                    if (isMasterKey)
                    {
                        this.secret = new SecretKeyPacket(pub.publicPk, encAlgorithm, s2kUsage, s2k, iv, encData);
                    }
                    else
                    {
                        this.secret = new SecretSubkeyPacket(pub.publicPk, encAlgorithm, s2kUsage, s2k, iv, encData);
                    }
                }
            }
            catch (PgpException e)
            {
                throw e;
            }
            catch (Exception e)
            {
                throw new PgpException("Exception encrypting key", e);
            }
        }
Пример #39
0
        /// <summary>Create a subkey</summary>
        internal PgpSecretKey(
            PgpKeyPair					keyPair,
            TrustPacket					trust,
            ArrayList					subSigs,
            SymmetricKeyAlgorithmTag	encAlgorithm,
            char[]						passPhrase,
			bool						useSHA1,
			SecureRandom				rand)
            : this(keyPair, encAlgorithm, passPhrase, useSHA1, rand)
        {
            this.secret = new SecretSubkeyPacket(
                secret.PublicKeyPacket,
                secret.EncAlgorithm,
                secret.S2kUsage,
                secret.S2k,
                secret.GetIV(),
                secret.GetSecretKeyData());

            this.trust = trust;
            this.subSigs = subSigs;
            this.pub = new PgpPublicKey(keyPair.PublicKey, trust, subSigs);
        }
Пример #40
0
        internal PgpSecretKey(
            PgpKeyPair					keyPair,
            SymmetricKeyAlgorithmTag	encAlgorithm,
            char[]						passPhrase,
			bool						useSHA1,
			SecureRandom				rand)
        {
            PublicKeyPacket pubPk = keyPair.PublicKey.publicPk;

            BcpgObject secKey;
            switch (keyPair.PublicKey.Algorithm)
            {
                case PublicKeyAlgorithmTag.RsaEncrypt:
                case PublicKeyAlgorithmTag.RsaSign:
                case PublicKeyAlgorithmTag.RsaGeneral:
                    RsaPrivateCrtKeyParameters rsK = (RsaPrivateCrtKeyParameters) keyPair.PrivateKey.Key;
                    secKey = new RsaSecretBcpgKey(rsK.Exponent, rsK.P, rsK.Q);
                    break;
                case PublicKeyAlgorithmTag.Dsa:
                    DsaPrivateKeyParameters dsK = (DsaPrivateKeyParameters) keyPair.PrivateKey.Key;
                    secKey = new DsaSecretBcpgKey(dsK.X);
                    break;
                case PublicKeyAlgorithmTag.ElGamalEncrypt:
                case PublicKeyAlgorithmTag.ElGamalGeneral:
                    ElGamalPrivateKeyParameters esK = (ElGamalPrivateKeyParameters) keyPair.PrivateKey.Key;
                    secKey = new ElGamalSecretBcpgKey(esK.X);
                    break;
                default:
                    throw new PgpException("unknown key class");
            }

            string cName = PgpUtilities.GetSymmetricCipherName(encAlgorithm);

            IBufferedCipher c = null;
            if (cName != null)
            {
                try
                {
                    c = CipherUtilities.GetCipher(cName + "/CFB/NoPadding");
                }
                catch (Exception e)
                {
                    throw new PgpException("Exception creating cipher", e);
                }
            }

            try
            {
                MemoryStream bOut = new MemoryStream();
                BcpgOutputStream pOut = new BcpgOutputStream(bOut);

                pOut.WriteObject(secKey);

                byte[] keyData = bOut.ToArray();
                byte[] checksumBytes = Checksum(useSHA1, keyData, keyData.Length);

                pOut.Write(checksumBytes);

                byte[] bOutData = bOut.ToArray();

                if (c != null)
                {
                    byte[] iv = new byte[8];
                    rand.NextBytes(iv);

                    S2k s2k = new S2k(HashAlgorithmTag.Sha1, iv, 0x60);
                    KeyParameter key = PgpUtilities.MakeKeyFromPassPhrase(encAlgorithm, s2k, passPhrase);

                    iv = new byte[c.GetBlockSize()];
                    rand.NextBytes(iv);
                    c.Init(true, new ParametersWithIV(key, iv));

                    byte[] encData = c.DoFinal(bOutData);

                    int usage = useSHA1
                        ?	SecretKeyPacket.UsageSha1
                        :	SecretKeyPacket.UsageChecksum;

                    this.secret = new SecretKeyPacket(pubPk, encAlgorithm, usage, s2k, iv, encData);
                }
                else
                {
                    this.secret = new SecretKeyPacket(pubPk, encAlgorithm, null, null, bOutData);
                }

                this.trust = null;
            }
            catch (PgpException e)
            {
                throw e;
            }
            catch (Exception e)
            {
                throw new PgpException("Exception encrypting key", e);
            }

            this.keySigs = new ArrayList();
        }
Пример #41
0
 /// <summary>Copy constructor - master key.</summary>
 private PgpSecretKey(
     SecretKeyPacket secret,
     TrustPacket     trust,
     ArrayList       keySigs,
     ArrayList       ids,
     ArrayList       idTrusts,
     ArrayList       idSigs,
     PgpPublicKey    pub)
 {
     this.secret = secret;
     this.trust = trust;
     this.keySigs = keySigs;
     this.ids = ids;
     this.idTrusts = idTrusts;
     this.idSigs = idSigs;
     this.pub = pub;
 }
        /// <summary>
        /// Return a copy of the passed in secret key, encrypted using a new password
        /// and the passed in algorithm.
        /// </summary>
        /// <param name="key">The PgpSecretKey to be copied.</param>
        /// <param name="oldPassPhrase">The current password for the key.</param>
        /// <param name="newPassPhrase">The new password for the key.</param>
        /// <param name="newEncAlgorithm">The algorithm to be used for the encryption.</param>
        /// <param name="rand">Source of randomness.</param>
        public static PgpSecretKey CopyWithNewPassword(IPgpSecretKey key, char[] oldPassPhrase, char[] newPassPhrase, SymmetricKeyAlgorithmTag newEncAlgorithm, SecureRandom rand)
        {
            var rawKeyData = key.ExtractKeyData(oldPassPhrase);
            var s2KUsage = key.SecretPacket.S2KUsage;
            byte[] iv = null;
            S2k s2K = null;
            byte[] keyData;

            if (newEncAlgorithm == SymmetricKeyAlgorithmTag.Null)
            {
                s2KUsage = SecretKeyPacket.UsageNone;
                if (key.SecretPacket.S2KUsage == SecretKeyPacket.UsageSha1)   // SHA-1 hash, need to rewrite Checksum
                {
                    keyData = new byte[rawKeyData.Length - 18];

                    Array.Copy(rawKeyData, 0, keyData, 0, keyData.Length - 2);

                    var check = Checksum(false, keyData, keyData.Length - 2);

                    keyData[keyData.Length - 2] = check[0];
                    keyData[keyData.Length - 1] = check[1];
                }
                else
                {
                    keyData = rawKeyData;
                }
            }
            else
            {
                try
                {
                    keyData = EncryptKeyData(rawKeyData, newEncAlgorithm, newPassPhrase, rand, out s2K, out iv);
                }
                catch (PgpException)
                {
                    throw;
                }
                catch (Exception e)
                {
                    throw new PgpException("Exception encrypting key", e);
                }
            }

            SecretKeyPacket secret;
            if (key.SecretPacket is SecretSubkeyPacket)
            {
                secret = new SecretSubkeyPacket(key.SecretPacket.PublicKeyPacket,
                    newEncAlgorithm, s2KUsage, s2K, iv, keyData);
            }
            else
            {
                secret = new SecretKeyPacket(key.SecretPacket.PublicKeyPacket,
                    newEncAlgorithm, s2KUsage, s2K, iv, keyData);
            }

            return new PgpSecretKey(secret, key.PublicKey);
        }
        public void SignKeyBindingSignature(PublicKeyPacket pkpPrimaryKey, SecretKeyPacket skpPrimaryKey, string strPassphrase, DateTime expirationTime, bool revocable)
        {
            byte[] bSubKey = new byte[pkpSubkey.Body.Length + 3];
            bSubKey[0] = 0x99;
            bSubKey[1] = (byte)((pkpSubkey.Body.Length >> 8) & 0xFF);
            bSubKey[2] = (byte)(pkpSubkey.Body.Length & 0xFF);
            Array.Copy(pkpSubkey.Body, 0, bSubKey, 3, pkpSubkey.Body.Length);

            byte[] bPrimaryKey = new byte[pkpPrimaryKey.Body.Length + 3];
            bPrimaryKey[0] = 0x99;
            bPrimaryKey[1] = (byte)((pkpPrimaryKey.Body.Length >> 8) & 0xFF);
            bPrimaryKey[2] = (byte)(pkpPrimaryKey.Body.Length & 0xFF);
            Array.Copy(pkpPrimaryKey.Body, 0, bPrimaryKey, 3, pkpPrimaryKey.Body.Length);

            byte[] bData = new byte[bPrimaryKey.Length + bSubKey.Length];
            Array.Copy(bPrimaryKey, 0, bData, 0, bPrimaryKey.Length);
            Array.Copy(bSubKey, 0, bData, bPrimaryKey.Length, bSubKey.Length);

            SignaturePacket spKeyBindingSig = new SignaturePacket();
            spKeyBindingSig.Version = SignaturePacketVersionNumbers.v4;
            spKeyBindingSig.HashAlgorithm = HashAlgorithms.SHA1;
            spKeyBindingSig.KeyID = pkpPrimaryKey.KeyID;
            spKeyBindingSig.SignatureType = SignatureTypes.SubkeyBindingSignature;
            if(expirationTime.Ticks != 0) {
                SignatureSubPacket sspExpiration = new SignatureSubPacket();
                sspExpiration.Type = SignatureSubPacketTypes.KeyExpirationTime;
                sspExpiration.KeyExpirationTime = new DateTime(expirationTime.Ticks + (new DateTime(1970,1,2)).Ticks - pkpPrimaryKey.TimeCreated.Ticks);
                spKeyBindingSig.AddSubPacket(sspExpiration, true);
            }
            if(!revocable) {
                SignatureSubPacket sspRevocable = new SignatureSubPacket();
                sspRevocable.Type = SignatureSubPacketTypes.Revocable;
                sspRevocable.Revocable = revocable;
                spKeyBindingSig.AddSubPacket(sspRevocable, true);
            }
            spKeyBindingSig.Sign(bData, skpPrimaryKey, strPassphrase);
            this.KeyBindingSignature = spKeyBindingSig;
        }