如何正确创建SHA256哈希?
我正在实现SSO,我必须计算SHA256具有一个字符串,并将散列发送回并验证用户身份的端点。我SHA1做的工作如下:如何正确创建SHA256哈希?
var hash = SHA1.Create();
var encoder = new ASCIIEncoding();
byte[] combined = encoder.GetBytes(encryptedTokenStr);
hash.ComputeHash(combined);
string delimitedHexHash = BitConverter.ToString(hash.Hash);
string completedSha1Hash = delimitedHexHash.Replace("-", "");
但如果我改变了哈希算法类型来SHA256
和其他系统正哈希算法更改为SHA256 Salted (Suffix)
不知道这是否是一样的SHA256
?下面的代码不能正常工作,这意味着它不会authenicate用户的另一面:
var hash = SHA256.Create();
var encoder = new UTF8Encoding();
byte[] combined = encoder.GetBytes(encryptedTokenStr);
hash.ComputeHash(combined);
string delimitedHexHash = BitConverter.ToString(hash.Hash);
string completedSha1Hash = delimitedHexHash.Replace("-", "");
SHA256是不一样的“SHA256咸鱼”。
嗯,从技术上讲,它们都是SHA256,它只是输入的不同。在做SHA256时,你自己散列数据。在做“盐化”(无关你使用哪个哈希函数)时,首先向输入添加一些“盐”(加法可能不同,但大多数情况下它只是串联;“后缀”暗示盐在添加之后添加输入),然后散列结果数据。
所以为了创建一个有效的散列,我需要知道盐是什么。正确? – xaisoft
是的,以及它们与数据结合的确切方式。 –
在我的解决方案我用下面(复制和粘贴准备):
using System;
using System.Security.Cryptography;
using System.Text;
public string ComputeHash(string plainText, byte[] salt = null)
{
int minSaltLength = 4;
int maxSaltLength = 16;
byte[] saltBytes = null;
if (salt != null)
{
saltBytes = salt;
}
else
{
Random r = new Random();
int len = r.Next(minSaltLength, maxSaltLength);
saltBytes = new byte[len];
using (RNGCryptoServiceProvider rng = new RNGCryptoServiceProvider())
{
rng.GetNonZeroBytes(saltBytes);
}
}
byte[] plainData = ASCIIEncoding.UTF8.GetBytes(plainText);
int plainLength = plainData.Length;
int saltLength = saltBytes.Length;
byte[] plainDataAndSalt = new byte[plainLength + saltLength];
Array.Copy(plainData, 0, plainDataAndSalt, 0, plainLength);
Array.Copy(saltBytes, 0, plainDataAndSalt, plainLength, saltLength);
byte[] hashValue = null;
using (SHA256Managed sha2 = new SHA256Managed())
{
hashValue = sha2.ComputeHash(plainDataAndSalt);
}
int hashLength = hashValue.Length;
byte[] result = new byte[hashLength + saltLength];
Array.Copy(hashValue, 0, result, 0, hashLength);
Array.Copy(saltBytes, 0, result, hashLength, saltLength);
return ASCIIEncoding.UTF8.GetString(result);
}
解决你的问题/问题:
string hash = hash.ComputeHash("your string");
或者,如果服务器为你提供盐串:
byte[] salt = ASCIIEncoding.UTF8.GetBytes("server salt string in plaintext");
string hash = hash.ComputeHash("your string to hash", salt);
然后将散列返回给服务器。
如果我知道所使用的散列盐值,那么如何修改您的代码?基本上来自其他系统,我将有散列密码和散列盐 – xaisoft
如果你有*散列*盐,你不能做一件事,你需要知道它的明文。 –
如果存在散列盐,应向SSO供应商索要纯文本盐。如果允许使用它当然。 Driveby登录通常在任何地方都不受支持。 –
你为什么使用var encoder = new UTF8Encoding();而不是var encoder = new ASCIIEncoding();如在第一个例子中那样。这是一个错字还是故意的? –
我看到一个使用UTF8的例子,所以这就是为什么。我其实不确定使用哪一个。 – xaisoft
他们将产生相同的结果根据:http://stackoverflow.com/questions/16994042/difference-between-encoding-utf8-getbytes-and-utf8encoding-default-getbytes#16994086 –