内外两层使用不同垫值

HMAC先把密钥处理到所选哈希函数规定的块宽度,再分别与固定的ipad、opad异或。内层处理经过ipad作用的密钥与消息,外层再处理opad对应值和内层摘要。两种垫值承担不同位置的分离,不能把内外调用随意合并成一次普通哈希。

较长密钥会先按规定哈希,较短密钥则补到块宽度;这里的块长度与最终摘要长度不是同一个参数。因此不能把某个示例中的64字节块长,硬编码成所有HMAC实例都适用的常数。

参考:[1]

标签和预计算状态都有保护要求

标签可以随消息发送,密钥却必须保密;从容易猜测的口令直接取一串字节,并不会因为套上HMAC名称就获得强密钥。长期使用还需要合适的更新和用途隔离,避免一处泄露扩展为所有消息来源都可伪造。

实现可以为同一密钥预计算部分内外状态,节省每条短消息重复处理密钥块的工作。RFC 2104同时强调,这些中间状态必须像密钥一样保护;它们不是可随意公开的普通性能缓存。

参考:[1] [2]

实例与截断规则需要明确

HMAC-SHA-256等名称指定所用哈希实例,而不是说普通SHA-256本身需要秘密密钥。协议还可按规定截短标签,但不能由每端各自选择保留哪些位;短标签改变猜测成功的条件,允许验证的次数也会影响整体风险。

旧规范中的MD5或SHA-1举例不应直接当成当前选型建议。RFC 6151已更新HMAC-MD5等历史说明,并反对新协议采用HMAC-MD5。结构的安全分析与某个底层函数、参数和部署要求的适用状态,需要分别核对。

参考:[1] [3]