2012-05-28 4 views
1

이전에 암호화 된 데이터의 해독에 문제가 있습니다. 나는 트리플 DES 효과를 얻기 위해 3 개의 서로 다른 키로 암호화 암호화 - 암호 해독 암호화를 사용하고 있습니다. 암호화 기능이 올바르게 작동하지만 8 바이트 배열을 반환하지만 암호 해독 함수는 빈 배열을 반환합니다.DES ECB C# 암호화/암호 해독

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; 
    } 

내가 뭘 잘못하고 있니?

+0

아마도 최종 마무리 (플러시 최종 블록 또는 그와 유사한 것) 또는 패딩 관련. – CodesInChaos

+0

감사합니다. "Flush final block"과 패딩이 도움이되지 않았습니다. – user1421600

+1

btw 왜 처음에는 이상한 일을하고 있습니까? .net에는 3DES 지원이 내장되어 있으며 ECB는 대부분의 응용 프로그램에서 잘못된 선택입니다. – CodesInChaos

답변

0

TripleDES 이미 프레임 워크에 존재하지만, 교육용으로 자신의 구현을 롤업하고 싶습니다.

당신은 일을 필요 이상으로 복잡하게 만듭니다. 당신이 스트림을 사용하고 있기 때문에 당신은 왜 대신에 그들 모두를 체인하지 않습니다 using 블록의 사용의

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; 
} 

만들기 메모와 패딩은 다른 스트림에 적용되는 방법도.

프레임 워크 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; 
} 

당신은 당신이 TripleDES에 대한 24 비트 키가 실제로 하나 개의 배열에 넣어 3 키는 것을 기억해야 다음 두 가지 암호화 방법의 결과를 비교하려면 :

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

cryptoStream.FlushFinalBlock()이 필요합니다. 그 코드는 훌륭하게 작동합니다 :

//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(); 
    }