使用OAEP Padding错误,RSA Decryption第二次失败

时间:2015-03-15 19:29:04

标签: c# encryption tcp stream cryptography

要交换AES加密消息,我使用RSA为每条消息编码IV并将其发送到另一个客户端。这在我第一次发送消息时成功,但在发送第二条消息时失败。客户端无法解密带有OAEP填充错误的消息的IV。

这是我的代码:

writeAes(Encoding.UTF8.GetBytes("12345"), rmAes.Key, RSAprovider.ToXmlString(false)); // These are just some sample messages
writeAes(Encoding.UTF8.GetBytes("67890"), rmAes.Key, RSAprovider.ToXmlString(false));

public void writeAes(TcpClient client, byte[] writeBuffer, int offset, byte[] AESkey, string RSAXml) //Some of these arguments are optional
{
    using (RijndaelManaged rijAlg = new RijndaelManaged())
    {
        rijAlg.KeySize = 128;
        rijAlg.Key = AESkey;
        rijAlg.GenerateIV();
        // Send IV
        using (RSACryptoServiceProvider RSAprovider = new RSACryptoServiceProvider(4096))
        {
            RSAprovider.PersistKeyInCsp = false;
            RSAprovider.FromXmlString(RSAXml);
            this.write(client, RSAprovider.Encrypt(rijAlg.IV, true));
            logger.Trace("Sent AES IV:\n{0}", BitConverter.ToString(rijAlg.IV).Replace("-", ""));
        }
        // Send Rijndael-encrypted Message
        CryptoStream csEncrypt = null;
        try
        {
            ICryptoTransform encryptor = rijAlg.CreateEncryptor(rijAlg.Key, rijAlg.IV);
            csEncrypt = new CryptoStream(client.GetStream(), encryptor, CryptoStreamMode.Write);
            csEncrypt.Write(writeBuffer, offset, writeBuffer.Length);
            csEncrypt.FlushFinalBlock();
            encryptor.Dispose();
        }
        finally
        {
            /*if (csEncrypt != null)
                csEncrypt.Dispose();*/
            // TODO: This needs to be disposed somehow but leave the NetworkStream open
        }
    }
}

接收:

logger.Debug("Got AES-Message:\n" + Encoding.UTF8.GetString(readAes(connectedClient, new byte[5], 0, aesKey, RSAprovider.ToXmlString(true))));
logger.Debug("Got AES-Message:\n" + Encoding.UTF8.GetString(readAes(connectedClient, new byte[5], 0, aesKey, RSAprovider.ToXmlString(true))));

public byte[] readAes(TcpClient client, byte[] readBuffer,int offset, byte[] AESkey, string RSAXml) //Some of these arguments are optional
{
    using (RijndaelManaged rijAlg = new RijndaelManaged())
    {
        rijAlg.KeySize = 128;
        rijAlg.Key = AESkey;
        using (RSACryptoServiceProvider RSAprovider = new RSACryptoServiceProvider(4096))
        {
            RSAprovider.PersistKeyInCsp = false;
            RSAprovider.FromXmlString(RSAXml);
            rijAlg.IV = RSAprovider.Decrypt(this.read(client, new byte[512]), true); //This is where the error occurs on the second message
            logger.Trace("Got AES IV:\n{0}", BitConverter.ToString(rijAlg.IV).Replace("-", ""));
        }
        CryptoStream cryptoStream = null;
        try
        {
            ICryptoTransform decryptor = rijAlg.CreateDecryptor(rijAlg.Key, rijAlg.IV);
            cryptoStream = new CryptoStream(client.GetStream(), decryptor, CryptoStreamMode.Read);
            int read = 0;
            int error = 0;
            while (read < readBuffer.Length)
            {
                int bytesRead = cryptoStream.Read(readBuffer, read, readBuffer.Length - read);
                read += bytesRead;
                if (bytesRead == 0 && read != error)
                {
                    logger.Debug("Reached end of stream at {0}. Waiting for more data...", read);
                    error = read;
                }
            }
            decryptor.Dispose();
            return readBuffer;
        }
        finally
        {
            /*if (cryptoStream != null)
                cryptoStream.Dispose();*/
            // TODO: This needs to be disposed somehow but leave the NetworkStream open
        }
    }
}

我的猜测是,CryptoStream尝试解密的数据比读取的数据多,并且弄乱了IV,但我不知道我可以改变什么来解决这个问题。

0 个答案:

没有答案