[ACCEPTED]-PartialInputStream during Bouncycastle PGP decryption-pgp

Accepted answer
Score: 14

Anybody who is struggeling heres a working 1 code:

using System;
using System.Xml;
using System.IO;
using System.Security.Cryptography;
using System.Security.Cryptography.Xml;
using System.Text;

using Org.BouncyCastle.Bcpg.OpenPgp;
using Org.BouncyCastle.Security;
using Org.BouncyCastle.Utilities.IO;
using Org.BouncyCastle.Utilities.Encoders;
using Org.BouncyCastle.Bcpg;

class Program
    private static PgpPublicKey ReadPublicKey(Stream inputStream)

        inputStream = PgpUtilities.GetDecoderStream(inputStream);

        PgpPublicKeyRingBundle pgpPub = new PgpPublicKeyRingBundle(inputStream);

        // 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.

        foreach (PgpPublicKeyRing kRing in pgpPub.GetKeyRings())
            foreach (PgpPublicKey k in kRing.GetPublicKeys())
                if (k.IsEncryptionKey)
                    return k;

        throw new ArgumentException("Can't find encryption key in key ring.");

    private static byte[] EncryptFile(byte[] clearData, string fileName, PgpPublicKey encKey, bool withIntegrityCheck)

        MemoryStream bOut = new MemoryStream();

        PgpCompressedDataGenerator comData = new PgpCompressedDataGenerator(

        Stream cos = comData.Open(bOut); // open it with the final destination
        PgpLiteralDataGenerator lData = new PgpLiteralDataGenerator();

        // we want to Generate compressed data. This might be a user option later,
        // in which case we would pass in bOut.
        Stream pOut = lData.Open(
            cos,                    // the compressed output stream
            fileName,               // "filename" to store
            clearData.Length,       // length of clear data
            DateTime.UtcNow         // current time

        pOut.Write(clearData, 0, clearData.Length);


        PgpEncryptedDataGenerator cPk = new PgpEncryptedDataGenerator(SymmetricKeyAlgorithmTag.Cast5, new SecureRandom());


        byte[] bytes = bOut.ToArray();

        MemoryStream encOut = new MemoryStream();
        Stream os = encOut;

        Stream cOut = cPk.Open(os, bytes.Length);
        cOut.Write(bytes, 0, bytes.Length);  // obtain the actual bytes from the compressed stream


        return encOut.ToArray();

    static void Main(string[] args)
            byte[] dataBytes = File.ReadAllBytes("test.xml");
            Stream keyIn = File.OpenRead("cert.asc");
            Stream outStream = File.Create("data.bpg");
            byte[] encrypted = EncryptFile(dataBytes, "data", ReadPublicKey(keyIn), false);
            outStream.Write(encrypted, 0, encrypted.Length);
        catch (Exception e)

Score: 1

I got the same error, when I tried to read 5 from the 'stream'.

PgpLiteralData ld = (PgpLiteralData)message;
var stream = ld.GetInputStream(); // the stream to read form

A solution for me was 4 to copy the stream to a new .net Stream 3 object like MemoryStream. And after that read from the 2 memoryStream object.

So, my base stream type 1 has nothing to do with Org.BouncyCastle.Bcpg stream types.

More Related questions