我已经开始构建一个安全的字符串类型 - 我称之为SecureStringV2 - 来扩展.Net框架中现有的SecureString类型。这种新类型将向现有类型添加一些基本功能(检查相等性,比较等),但仍保持SecureString类型提供的安全性,即在类型使用后清除内存中的所有内容。我计划使用Marshal类和哈希算法来实现这些功能。关于如何完成这项工作并完成正确的指示将不胜感激。你有没有看到我实施这个想法的任何问题?谢谢:))
更新:到目前为止,我的想法引领了我对图书馆核心课程的看法。看看,让我知道你的想法。
/// <summary>
/// This class is extension of the SecureString Class in the .Net framework.
/// It provides checks for equality of multiple SStringV2 instances and maintains
/// the security provided by the SecureString Class
/// </summary>
public class SStringV2 : IEquatable<SStringV2> , IDisposable
{
private SecureString secureString = new SecureString();
private Byte[] sStringBytes;
private String hash = string.Empty;
/// <summary>
/// SStringV2 constructor
/// </summary>
/// <param name="confidentialData"></param>
public SStringV2(ref Char[] confidentialData)
{
GCHandle charArrayHandle = GCHandle.Alloc(confidentialData, GCHandleType.Pinned);
// The unmanaged string splices a zero byte inbetween every two bytes
//and at its end doubling the total number of bytes
sStringBytes = new Byte[confidentialData.Length*2];
try
{
for (int index = 0; index < confidentialData.Length; ++index)
{
secureString.AppendChar(confidentialData[index]);
}
}
finally
{
ZeroOutSequence.ZeroOutArray(ref confidentialData);
charArrayHandle.Free();
}
}
/// <summary>
/// Computes the hash value of the secured string
/// </summary>
private void GenerateHash()
{
IntPtr unmanagedRef = Marshal.SecureStringToBSTR(secureString);
GCHandle byteArrayHandle = GCHandle.Alloc(sStringBytes, GCHandleType.Pinned);
Marshal.Copy(unmanagedRef, sStringBytes, 0, sStringBytes.Length);
SHA256Managed SHA256 = new SHA256Managed();
try
{
hash = Convert.ToBase64String(SHA256.ComputeHash(this.sStringBytes));
}
finally
{
SHA256.Clear();
ZeroOutSequence.ZeroOutArray(ref sStringBytes);
byteArrayHandle.Free();
Marshal.ZeroFreeBSTR(unmanagedRef);
}
}
#region IEquatable<SStringV2> Members
public bool Equals(SStringV2 other)
{
if ((this.hash == string.Empty) & ( other.hash == string.Empty))
{
this.GenerateHash();
other.GenerateHash();
}
else if ((this.hash == string.Empty) & !(other.hash == string.Empty))
{
this.GenerateHash();
}
else if (!(this.hash == string.Empty) & (other.hash == string.Empty))
{
other.GenerateHash();
}
if (this.hash.Equals(other.hash))
{
return true;
}
return false;
}
#endregion
#region IDisposable Members
public void Dispose()
{
secureString.Dispose();
hash = string.Empty;
GC.SuppressFinalize(this);
}
#endregion
}
}
答案 0 :(得分:1)
只是一个简单的注释 - 你要问的问题是错误的哈希相等与数据相等 - 确保它们不同的可能性很低但是一旦你点击它就会成为一场噩梦:/(我有“运气”调试和修复几年前犯同样错误的自定义哈希映射实现,所以请相信我;))。
答案 1 :(得分:1)
不要忘记SecureString使用双向加密。我没有在你的班级看到任何加密。
答案 2 :(得分:0)
如果你传递一个char []数组,你开始失去了securestring的好处。 char []数组可以在清除之前由垃圾收集器在内存中复制。