Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/260.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 生成AES 256位键值_C#_Hash_Aes_Encryption Symmetric - Fatal编程技术网

C# 生成AES 256位键值

C# 生成AES 256位键值,c#,hash,aes,encryption-symmetric,C#,Hash,Aes,Encryption Symmetric,有人知道从任意长度的密码短语生成256位键值的方法吗?由于需要再次生成加密值并在数据库中进行比较,因此无法对加密进行加密。因此,值必须在每次加密时生成相同的加密字符串 目前我使用的是一个32字符的密钥,假设它是256位,这可能是错误的 因此,我希望将“quick brown fox”转换为合适的AES 256位密钥?您可以使用一些哈希函数,从任意长度的输入中提供256位输出,例如SHA256。您可以使用任意大小的密码构造,然后派生出所需大小的密钥,在本例中为256位(32字节): 为了产生确定性

有人知道从任意长度的密码短语生成256位键值的方法吗?由于需要再次生成加密值并在数据库中进行比较,因此无法对加密进行加密。因此,值必须在每次加密时生成相同的加密字符串

目前我使用的是一个32字符的密钥,假设它是256位,这可能是错误的


因此,我希望将“quick brown fox”转换为合适的AES 256位密钥?

您可以使用一些哈希函数,从任意长度的输入中提供256位输出,例如SHA256。

您可以使用任意大小的密码构造,然后派生出所需大小的密钥,在本例中为256位(32字节):

为了产生确定性输出(即相同的输入将产生相同的输出),您需要对salt进行硬编码。salt必须至少为8个字节:

private static readonly byte[] Salt = 
    new byte[] { 10, 20, 30 , 40, 50, 60, 70, 80};

最好的方法可能是使用SHA256(将生成256位输出)和特定于应用程序的salt&迭代计数来使用PBKDF2。您应该知道,使用特定于应用程序的salt会从PBKDF2中移除很多保护,所以您可能需要额外的保护来缓解此问题。一种方法是确保数据库是安全的,并且可以使用最大的尝试次数

您规定32字符的密码短语不是256位密钥是正确的。它没有包含足够的熵,某些字节甚至可能没有有效的字符表示形式。

