2010-02-04 18 views
6

Sto cercando di inviare alcuni dati crittografati dal mio sito di SharePoint al sito PeopleSoft della mia azienda. La gente di PeopleSoft insiste che devo usare la libreria OpenSSL per la mia crittografia. Ho scaricato e installato il progetto OpenSSL.Net da SourceForge.Come utilizzare il wrapper OpenSSL.Net C# per crittografare una stringa con AES?

Per i miei scopi, devo semplicemente crittografare una stringa con AES. So come farlo con la libreria System.Security.Cryptography, ma sto avendo un momento molto difficile per tradurre questo lato OpenSSL.Net. Molto frustrante, dal momento che posso vedere tutto ciò che penso di cui ho bisogno in Intellisense!

Qualcuno ha un esempio di esecuzione di crittografia/decrittografia di stringhe con AES utilizzando il wrapper OpenSSL.Net?

Grazie!

-Nick

risposta

4

Ecco il campione che funziona per me. L'ho semplificato usando la copia-incolla ma non dovrebbe importare.

Sto utilizzando la password di testo a causa della compatibilità con la libreria JS, ma l'SSL aperto supporta l'uso diretto di byte [] Chiave e IV, quindi spetta a voi cosa usare.

Per commutare i dati binari nella stringa basta usare

Encoding.UTF8.GetBytes() and Encoding.UTF8.GetString() 

convertire avanti e indietro.

public Byte[] Encrypt(Byte[] data, String password) 
    { 
     //Just random 8 bytes for salt 
     var salt = new Byte[] {1, 2, 3, 4, 5, 6, 7, 8}; 

     using (var cc = new CipherContext(Cipher.AES_256_CBC)) 
     { 
      //Constructing key and init vector from string password 
      byte[] passwordBytes = Encoding.UTF8.GetBytes(password); 
      byte[] iv; 
      byte[] key = cc.BytesToKey(MessageDigest.MD5, salt, passwordBytes, 1, out iv); 

      var memoryStream = new MemoryStream(); 

      //Performing encryption thru unmanaged wrapper 
      var aesData = cc.Crypt(data, key, iv, true); 

      //Append salt so final data will look Salted___SALT|RESTOFTHEDATA 
      memoryStream.Write(Encoding.UTF8.GetBytes("Salted__"), 0, 8); 
      memoryStream.Write(salt, 0, 8); 
      memoryStream.Write(aesData, 0, aesData.Length); 

      return memoryStream.ToArray(); 
     } 
    } 

    public Byte[] Decrypt(String password, Byte[] encryptedData) 
    { 
     byte[] salt = null; 
     //extracting salt if presented 
     if (encryptedData.Length > 16) 
     { 
      if (Encoding.UTF8.GetString(encryptedData).StartsWith("Salted__")) 
      { 
       salt = new Byte[8]; 
       Buffer.BlockCopy(encryptedData, 8, salt, 0, 8); 
      } 
     } 

     //Removing salt from the original array 
     int aesDataLength = encryptedData.Length - 16; 
     byte[] aesData = new byte[aesDataLength]; 
     Buffer.BlockCopy(encryptedData, 16, aesData, 0, aesDataLength); 


     using (var cc = new CipherContext(Cipher.AES_256_CBC)) 
     { 
      //Constructing key and init vector from string password and salt 
      byte[] passwordBytes = Encoding.UTF8.GetBytes(password); 
      byte[] iv; 
      byte[] key = cc.BytesToKey(MessageDigest.MD5, salt, passwordBytes, 1, out iv); 

      //Decrypting 
      return cc.Decrypt(aesData, key, iv, 0); 

     } 


    } 
+1

Questi sono alcuni altamente otto bytes casuali per il sale;) – Nate

+0

Bene, abbastanza casuale per rispondere alla domanda come questo non è davvero un codice dal vivo :) –

+0

mia implementazione è basata fuori di questo esempio. Sto usando il contesto Cipher.AES_256_CBC ma se la mia password è <16 byte quando viene chiamato cc.Crypt genera un'eccezione. Perché sta cercando di scrivere i dati crittografati che sono 16 byte nel buffer da 8 byte che crea. Hai incontrato questo? Sto usando OpenSSL.Net 0.4.4 e sto usando un digest di messaggio SHA1. – Jeff

Problemi correlati