init commit
This commit is contained in:
@@ -0,0 +1,213 @@
|
||||
using System;
|
||||
using System.Collections;
|
||||
using System.IO;
|
||||
using Org.BouncyCastle.Security;
|
||||
using Org.BouncyCastle.Utilities;
|
||||
using Org.BouncyCastle.Utilities.Collections;
|
||||
|
||||
namespace Org.BouncyCastle.Bcpg.OpenPgp;
|
||||
|
||||
public class PgpSecretKeyRing : PgpKeyRing
|
||||
{
|
||||
private readonly IList keys;
|
||||
|
||||
private readonly IList extraPubKeys;
|
||||
|
||||
internal PgpSecretKeyRing(IList keys)
|
||||
: this(keys, Platform.CreateArrayList())
|
||||
{
|
||||
}
|
||||
|
||||
private PgpSecretKeyRing(IList keys, IList extraPubKeys)
|
||||
{
|
||||
this.keys = keys;
|
||||
this.extraPubKeys = extraPubKeys;
|
||||
}
|
||||
|
||||
public PgpSecretKeyRing(byte[] encoding)
|
||||
: this(new MemoryStream(encoding))
|
||||
{
|
||||
}
|
||||
|
||||
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 var ids, out var idTrusts, out var 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));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public PgpPublicKey GetPublicKey()
|
||||
{
|
||||
return ((PgpSecretKey)keys[0]).PublicKey;
|
||||
}
|
||||
|
||||
public PgpSecretKey GetSecretKey()
|
||||
{
|
||||
return (PgpSecretKey)keys[0];
|
||||
}
|
||||
|
||||
public IEnumerable GetSecretKeys()
|
||||
{
|
||||
return new EnumerableProxy(keys);
|
||||
}
|
||||
|
||||
public PgpSecretKey GetSecretKey(long keyId)
|
||||
{
|
||||
foreach (PgpSecretKey key in keys)
|
||||
{
|
||||
if (keyId == key.KeyId)
|
||||
{
|
||||
return key;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public IEnumerable GetExtraPublicKeys()
|
||||
{
|
||||
return new EnumerableProxy(extraPubKeys);
|
||||
}
|
||||
|
||||
public byte[] GetEncoded()
|
||||
{
|
||||
MemoryStream memoryStream = new MemoryStream();
|
||||
Encode(memoryStream);
|
||||
return memoryStream.ToArray();
|
||||
}
|
||||
|
||||
public void Encode(Stream outStr)
|
||||
{
|
||||
if (outStr == null)
|
||||
{
|
||||
throw new ArgumentNullException("outStr");
|
||||
}
|
||||
foreach (PgpSecretKey key in keys)
|
||||
{
|
||||
key.Encode(outStr);
|
||||
}
|
||||
foreach (PgpPublicKey extraPubKey in extraPubKeys)
|
||||
{
|
||||
extraPubKey.Encode(outStr);
|
||||
}
|
||||
}
|
||||
|
||||
public static PgpSecretKeyRing ReplacePublicKeys(PgpSecretKeyRing secretRing, PgpPublicKeyRing publicRing)
|
||||
{
|
||||
IList list = Platform.CreateArrayList(secretRing.keys.Count);
|
||||
foreach (PgpSecretKey key in secretRing.keys)
|
||||
{
|
||||
PgpPublicKey publicKey = publicRing.GetPublicKey(key.KeyId);
|
||||
list.Add(PgpSecretKey.ReplacePublicKey(key, publicKey));
|
||||
}
|
||||
return new PgpSecretKeyRing(list);
|
||||
}
|
||||
|
||||
public static PgpSecretKeyRing CopyWithNewPassword(PgpSecretKeyRing ring, char[] oldPassPhrase, char[] newPassPhrase, SymmetricKeyAlgorithmTag newEncAlgorithm, SecureRandom rand)
|
||||
{
|
||||
IList list = Platform.CreateArrayList(ring.keys.Count);
|
||||
foreach (PgpSecretKey secretKey in ring.GetSecretKeys())
|
||||
{
|
||||
if (secretKey.IsPrivateKeyEmpty)
|
||||
{
|
||||
list.Add(secretKey);
|
||||
}
|
||||
else
|
||||
{
|
||||
list.Add(PgpSecretKey.CopyWithNewPassword(secretKey, oldPassPhrase, newPassPhrase, newEncAlgorithm, rand));
|
||||
}
|
||||
}
|
||||
return new PgpSecretKeyRing(list, ring.extraPubKeys);
|
||||
}
|
||||
|
||||
public static PgpSecretKeyRing InsertSecretKey(PgpSecretKeyRing secRing, PgpSecretKey secKey)
|
||||
{
|
||||
IList list = Platform.CreateArrayList(secRing.keys);
|
||||
bool flag = false;
|
||||
bool flag2 = false;
|
||||
for (int i = 0; i != list.Count; i++)
|
||||
{
|
||||
PgpSecretKey pgpSecretKey = (PgpSecretKey)list[i];
|
||||
if (pgpSecretKey.KeyId == secKey.KeyId)
|
||||
{
|
||||
flag = true;
|
||||
list[i] = secKey;
|
||||
}
|
||||
if (pgpSecretKey.IsMasterKey)
|
||||
{
|
||||
flag2 = true;
|
||||
}
|
||||
}
|
||||
if (!flag)
|
||||
{
|
||||
if (secKey.IsMasterKey)
|
||||
{
|
||||
if (flag2)
|
||||
{
|
||||
throw new ArgumentException("cannot add a master key to a ring that already has one");
|
||||
}
|
||||
list.Insert(0, secKey);
|
||||
}
|
||||
else
|
||||
{
|
||||
list.Add(secKey);
|
||||
}
|
||||
}
|
||||
return new PgpSecretKeyRing(list, secRing.extraPubKeys);
|
||||
}
|
||||
|
||||
public static PgpSecretKeyRing RemoveSecretKey(PgpSecretKeyRing secRing, PgpSecretKey secKey)
|
||||
{
|
||||
IList list = Platform.CreateArrayList(secRing.keys);
|
||||
bool flag = false;
|
||||
for (int i = 0; i < list.Count; i++)
|
||||
{
|
||||
PgpSecretKey pgpSecretKey = (PgpSecretKey)list[i];
|
||||
if (pgpSecretKey.KeyId == secKey.KeyId)
|
||||
{
|
||||
flag = true;
|
||||
list.RemoveAt(i);
|
||||
}
|
||||
}
|
||||
if (!flag)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
return new PgpSecretKeyRing(list, secRing.extraPubKeys);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user