0

I need to convert a base64-encoded string to a SecureString without having to use a regular C# string, po prevent a password being stored in memory in cleartext.

Right now I have code that does this:

string encodedPassword = "TXlQYXNzd29yZA==";
byte[] encodedBytes = Convert.FromBase64String(encodedPassword);
string clearTextPassword = Encoding.UTF8.GetString(encodedBytes);
SecureString secureString = ConvertToSecureString(clearTextPassword);

I would like something like this: Convert.FromBase64StringToSecureString(EncodedPassword)

Frogger
  • 94
  • 8
  • 4
    Well, your base64 representation is already stored in memory, so I'm not sure what actual protection you'd get by going from encoded -> SecureString. [You may also want to take a look at this](https://github.com/dotnet/platform-compat/blob/master/docs/DE0001.md) if you plan to go to other platforms. – Jonathon Chase Jan 07 '19 at 18:19
  • I agree with your comment about the base64 string already being in memory so the password could be found. I am attempting to pass a security test that is looking for the password in clear text. I know "obfuscation != security", but in this case it will help. – Frogger Jan 07 '19 at 19:16

1 Answers1

0

I ended up writing the following method that uses the GetChars() method, and then clear the array once used. There is a chance it could leave something behind in memory if an exception is thrown during execution but I'm not concerned about that case.

private static SecureString DecodeBase64String(string encodedData)
{
    var secureString = new SecureString();

    if (string.IsNullOrWhiteSpace(encodedData))
    {
        secureString.MakeReadOnly();
        return secureString;
    }
    try
    {
        var encodedBytes = Convert.FromBase64String(encodedData);
        var passwordChars = Encoding.UTF8.GetChars(encodedBytes);

        // clear the encoded bytes so they aren't resident in memory
        for (var i = 0; i < encodedBytes.Length; i++)
        {
            encodedBytes[i] = 0;
        }

        foreach (var c in passwordChars)
        {
            secureString.AppendChar(c);
        }

        // clear the password characters so they aren't resident in memory
        for (var i = 0; i < passwordChars.Length; i++)
        {
            passwordChars[i] = (char)0;
        }

        secureString.MakeReadOnly();
        return secureString;
    }
    catch (FormatException)
    {
        secureString.MakeReadOnly();
        return secureString;
    }
}
Frogger
  • 94
  • 8