公共静态字符串生成器ITKEY(int-letterCount=44)
public static string GenerateBitKey(int letterCount = 44)
    {
        // Get the number of words and letters per word.
        int num_letters = letterCount;
        // Make an array of the letters we will use.
        char[] letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789".ToCharArray();

        // Make a random number generator.
        Random rand = new Random();

        // Make the words.
        // Make a word.
        string word = "";
        for (int j = 1; j <= num_letters; j++)
        {
            // Pick a random number between 0 and 25
            // to select a letter from the letters array.
            int letter_num = rand.Next(0, letters.Length - 1);

            // Append the letter.
            word += letters[letter_num];
        }
        return word;
    }
{ //获取每个单词的单词数和字母数。 int num_字母=字母计数; //把我们要用的字母排成一个数组。 char[]letters=“abcdefghijklmnopqrstuvxyz012456789”。ToCharArray(); //制作一个随机数发生器。 Random rand=新的Random(); //写单词。 //说一句话。 字串=”; 对于(int j=1;j
private static IBuffer GetMD5Hash(字符串键)
{
IBuffer bufferUTF8Msg=CryptographicBuffer.ConvertStringToBinary(key,BinaryStringEncoding.Utf8);
HashAlgorithmProvider HashAlgorithmProvider=HashAlgorithmProvider.OpenAlgorithm(HashAlgorithmNames.Md5);
IBuffer hashBuffer=hashAlgorithmProvider.HashData(bufferUTF8Msg);
if(hashBuffer.Length!=hashAlgorithmProvider.HashLength)
{
抛出新异常(“创建哈希时出错”);
}
返回哈希缓冲区;
}
#区域静态
公共静态字符串GenerateKey(字符串密码,int-resultKeyLength=68)
{
如果(密码长度<6)
抛出新ArgumentException(“密码长度必须至少为6个字符或以上”);
字符串键=”;
var hashKey=GetMD5Hash(密码);
var decryptBuffer=cryptographicsbuffer.ConvertStringToBinary(密码,BinaryStringEncoding.Utf8);
var AES=SymmetricKeyAlgorithmProvider.OpenAlgorithm(SymmetricAlgorithmNames.AesEcbPkcs7);
var symmetricKey=AES.CreateSymmetricKey(hashKey);
var encryptedBuffer=cryptographicsengine.Encrypt(symmetricKey,decryptedbuffer,null);
key=CryptographicBuffer.EncodeToBase64String(encryptedBuffer);
字符串cleanKey=key.Trim(新字符[]{'、'\r'、'\t'、'\n'、'/'、'+'、'='});
cleanKey=cleanKey.Replace(“/”,string.Empty)。Replace(“+”,string.Empty)。Replace(“=”,string.Empty);
键=清洁键;
如果(key.Length>resultKeyLength)
{
key=key.Substring(0,Math.Min(key.Length,resultKeyLength));
}
else if(key.Length==resultKeyLength)
{
返回键;
}
否则如果(key.Length

//获取AES密钥的前44个字符,以及AES IV的剩余字符。我只想要没有密码的密钥

    public static string GenerateBitKey(int letterCount = 44)
    {
        // Get the number of words and letters per word.
        int num_letters = letterCount;
        // Make an array of the letters we will use.
        char[] letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrsruvwxyz+".ToCharArray();
        int lettersLength =  letters.Length;

        // Make a word.
        string word = "";

        //Use Cryptography to generate random numbers rather than Psuedo Random Rand
        // Deliberate overkill here
        byte[] randomBytes = new byte[num_letters*256];


        List<int> rands = new List<int>();
        do
        {
            using (System.Security.Cryptography.RNGCryptoServiceProvider rngCsp = new
                        System.Security.Cryptography.RNGCryptoServiceProvider())
            {
                // Fill the array with a random value.
                rngCsp.GetBytes(randomBytes);
            }


            // Truncate the set of random bytes to being in range 0 .. (lettersLength-1)
            // Nb Using mod of randomBytes will reduce entropy of the set

            foreach (var x in randomBytes)
            {
                if (x < lettersLength)
                    rands.Add((int)x);
                if (rands.Count()==num_letters)
                     break;
            }
        }
        while (rands.Count < letterCount);


        int[] randsArray = rands.ToArray();

        // Get random selection of characters from letters
        for (int j = 0; j < num_letters; j++)
        {
            int letter_num = randsArray[j];
            // Append the letter.
            word += letters[letter_num];
        }
        return word;
    }
公共静态字符串GenerateBitKey(int-letterCount=44)
{
//获取每个单词的单词数和字母数。
int num_字母=字母计数;
//把我们要用的字母排成一个数组。
char[]letters=“abcdefghijklmnopqrstuvwxyz123456789abcdefghijklmnopqrsruvwxyz+”。tocharray();
int-lettersLength=字母长度;
//说一句话。
字串=”;
//使用加密技术生成随机数,而不是伪随机数
//这里故意杀伤力过大
字节[]随机字节=新字节[num_letters*256];
List rands=新列表();
做
{
使用(System.Security.Cryptography.RNGCryptoServiceProvider rngCsp=new)
System.Security.Cryptography.RNGCryptoServiceProvider())
{
//用随机值填充数组。
rngCsp.GetBytes(随机字节);
}
//将随机字节集截断为范围0..(字母长度-1)
//Nb使用mod of randomBytes将减少集合的熵
foreach(变量x,以随机字节为单位)
{
如果(x<字母长度)
随机添加((int)x);
if(rands.Count()==num_个字母)
打破
}
}
而(rands.Count
官方说法,散列不是基于密码的密钥派生函数,因此不应直接使用。有关上面的实现,请参阅ByteBlasts答案:)谢谢-因此,上面方法中的32字节数组是256字节
 private static IBuffer GetMD5Hash(string key)
    {
        IBuffer bufferUTF8Msg = CryptographicBuffer.ConvertStringToBinary(key, BinaryStringEncoding.Utf8);
        HashAlgorithmProvider hashAlgorithmProvider = HashAlgorithmProvider.OpenAlgorithm(HashAlgorithmNames.Md5);
        IBuffer hashBuffer = hashAlgorithmProvider.HashData(bufferUTF8Msg);
        if (hashBuffer.Length != hashAlgorithmProvider.HashLength)
        {
            throw new Exception("There was an error creating the hash");
        }
        return hashBuffer;
    }

    #region Static

    public static string GenerateKey(string password, int resultKeyLength = 68)
    {
        if (password.Length < 6)
            throw new ArgumentException("password length must atleast 6 characters or above");
        string key = "";

        var hashKey = GetMD5Hash(password);
        var decryptBuffer = CryptographicBuffer.ConvertStringToBinary(password, BinaryStringEncoding.Utf8);
        var AES = SymmetricKeyAlgorithmProvider.OpenAlgorithm(SymmetricAlgorithmNames.AesEcbPkcs7);
        var symmetricKey = AES.CreateSymmetricKey(hashKey);
        var encryptedBuffer = CryptographicEngine.Encrypt(symmetricKey, decryptBuffer, null);
        key = CryptographicBuffer.EncodeToBase64String(encryptedBuffer);
        string cleanKey  = key.Trim(new char[] { ' ', '\r', '\t', '\n', '/', '+', '=' });
        cleanKey = cleanKey.Replace("/", string.Empty).Replace("+", string.Empty).Replace("=", string.Empty);
        key = cleanKey;
        if(key.Length > resultKeyLength)
        {
           key = key.Substring(0, Math.Min(key.Length, resultKeyLength));
        }
        else if(key.Length == resultKeyLength)
        {
            return key;
        }
        else if (key.Length < resultKeyLength)
        {
            key = GenerateKey(key);
        }
        return key;

    }
    public static string GenerateBitKey(int letterCount = 44)
    {
        // Get the number of words and letters per word.
        int num_letters = letterCount;
        // Make an array of the letters we will use.
        char[] letters = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrsruvwxyz+".ToCharArray();
        int lettersLength =  letters.Length;

        // Make a word.
        string word = "";

        //Use Cryptography to generate random numbers rather than Psuedo Random Rand
        // Deliberate overkill here
        byte[] randomBytes = new byte[num_letters*256];


        List<int> rands = new List<int>();
        do
        {
            using (System.Security.Cryptography.RNGCryptoServiceProvider rngCsp = new
                        System.Security.Cryptography.RNGCryptoServiceProvider())
            {
                // Fill the array with a random value.
                rngCsp.GetBytes(randomBytes);
            }


            // Truncate the set of random bytes to being in range 0 .. (lettersLength-1)
            // Nb Using mod of randomBytes will reduce entropy of the set

            foreach (var x in randomBytes)
            {
                if (x < lettersLength)
                    rands.Add((int)x);
                if (rands.Count()==num_letters)
                     break;
            }
        }
        while (rands.Count < letterCount);


        int[] randsArray = rands.ToArray();

        // Get random selection of characters from letters
        for (int j = 0; j < num_letters; j++)
        {
            int letter_num = randsArray[j];
            // Append the letter.
            word += letters[letter_num];
        }
        return word;
    }