我们使用 BouncyCastle API 为客户端加密文件。他得到了“仅限您的眼睛”的字样。尝试解密时来自 PGP 的消息。为什么?

发布于 2024-11-08 01:26:30 字数 4182 浏览 0 评论 0原文

我们使用 Bouncy.Castle C# API 进行 PGP 加密。我绝不是 PGP 加密和各种可用选项方面的专家。

加密似乎运行良好,但是,当客户端尝试解密时,他说 PGP 不会输出到文件,而只会输出到屏幕,因为它被标记为“仅供您查看”。这是 --verbose 消息:

pgp --decrypt Client_FileExport_20110510_020011.zip.pgp
  Client_FileExport_20110511_132203.zip.pgp --info verbose

McAfee E-Business Server v8.5 - Full License
(c) 1991-2006 McAfee, Inc.  All Rights Reserved.

Setting temporary directory to C:\DOCUME~1\$963\LOCALS~1\Temp\
Decoding data....

event 1: initial
event 13: BeginLex
event 8: Analyze
File is encrypted.  event 9: Recipients
Secret key is required to read it.
Key for user ID "Client_RSAv4_Key <[email protected]>"
event 6: Passphrase
You need a pass phrase to unlock your secret key.

Enter pass phrase:

event 23: Decryption

symmetric cipher used: CAST5
event 11: Output options
typecode: 0062
for your eyes only


This message is marked "For your eyes only".  Display now (Y/n)?

我不知道如何调试它。有人知道吗?

这是我们用来加密数据的通用代码。在这种情况下,我们不会签署文档,因此可以忽略该部分代码。

private void EncryptImpl(Stream inputStream, Stream outputStream, bool signOutput)
    {
        const int BUFFER_SIZE = 1 << 16; // should always be power of 2
        bool armor = true;
        bool withIntegrityCheck = true;

        if (armor)
            outputStream = new ArmoredOutputStream(outputStream);

        var encKey = PgpHelper.ReadPublicKey(this.EncryptionPublicKey);

        // Init encrypted data generator
        PgpEncryptedDataGenerator encryptedDataGenerator =
            new PgpEncryptedDataGenerator(SymmetricKeyAlgorithmTag.Cast5, withIntegrityCheck, new SecureRandom());
        encryptedDataGenerator.AddMethod(encKey);
        Stream encryptedOut = encryptedDataGenerator.Open(outputStream, new byte[BUFFER_SIZE]);

        // Init compression
        PgpCompressedDataGenerator compressedDataGenerator = new PgpCompressedDataGenerator(CompressionAlgorithmTag.Zip);
        Stream compressedOut = compressedDataGenerator.Open(encryptedOut);

        PgpSignatureGenerator signatureGenerator = null;
        if (signOutput)
        {
            // Init signature
            var pgpSecKey = PgpHelper.ReadSecretKey(this.OrigamiSecretKey);
            PgpPrivateKey pgpPrivKey = pgpSecKey.ExtractPrivateKey(this.PassPhrase.ToCharArray());
            signatureGenerator = new PgpSignatureGenerator(pgpSecKey.PublicKey.Algorithm, HashAlgorithmTag.Sha1);
            signatureGenerator.InitSign(PgpSignature.BinaryDocument, pgpPrivKey);
            foreach (string userId in pgpSecKey.PublicKey.GetUserIds())
            {
                PgpSignatureSubpacketGenerator spGen = new PgpSignatureSubpacketGenerator();
                spGen.SetSignerUserId(false, userId);
                signatureGenerator.SetHashedSubpackets(spGen.Generate());
                // Just the first one!
                break;
            }
            signatureGenerator.GenerateOnePassVersion(false).Encode(compressedOut);
        }

        // Create the Literal Data generator output stream
        PgpLiteralDataGenerator literalDataGenerator = new PgpLiteralDataGenerator();

        // TODO: Use lastwritetime from source file
        Stream literalOut = literalDataGenerator.Open(compressedOut, PgpLiteralData.Binary,
            PgpLiteralDataGenerator.Console, DateTime.Now, new byte[BUFFER_SIZE]);

        // Open the input file
        byte[] buf = new byte[BUFFER_SIZE];
        int len;
        while ((len = inputStream.Read(buf, 0, buf.Length)) > 0)
        {
            literalOut.Write(buf, 0, len);

            if (signOutput)
                signatureGenerator.Update(buf, 0, len);
        }

        literalOut.Close();
        literalDataGenerator.Close();

        if (signOutput)
            signatureGenerator.Generate().Encode(compressedOut);

        compressedOut.Close();
        compressedDataGenerator.Close();
        encryptedOut.Close();
        encryptedDataGenerator.Close();
        inputStream.Close();

        if (armor)
            outputStream.Close();
    }

We use the Bouncy.Castle C# API to do PGP encryption. I am by no means an expert on PGP encryption and the various options available.

The encryption seems to run fine, however, when the client tries to decrypt it, he says that PGP won't output to file but only output to screen because it is marked "For your eyes only." This is the --verbose message:

pgp --decrypt Client_FileExport_20110510_020011.zip.pgp
  Client_FileExport_20110511_132203.zip.pgp --info verbose

