I saw a video detailing how to write a simple salted hash program in C# here. Below is the code they wrote (slightly edited for console applications):
using System;
using System.Text;
using System.Security.Cryptography;
namespace MyApplication
{
class Program
{
const int SALT_SIZE = 10;
static void Main(string[] args)
{
string salt = CreateSalt();
string password = "securePassword";
string hashedPassword = GenerateSHA256Hash(password, salt);
Console.WriteLine("salt: " + salt);
Console.WriteLine("hashedPassword: " + hashedPassword);
}
private static string CreateSalt()
{
var rng = new RNGCryptoServiceProvider();
var buffer = new byte[SALT_SIZE];
rng.GetBytes(buffer);
return Convert.ToBase64String(buffer);
}
private static string GenerateSHA256Hash(string input, string salt)
{
byte[] bytes = Encoding.UTF8.GetBytes(input + salt);
var hashManager = new SHA256Managed();
byte[] hash = hashManager.ComputeHash(bytes);
return ByteArrayToHexString(hash);
}
private static string ByteArrayToHexString(byte[] bytes)
{
StringBuilder sb = new StringBuilder(bytes.Length * 2);
foreach (byte b in bytes)
sb.AppendFormat("{0:x2}", b);
return sb.ToString();
}
}
}
From what I've read online, salted hashes are one of the most secure ways of storing passwords. However, I have a few questions:
I have read that it's not enough to hash a salted password once. You need to keep hashing it thousands of times to make brute-forcing more difficult for attackers.
Would doing something like below be more secure, and what would be a good number of times to repeat hashing?
var hash = hashManager.ComputeHash(bytes); for (int i = 0; i < 10000; i++) hash = hashManager.ComputeHash(hash);
I've also read that you also need to include the salt when rehashing, but I don't understand how to add it properly.
For the
salt
buffer size, is 10 a good number to use, or would a higher/lower number be more secure (e.g. 16)?I'm taking this with a grain of salt, but I've read that SHA256 isn't a secure choice anymore because it's too fast, meaning brute forces are quicker to do.
Does this mean that fast algorithms like SHA are obsolete and need to be replaced with slower algorithms like
bcrypt
?I assume that Hex Strings are a secure way to store salted hashes. Is this correct?
After applying all changes from the above questions (if any), would the above code be secure enough to use in a production setting?