为了账号安全,请及时绑定邮箱和手机立即绑定

使用 io.ReadFull 分块处理数据会导致文件损坏?

使用 io.ReadFull 分块处理数据会导致文件损坏?

Go
饮歌长啸 2022-07-11 10:29:21
我正在尝试通过io.ReadFull以块的形式处理数据以节省内存来下载和解密 HLS 流:为简单起见,省略了不相关的代码部分。func main() {    f, _ := os.Create(out.ts)    for _, v := range mediaPlaylist {        resp, _ := http.Get(v.URI)        for {            r, err := decryptHLS(key, iv, resp.Body)            if err != nil && err == io.EOF {                break            else if err != nil && err != io.ErrUnexpectedEOF {                panic(err)            }            io.Copy(f, r)        }    }}func decryptHLS(key []byte, iv []byte, r io.Reader) (io.Reader, error) {    block, _ := aes.NewCipher(key)    buf := make([]byte, 8192)    mode := cipher.NewCBCDecrypter(block, iv)        n, err := io.ReadFull(r, buf)        if err != nil && err != io.ErrUnexpectedEOF {                return nil, err        }    mode.CryptBlocks(buf, buf)    return bytes.NewReader(buf[:n]), err}起初,这似乎可以正常工作,因为文件大小正确且下载过程中没有错误,但视频已损坏。不完全因为该文件仍被识别为视频,但图像和声音失真。如果我更改要使用的代码ioutil.ReadAll,最终的视频文件将不再损坏:func main() {    f, _ := os.Create(out.ts)    for _, v := range mediaPlaylist {        resp, _ := http.Get(v.URI)        segment, _ := ioutil.ReadAll(resp.Body)        r, _ := decryptHLS(key, iv, &segment)        io.Copy(f, r)    }}func decryptHLS(key []byte, iv []byte, s *[]byte) io.Reader {    block, _ := aes.NewCipher(key)    mode := cipher.NewCBCDecrypter(block, iv)    mode.CryptBlocks(*s, *s)    return bytes.NewReader(*s)}任何想法为什么它在将整个段读入内存时正常工作,而不是io.ReadFull在块中使用和处理它时?
查看完整描述

1 回答

?
忽然笑

TA贡献1806条经验 获得超5个赞

在内部, CBCDecrypter 会复制您的iv,因此后续块以初始 IV 开头,而不是由先前解密改变的那个。

创建一次解密器,您应该能够继续重复使用它来逐块解密(假设块大小是此加密算法预期的块大小的倍数)。


查看完整回答
反对 回复 2022-07-11
  • 1 回答
  • 0 关注
  • 82 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信