McAfee E-Business Server v8.5 - Full License
(c) 1991-2006 McAfee, Inc.  All Rights Reserved.

Setting temporary directory to C:\DOCUME~1\$963\LOCALS~1\Temp\
Decoding data....

event 1: initial
event 13: BeginLex
event 8: Analyze
File is encrypted.  event 9: Recipients
Secret key is required to read it.
Key for user ID "Client_RSAv4_Key <[email protected]>"
event 6: Passphrase
You need a pass phrase to unlock your secret key.

Enter pass phrase:

event 23: Decryption

symmetric cipher used: CAST5
event 11: Output options
typecode: 0062
for your eyes only


This message is marked "For your eyes only".  Display now (Y/n)?

I have no clue as to how to go about debugging this. Anybody know?

Here is the general code we use to encrypt data. In this scenario we are not signing the document, so that portion of the code can be ignored.

private void EncryptImpl(Stream inputStream, Stream outputStream, bool signOutput)
    {
        const int BUFFER_SIZE = 1 << 16; // should always be power of 2
        bool armor = true;
        bool withIntegrityCheck = true;

        if (armor)
            outputStream = new ArmoredOutputStream(outputStream);

        var encKey = PgpHelper.ReadPublicKey(this.EncryptionPublicKey);

        // Init encrypted data generator
        PgpEncryptedDataGenerator encryptedDataGenerator =
            new PgpEncryptedDataGenerator(SymmetricKeyAlgorithmTag.Cast5, withIntegrityCheck, new SecureRandom());
        encryptedDataGenerator.AddMethod(encKey);
        Stream encryptedOut = encryptedDataGenerator.Open(outputStream, new byte[BUFFER_SIZE]);

        // Init compression
        PgpCompressedDataGenerator compressedDataGenerator = new PgpCompressedDataGenerator(CompressionAlgorithmTag.Zip);
        Stream compressedOut = compressedDataGenerator.Open(encryptedOut);

        PgpSignatureGenerator signatureGenerator = null;
        if (signOutput)
        {
            // Init signature
            var pgpSecKey = PgpHelper.ReadSecretKey(this.OrigamiSecretKey);
            PgpPrivateKey pgpPrivKey = pgpSecKey.ExtractPrivateKey(this.PassPhrase.ToCharArray());
            signatureGenerator = new PgpSignatureGenerator(pgpSecKey.PublicKey.Algorithm, HashAlgorithmTag.Sha1);
            signatureGenerator.InitSign(PgpSignature.BinaryDocument, pgpPrivKey);
            foreach (string userId in pgpSecKey.PublicKey.GetUserIds())
            {
                PgpSignatureSubpacketGenerator spGen = new PgpSignatureSubpacketGenerator();
                spGen.SetSignerUserId(false, userId);
                signatureGenerator.SetHashedSubpackets(spGen.Generate());
                // Just the first one!
                break;
            }
            signatureGenerator.GenerateOnePassVersion(false).Encode(compressedOut);
        }

        // Create the Literal Data generator output stream
        PgpLiteralDataGenerator literalDataGenerator = new PgpLiteralDataGenerator();

        // TODO: Use lastwritetime from source file
        Stream literalOut = literalDataGenerator.Open(compressedOut, PgpLiteralData.Binary,
            PgpLiteralDataGenerator.Console, DateTime.Now, new byte[BUFFER_SIZE]);

        // Open the input file
        byte[] buf = new byte[BUFFER_SIZE];
        int len;
        while ((len = inputStream.Read(buf, 0, buf.Length)) > 0)
        {
            literalOut.Write(buf, 0, len);

            if (signOutput)
                signatureGenerator.Update(buf, 0, len);
        }

        literalOut.Close();
        literalDataGenerator.Close();

        if (signOutput)
            signatureGenerator.Generate().Encode(compressedOut);

        compressedOut.Close();
        compressedDataGenerator.Close();
        encryptedOut.Close();
        encryptedDataGenerator.Close();
        inputStream.Close();

        if (armor)
            outputStream.Close();
    }

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

眉目亦如画i 2024-11-15 01:26:31

我猜测是 PgpLiteralDataGenerator.Console 导致它仅显示在客户端计算机的控制台中。

Stream literalOut = literalDataGenerator.Open(
    compressedOut, 
    PgpLiteralData.Binary,             
    PgpLiteralDataGenerator.Console,
    DateTime.Now, 
    new byte[BUFFER_SIZE]);

I'm guessing that PgpLiteralDataGenerator.Console is what is causing it to show up only in the console of the client machine.

Stream literalOut = literalDataGenerator.Open(
    compressedOut, 
    PgpLiteralData.Binary,             
    PgpLiteralDataGenerator.Console,
    DateTime.Now, 
    new byte[BUFFER_SIZE]);
旧情勿念 2024-11-15 01:26:31

当加密文件不包含原始文件的名称时,会显示此消息。如果您不加密文件,则可以将几乎任何内容放入该字段(假定它构成文件名,对目标系统有效)。

This message is shown when the encrypted file doesn't include a name of the original file. If you are not encrypting the file, you can put almost anything to that field (given that it constitutes a file name, valid for the target system).

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文