HMACSHA256和HMACSHA512之间的差异

Luk*_*ett 10 c# security cryptography hmac

我们使用以下代码针对C#中的敏感值生成HMac哈希

public string GenerateHMac(string key, string message)
{
    var decodedKey = Convert.FromBase64String(key);

    var hasher = new HMACSHA256(decodedKey);

    var messageBytes = Encoding.Default.GetBytes(message);

    var hash = hasher.ComputeHash(messageBytes);

    return Convert.ToBase64String(hash);
}
Run Code Online (Sandbox Code Playgroud)

传入的密钥是256位base 64编码字符串.提出了一个问题,我们是否应该使用HMACSHA256,HMACSHA384或HMACSHA512来散列该值.

  • 使用HMACSHA512相对于HMACSHA256有什么好处?
  • 它更安全吗?
  • 使用更长的密钥时是否会产生显着的性能影响?

作为旁注; decodedKey如果我使用HMACSHA512,我传递给构造函数的值是否需要是512位密钥?

Maa*_*wes 22

TL; DR:使用HMAC-SHA512获得最佳速度,安全性和良好的兼容性.SHA-256也非常安全,可以在具有32位操作的CPU上使用.


要查看哈希方法本身的强度,请查看keylength.com网站.你会发现即使是SHA-256也有相当大的安全边际.

更重要的是,HMAC算法几乎无视对底层哈希算法的攻击.HMAC不受生日问题的影响,将关键强度减半,使哈希输出减半.它不适用仅仅是因为攻击者不持有密钥,因此不能尝试创建冲突.这就是为什么即使HMAC-SHA1也非常安全.


现在哈希的速度取决于执行环境.但总的来说,您可以做出以下假设:

  1. SHA-1通常比同一平台上的任何SHA-2实现更快;
  2. 在64位计算机上SHA-512比SHA-256更快(因为它们在内部使用64位算术);
  3. 在8,16和32位机器上,SHA-256比SHA-512更快.

如果您期望兼容性问题,请使用SHA-1.否则你也可以选择SHA-512(并将结果切换到合理的位数).SHA-512的内部状态和更高的安全性可能是一个小优势.由于算法的一般问题,我遇到了不接受任何形式的SHA-1的客户的问题; 换句话说,它一般不安全的事实可能会妨碍接受.


请注意,SHA-384和不太为人所知的SHA-512/256和SHA-512/224哈希方法是SHA-512的一种特殊形式,切换为384,256和224位输出.所以这些算法的速度是相同的.除输出大小之外的唯一区别是这些特殊形式在内部使用不同的初始值.否则,SHA-512切割到384位与SHA-512/384一样安全和快速.但是,如果需要特定的输出大小,则应使用SHA-384保持兼容.

SHA-384和SHA-512/256和SHA-512/224使用不同的初始值,因此它们中的任何一个的输出都不同于SHA-512和彼此; 一种称为域分离的功能.域分离使得不可能使用攻击或(部分)预测其他相关散列函数的散列结果.


输入密钥大小不依赖于底层哈希函数.密钥首先进行XOR掩码,然后通过底层哈希函数进行哈希处理; 哈希算法可以将几乎无限量的数据作为输入.

建议使用至少与所使用的哈希方法大小相同的密钥大小,否则可能会降低HMAC方法提供的安全边际.如果密钥大小强制散列算法散列多个块,则可能会有轻微的性能损失.


您也可以使用(即将推出的)SHA-3标准,因为它是安全的.HMAC-SHA-3目前并没有太多意义.HMAC实际上对SHA-3(Keccak)来说太过分了; 即使没有HMAC结构,SHA-3也应该是安全的.到目前为止,KMAC已被标准化为SHA-3的MAC构造.

SHA-2构造在某种程度上令人惊讶地显示出在SHA-3竞争期间对密码分析具有相当好的抵抗力.因此,没有迫切需要升级到KMAC/SHA-3.


jbt*_*ule 5

我认为你不需要担心安全优势,HmacSha1 仍然被认为是安全的,安全性应该被认为是相对于密钥长度的。Sha256 与 Sha512 的性能将取决于实现、平台等,您必须自己测试。您提供给 HMAC 的密钥长度与哈希算法无关,请参阅伪代码