librespot/audio/src/decrypt.rs

50 lines
1.2 KiB
Rust
Raw Normal View History

2015-06-23 14:38:29 +00:00
use std::io;
2018-07-30 11:18:43 +00:00
use aes_ctr::Aes128Ctr;
use aes_ctr::stream_cipher::{
2018-12-06 09:49:23 +00:00
NewStreamCipher, SyncStreamCipher, SyncStreamCipherSeek
2018-07-30 11:18:43 +00:00
};
use aes_ctr::stream_cipher::generic_array::GenericArray;
2015-06-23 14:38:29 +00:00
2017-08-03 18:58:44 +00:00
use core::audio_key::AudioKey;
2015-06-23 14:38:29 +00:00
2018-07-30 11:18:43 +00:00
const AUDIO_AESIV: [u8; 16] = [
0x72, 0xe0, 0x67, 0xfb, 0xdd, 0xcb, 0xcf, 0x77,
0xeb, 0xe8, 0xbc, 0x64, 0x3f, 0x63, 0x0d, 0x93,
2018-02-26 01:50:41 +00:00
];
2015-06-23 14:38:29 +00:00
2016-01-02 15:19:39 +00:00
pub struct AudioDecrypt<T: io::Read> {
2018-07-30 11:18:43 +00:00
cipher: Aes128Ctr,
2015-06-23 14:38:29 +00:00
reader: T,
}
2016-01-02 15:19:39 +00:00
impl<T: io::Read> AudioDecrypt<T> {
2015-06-23 17:34:48 +00:00
pub fn new(key: AudioKey, reader: T) -> AudioDecrypt<T> {
2018-07-30 11:18:43 +00:00
let cipher = Aes128Ctr::new(
&GenericArray::from_slice(&key.0),
&GenericArray::from_slice(&AUDIO_AESIV),
);
AudioDecrypt { cipher, reader }
2015-06-23 14:38:29 +00:00
}
}
2016-01-02 15:19:39 +00:00
impl<T: io::Read> io::Read for AudioDecrypt<T> {
2015-06-23 14:38:29 +00:00
fn read(&mut self, output: &mut [u8]) -> io::Result<usize> {
2018-07-30 11:18:43 +00:00
let len = try!(self.reader.read(output));
2015-06-23 14:38:29 +00:00
2018-07-30 11:18:43 +00:00
self.cipher.apply_keystream(&mut output[..len]);
2015-06-23 14:38:29 +00:00
Ok(len)
}
}
2016-01-02 15:19:39 +00:00
impl<T: io::Read + io::Seek> io::Seek for AudioDecrypt<T> {
2015-06-23 17:34:48 +00:00
fn seek(&mut self, pos: io::SeekFrom) -> io::Result<u64> {
let newpos = try!(self.reader.seek(pos));
2018-07-30 11:18:43 +00:00
self.cipher.seek(newpos);
2015-06-23 17:34:48 +00:00
2018-07-30 11:18:43 +00:00
Ok(newpos)
2015-06-23 14:38:29 +00:00
}
}