3

I have working code that will encrypt and decrypt a string provided to methods and this all works fine for when im storing a users entered password for convenience later.

However what I am trying to do is provide a password (encrypted) in the applications config file that allows users to pull data from an SQL server on the same domain.

Because I've used ProtectedData.Protect with DataProtectionScope.CurrentUser it has been encrypted using me as a key meaning users cannot decrypt this key, and DataProtectionScope.LocalMachine is also not applicable.

private static byte[] Entropy = { // Some arbitrary numbers };

public static string Encrypt(string _toEncrypt)
{
    byte[] originalText = Encoding.Unicode.GetBytes(_toEncrypt);
    byte[] EncryptedText = ProtectedData.Protect(originalText, Entropy, DataProtectionScope.CurrentUser);
    return Convert.ToBase64String(EncryptedText);
}

public static string Decrypt(string _toDecrypt)
{
    byte[] EncryptedText = Convert.FromBase64String(_toDecrypt);
    byte[] OriginalText = ProtectedData.Unprotect(EncryptedText, Entropy, DataProtectionScope.CurrentUser);
    return Encoding.Unicode.GetString(OriginalText);
}

Is there another way of doing this that allows for a password to be decrypted when required and be provided in its encrypted format for security reasons?

Ben R
  • 85
  • 6
  • 1
    Is your application configuration file an Xml Configuration file (`app.config` or `web.config`)? – Joshua Robinson Jul 23 '19 at 13:34
  • @JoshuaRobinson yes im using app.config – Ben R Jul 23 '19 at 13:45
  • 1
    "`im storing a users entered password for convenience later.`" _Don't do that!_ **IT'S NOT OKAY TO ENCRYPT/DECRYPT USER PASSWORDS!!** You must **HASH** user passwords, which is different from encryption. _Hashed values cannot be decrypted!_. To validate a login attempt, you also hash the attempted password, and then compare the hashes. Even that is the simplified version. Look into bcrypt/scrypt libraries. – Joel Coehoorn Jul 23 '19 at 17:47
  • If any user can decrypt it, why did you encrypt it? The correct way to handle the overarching problem you're facing is to not use username and password for authenticating to the database, use integrated security which will use the current user logged into the computer instead, and move the authentication problem to the SQL server instead of locally. – Lasse V. Karlsen Jul 23 '19 at 17:52
  • The database is not one I own so cannot change authentication, the owner/creator/business has decided to use SQL account authentication so i need to follow suit. As for not storing passwords im well aware of this and the protocol, however what other solution is there when a generic account is created with read-only access and the password is required to view the database with preformed SQL queries? The user and pass have to be provided some how which is why its encrypted and decrypted at the time of requirement automatically by the program – Ben R Jul 24 '19 at 06:44
  • The service account is one thing. User passwords stored for convenience is quite another. – Joel Coehoorn Jul 24 '19 at 14:53

1 Answers1

0

Since you're using app.config for your configuration file, you can actually use the aspnet_regiis utility to encrypt sections of the file.

It's been a while since I've had to do this, but there are some resources on the internet if you do some searching (for example). But, if I recall correctly the steps are basically:

  1. Temporarily rename your app.config to web.config because aspnet_regiis will only work on web.config.
  2. Open a Developer Command Prompt (might need to do it as an administrator).
  3. Run aspnet_regiis -pef <the section you're encrypting> <path to your web.config>. The path should just be the folder where the configuration file can be found, don't include web.config.
  4. Rename your configuration file back to app.config.

This will need to be run on the server or machine hosting your application. If your application is not running from a single server things become more complicated as you will have to export the key, and import it to every computer running the application. This article contains the steps:

  1. Create a machine-level RSA Key Container (1 time step)
  2. Exporting the Custom RSA Encryption Key (1 time step)
  3. Importing the Certificate (1 time step - per machine)
  4. Adding Permissions to the Certificate (1 time step - per machine)
  5. Encrypting the Configuration Section
  6. Decrypting the Configuration Section

You don't actually need to do any sort of special decryption in your application. The configuration system will handle that for you automatically.

Joel Coehoorn
  • 399,467
  • 113
  • 570
  • 794
Joshua Robinson
  • 3,399
  • 7
  • 22