【问题标题】:Rfc2898DeriveBytes how to verify the password which is store in database as hash valueRfc2898DeriveBytes如何验证存储在数据库中的密码作为哈希值
【发布时间】:2017-09-11 03:38:42
【问题描述】:

如何验证作为哈希值存储在数据库中的密码

当我使用数据库值验证密码哈希时,它永远不会相同,因为它会生成随机盐。

如何添加盐以进行验证和测试。

以下是我用于散列和验证散列密码的代码。

我的代码:

/// <summary>
        /// Generate the value from bytes.
        /// </summary>
        /// <param name="password"></param>
        /// <param name="iterationCount"></param>
        /// <returns></returns>
        private static string GenerateHashValue(string password)
        {
            return Convert.ToBase64String(GenerateHashBytes(password));
        }

        /// <summary>
        /// Hashing the password using PBKDF2
        /// </summary>
        /// <param name="password"></param>
        /// <param name="iterationCount"></param>
        /// <returns></returns>
        private static byte[] GenerateHashBytes(string password)
        {
            byte[] hashValue;
            //create salt
            byte[] salt = GenerateRandomSalt();
            var valueToHash = string.IsNullOrEmpty(password) ? string.Empty : password;
            using (var pbkdf2 = new Rfc2898DeriveBytes(valueToHash,salt, iterationCount))
            {
                hashValue = pbkdf2.GetBytes(DerivedKeyLength); 
            }
            return hashValue;
        }

        public static bool VerifyPassword(string password, string correctHash)
        {
            byte[] hash;
            byte[] OriginalHash = Encoding.ASCII.GetBytes(correctHash);
            hash = GenerateHashBytes(password); 
            return SlowEquals(hash, OriginalHash);
        }

        private static bool SlowEquals(byte[] a, byte[] b)
        {
            var diff = (uint)a.Length ^ (uint)b.Length;
            for (int i = 0; i < a.Length && i < b.Length; i++)
            {
                diff |= (uint)(a[i] ^ b[i]);
            }
            return diff == 0;
        }

        /// <summary>
        /// Used to generate the random string to append hash.
        /// </summary>
        /// <returns></returns>
        private static byte[] GenerateRandomSalt()
        {
            /*We are using the RNGCryptoServiceProvider class to create a Cryptography Secure Pseudo-Random Number Generator that will generate the level of randomness and uniqueness we require for a salt.*/
            var csprng = new RNGCryptoServiceProvider();
            var salt = new byte[SaltByteLength];
            csprng.GetBytes(salt);
            return salt;
        }

【问题讨论】:

    标签: c# hash password-hash string-hashing


    【解决方案1】:

    您必须创建一个 salt 并将其与密码哈希一起存储在您的数据库中。

    在对密码进行哈希处理后,您向数据库请求用户 X(或其他)的 salt,检查它是否存在,并将 salt 应用于您的哈希。

    看起来像这样(带有您提供的少量代码的伪代码):

    var salt = GetSaltFromDB();
    if (salt == null) //Not yet in DB
        salt = GenerateSalt(); //This also saves the salt to DB
    using (var pbkdf2 = new Rfc2898DeriveBytes(valueToHash, salt, iterationCount))
    {
        hashValue = pbkdf2.GetBytes(DerivedKeyLength); 
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2012-11-25
      • 1970-01-01
      • 2020-05-13
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多