SecureString是只写的类吗?

时间:2011-05-14 05:09:27

标签: c# .net security securestring

我最近发现了SecureString,它似乎适合一个完美的应用程序,我希望在应用程序开始时基本上初始化一个静态秘密字符串,然后将其设置为只读并在应用程序的整个生命周期中使用它(如一部分哈希)。

我无法理解如何使用SecureString类。据我所知,您可以设置SecureString,但无法比较值或以任何方式检索值。

如果这个类是只写的,那么这个类的目的是什么?

2 个答案:

答案 0 :(得分:3)

不,它不是只写的:您可以使用Marshal类从String检索常规.NET SecureString

IntPtr ptr = Marshal.SecureStringToBSTR(secureString);
string str = Marshal.PtrToStringBSTR(ptr);
Marshal.ZeroFreeBSTR(ptr);
return str;

请注意,这会分配非托管内存,因此您需要确保释放它(使用Marshal.ZeroFreeBSTR)以避免泄漏。并且不用说,一旦你将它转换为.NET字符串,你将失去SecureString的好处(String将保留在内存中,直到它被GC,它可能被分页到磁盘等)。 / p>

SecureString类的目的是您可以在API中使用它,其中应保护用户数据的隐私(例如,密码或信用卡号)(例如,如果您的应用程序崩溃并且小型转储器保存到磁盘) 。 .NET Framework中的一些类(例如PasswordBox.SecurePassword)接受SecureString对象以避免暴露此数据。

答案 1 :(得分:0)

这里的两种方式,一种将其转换为securestring和securestring的方法。当然,将它存储在一个安全串中的重点是防止它首先存在于内存中。

        #region SecureString Manipulation
    /// <summary>
    /// Convert a Securestring to a regular string (not considered best practice, but make sure it's not in memory if you can help it)
    /// </summary>
    /// <param name="securePassword">Password stored in a secure string</param>
    /// <returns>regular string of securestring password</returns>
    public static string ConvertToUnsecureString(this System.Security.SecureString securePassword)
    {
        if (securePassword == null)
            throw new ArgumentNullException("securePassword");

        IntPtr unmanagedString = IntPtr.Zero;
        try
        {
            unmanagedString = Marshal.SecureStringToGlobalAllocUnicode(securePassword);
            return Marshal.PtrToStringUni(unmanagedString);
        }
        finally
        {
            Marshal.ZeroFreeGlobalAllocUnicode(unmanagedString);
        }
    }

    /// <summary>
    /// Pass a text password to this function to return a SecureString (doesn't store the password in memory)
    /// </summary>
    /// <param name="password">Text version of a password</param>
    /// <returns>SecureString of a password (not readable by memory)</returns>
    public static SecureString ConvertToSecureString(this string password)
    {
        if (password == null)
            throw new ArgumentNullException("password");

        var secure = new SecureString();
        foreach (var c in password.ToCharArray())
            secure.AppendChar(c);
        return secure;
    }
    #endregion