Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the best practice when saving passwords using the C# Settings feature?

I am using Visual C# built in feature Settings to save some of my program's options. I also want to store one password, but then it comes public... is it possible to encrypt the password before saving it using this settings method and then decrypt it back?

like image 786
Badr Hari Avatar asked Oct 14 '10 20:10

Badr Hari


3 Answers

For simple encryption needs, I've used the DPAPI via the ProtectedData class. To make the resulting encrypted value storable in a text file or registry, I encode the resulting byte array.

Here is the class I wrote to wrap this up:

namespace SomeNamespace
{
   using System;
   using System.Security.Cryptography;
   using System.Text;

   /// <summary>
   /// used for encryption and decryption
   /// </summary>
   public static class DataProtector
   {
      private const string EntropyValue = "secret";

      /// <summary>
      /// Encrypts a string using the DPAPI.
      /// </summary>
      /// <param name="stringToEncrypt">The string to encrypt.</param>
      /// <returns>The encrypted data.</returns>
      public static string EncryptData(string stringToEncrypt)
      {
         byte[] encryptedData = ProtectedData.Protect(Encoding.Unicode.GetBytes(stringToEncrypt), Encoding.Unicode.GetBytes(EntropyValue), DataProtectionScope.LocalMachine);
         return Convert.ToBase64String(encryptedData);
      }

      /// <summary>
      /// Decrypts a string using the DPAPI.
      /// </summary>
      /// <param name="stringToDecrypt">The string to decrypt.</param>
      /// <returns>The decrypted data.</returns>
     public static string DecryptData(string stringToDecrypt)
      {
         byte[] decryptedData = ProtectedData.Unprotect(Convert.FromBase64String(stringToDecrypt), Encoding.Unicode.GetBytes(EntropyValue), DataProtectionScope.LocalMachine);
         return Encoding.Unicode.GetString(decryptedData);
      }
   }
}
like image 51
Russell McClure Avatar answered Oct 20 '22 10:10

Russell McClure


A simple way to do it is to encrypt the password with itself. You'll never be able to unencrypt it, but you will be able to compare a user-entered password to it.

like image 29
Andrew Lewis Avatar answered Oct 20 '22 10:10

Andrew Lewis


If you encrypt the password, you will still have to store a decryption key somewhere in the program, so it still amounts to security by obscurity.

However, it would keep the honest people honest.

The most common practice I have seen for this is a challenge/response system, where the user puts in a registration name, the program provides a challenge string, and you email them the corresponding response string (encrypted), which the user cuts and pastes into a registration dialog in the program. The program decrypts the response, compares it to the challenge, and off you go.

Of course, since you still have to provide the decryption password in the program itself, it can still be defeated by a determined hacker.

like image 2
Robert Harvey Avatar answered Oct 20 '22 09:10

Robert Harvey