C#与Swift计算字符串SHA1哈希结果不匹配问题排查
问题根因
两端哈希计算结果不一致的核心原因是传入SHA1算法的原始字节数据编码规则不匹配,和SHA1算法本身的实现无关:
- C#代码中使用
Encoding.Unicode获取字节数组,该编码在.NET体系中是小端序UTF-16编码,每个字符占2字节,测试字符串test1234会被编码为16字节长度的原始数据。 - 原Swift代码中使用
.utf8编码获取字节数组,test1234全部为ASCII字符,编码后仅为8字节长度的原始数据。
输入给哈希算法的原始内容完全不同,输出结果自然无法对齐。
修正方案
将Swift端的字符串编码替换为和C#端完全一致的小端序UTF-16即可,修正后代码如下:
import CryptoKit // 编码指定为utf16LittleEndian,和C# Encoding.Unicode规则对齐 guard let data = "test1234".data(using: .utf16LittleEndian) else { fatalError("字符串编码失败") } let digest = Insecure.SHA1.hash(data: data) print(digest.hexStr) extension Digest { var bytes: [UInt8] { Array(makeIterator()) } var data: Data { Data(bytes) } var hexStr: String { bytes.map { String(format: "%02X", $0) }.joined() } }
运行上述代码将输出和C#端完全一致的结果:5387F24564B241075F48BBDFDDDC12640015E92A。
注意:不要混淆UTF-16的字节序,.NET中
Encoding.Unicode固定为小端序,Encoding.BigEndianUnicode才对应大端序UTF-16,编码选错依然会出现结果不匹配的问题。
内容的提问来源于stack exchange,提问作者dweb
相关产品推荐
相关产品推荐

