我正在尝试使用 XTS 模式和 Golang 使用 AES-256 加密文件。 我最近刚刚从 CTR 模式转移到 XTS,我面临这个错误
一个很好的东西,我的代码片段:
func Encrypt(loc string, k *kyber.Kyber) (esK string, err error) {
in, err := os.Open(loc)
if err != nil {
return "", err
}
defer in.Close()
out, err := os.Create(loc + EncryptExtension)
if err != nil {
return "", err
}
defer out.Close()
sK, esK, err := k.SecretKey()
if err != nil {
return "", err
}
cipher, err := xts.NewCipher(aes.NewCipher, sK) // sK = 32 bytes
if err != nil {
return "", err
}
pT := make([]byte, BufferSize) // BufferSize = 2 * 1024 * 1024 = 2MB
for {
len, err := in.Read(pT)
if err != nil && err != io.EOF {
return "", err
}
if len == 0 {
break
}
cT := make([]byte, len)
cipher.Encrypt(cT, pT[:len], 0) // When len % 16 != 0 the code just panic
if _, err := out.Write(cT); err != nil {
return "", err
}
}
return esK, nil
}
我知道错误的含义,并且我知道修复它的解决方法,但这里的主要问题是,XTS 不是设计用于处理任意数据长度吗?为什么 Golang 不遵循这一点?
根据 NIST 800-38E
XTS-AES 模式旨在对使用固定长度“数据单元”的存储设备上的数据进行加密保护。
x/crypto/xts 库明确声明以下内容(链接):
此包不实现密文窃取,因此扇区必须是 16 字节的倍数。
十多年前贡献初始代码的原始 CL 从未包含对密文窃取的支持,也没有提供原因。由于复杂性,它可能被省略。