简体   繁体   English

DES ECB C#加密/解密

[英]DES ECB C# encryption/decryption

I have a problem with decryption of data previously encrypted. 我对以前加密的数据解密有问题。 I am using the sequential encrypt-decrypt-encrypt with three different keys to get triple des effect. 我正在使用具有三个不同密钥的顺序加密-解密-加密来获得三重des效果。 The encryption function works correctly (returns 8-byte array), but the decryption function returns empty array. 加密功能正常工作(返回8字节数组),但解密功能返回空数组。

    public static byte[] EncryptDES(byte[] clearData, byte[] key) 
    { 
        DES desEncrypt = new DESCryptoServiceProvider(); 
        desEncrypt.Mode = CipherMode.ECB; 
        desEncrypt.Key = key; 
        ICryptoTransform transForm = desEncrypt.CreateEncryptor(); 
        MemoryStream encryptedStream = new MemoryStream(); 
        CryptoStream cryptoStream = new CryptoStream(encryptedStream, transForm, CryptoStreamMode.Write); 
        cryptoStream.Write(clearData, 0, clearData.Length); 
        byte [] encryptedData = encryptedStream.ToArray(); 
        return encryptedData;
    }

    public static byte[] DecryptDES(byte[] clearData, byte[] key)
    {
        DES desDecrypt = new DESCryptoServiceProvider();
        desDecrypt.Mode = CipherMode.ECB;
        desDecrypt.Key = key;
        ICryptoTransform transForm = desDecrypt.CreateDecryptor();
        MemoryStream decryptedStream = new MemoryStream();
        CryptoStream cryptoStream = new CryptoStream(decryptedStream, transForm, CryptoStreamMode.Write);
        cryptoStream.Write(clearData, 0, clearData.Length);
        byte[] encryptedData = decryptedStream.ToArray();
        return encryptedData;
    }

    public static byte[] Encrypt3DES(byte[] clearData, byte[] key0, byte[] key1, byte[] key2) 
    {
        byte[] encryptedData1 = new byte[clearData.Length];
        byte[] encryptedData2 = new byte[clearData.Length];
        byte[] encryptedData3 = new byte[clearData.Length];
        encryptedData1 = DESCrypto.EncryptDES(clearData    , key0);
        encryptedData2 = DESCrypto.DecryptDES(encryptedData1, key1);
        encryptedData3 = DESCrypto.EncryptDES(encryptedData2, key2);
        return encryptedData3;
    } 

What am I doing wrong? 我究竟做错了什么?

TripleDES already exist in the Framework but I guess you want to roll your own implementation for educational purposes. 该框架中已经存在TripleDES ,但我想您想出于教育目的推出自己的实现。

You're making things more complicated than necessary. 您正在使事情变得不必要的复杂。 Since you are using streams why don't you chain them all instead: 由于您正在使用流,所以为什么不将它们全部链接起来:

public static byte[] TripleDESEncrypt(byte[] plainText, byte[] key1, byte[] key2, byte[] key3)
{
  var des = DES.Create();
  des.Mode = CipherMode.ECB;

  des.Padding = PaddingMode.None;
  des.Key = key3;
  var encryptor1 = des.CreateEncryptor();

  des.Key = key2;
  var decryptor = des.CreateDecryptor();

  des.Padding = PaddingMode.PKCS7;
  des.Key = key1;
  var encryptor2 = des.CreateEncryptor();

  byte[] result;
  using (var ms = new MemoryStream())
  {
    using (var cs1 = new CryptoStream(ms, encryptor1, CryptoStreamMode.Write))
    using (var cs2 = new CryptoStream(cs1, decryptor, CryptoStreamMode.Write))
    using (var cs3 = new CryptoStream(cs2, encryptor2, CryptoStreamMode.Write))
      cs3.Write(plainText, 0, plainText.Length);

    result = ms.ToArray();
  }


  return result;
}

public static byte[] TripleDESDecrypt(byte[] cipherText, byte[] key1, byte[] key2, byte[] key3)
{
  var des = DES.Create();
  des.Mode = CipherMode.ECB;

  des.Padding = PaddingMode.PKCS7;
  des.Key = key1;
  var decryptor1 = des.CreateDecryptor();

  des.Padding = PaddingMode.None;
  des.Key = key2;
  var encryptor = des.CreateEncryptor();

  des.Key = key3;
  var decryptor2 = des.CreateDecryptor();

  byte[] result;
  using (var ms = new MemoryStream())
  {
    using (var cs1 = new CryptoStream(ms, decryptor1, CryptoStreamMode.Write))
    using (var cs2 = new CryptoStream(cs1, encryptor, CryptoStreamMode.Write))
    using (var cs3 = new CryptoStream(cs2, decryptor2, CryptoStreamMode.Write))
      cs3.Write(cipherText, 0, cipherText.Length);

    result = ms.ToArray();
  }


  return result;
}

Make note of the usage of using blocks and also how the padding is applied to the different streams. 记录使用using块的用法,以及如何将填充应用于不同的流。

The framework TripleDES is about 2.5 times faster than the above code. TripleDES框架比上述代码快约2.5倍。

public static byte[] TripleDESEncryptFramework(byte[] plainText, byte[] key)
{
  var tdes = TripleDES.Create();
  tdes.Mode = CipherMode.ECB;
  tdes.Padding = PaddingMode.PKCS7;
  tdes.Key = key;

  var encryptor = tdes.CreateEncryptor();

  byte[] result;
  using (var ms = new MemoryStream())
  {
    using (var cs = new CryptoStream(ms, encryptor, CryptoStreamMode.Write))
      cs.Write(plainText, 0, plainText.Length);

    result = ms.ToArray();
  }

  return result;
}

If you want to compare the results of the two different encryption methods then you need to remember that the 24-bit key for TripleDES is actually the 3 keys put in one array: 如果要比较两种不同加密方法的结果,则需要记住, TripleDES的24位密钥实际上是放在一个数组中的3个密钥:

[  key1  ][  key2  ][  key3  ]
==============================
[            key             ]

Just need cryptoStream.FlushFinalBlock(). 只需要cryptoStream.FlushFinalBlock()。 Its code works great: 它的代码效果很好:

   //ENCRYPT
   public static byte[] EncryptDES(byte[] clearData, byte[] key) 
   { 
       DES desEncrypt = new DESCryptoServiceProvider(); 
       desEncrypt.Mode = CipherMode.ECB; 
       desEncrypt.Key = key; 
       ICryptoTransform transForm = desEncrypt.CreateEncryptor(); 
       MemoryStream encryptedStream = new MemoryStream(); 
       CryptoStream cryptoStream = new CryptoStream(encryptedStream, transForm, CryptoStreamMode.Write); 
       cryptoStream.Write(clearData, 0, clearData.Length);
       cryptoStream.FlushFinalBlock();
       return encryptedStream.ToArray();
   }

   //DECRYPT
   public static byte[] DecryptDES(byte[] clearData, byte[] key)
   {
       DES desDecrypt = new DESCryptoServiceProvider();
       desDecrypt.Mode = CipherMode.ECB;
       desDecrypt.Key = key;
       ICryptoTransform transForm = desDecrypt.CreateDecryptor();
       MemoryStream decryptedStream = new MemoryStream();
       CryptoStream cryptoStream = new CryptoStream(decryptedStream, transForm, CryptoStreamMode.Write);
       cryptoStream.Write(clearData, 0, clearData.Length);
       cryptoStream.FlushFinalBlock();
       return decryptedStream.ToArray();
   }

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM