fxfs_crypto/cipher/
fxfs.rs1use super::{Cipher, SECTOR_SIZE, Tweak, UnwrappedKey, XtsProcessor};
5use aes::Aes256;
6use aes::cipher::generic_array::GenericArray;
7use aes::cipher::{BlockDecrypt, BlockEncrypt, KeyInit};
8use anyhow::Error;
9use log::warn;
10use zerocopy::IntoBytes;
11
12#[derive(Debug)]
13pub struct FxfsCipher {
14 key: Aes256,
15}
16impl FxfsCipher {
17 pub fn new(key: &UnwrappedKey) -> Self {
18 Self { key: Aes256::new(GenericArray::from_slice(key)) }
19 }
20}
21impl Cipher for FxfsCipher {
22 fn encrypt(
23 &self,
24 _ino: u64,
25 _device_offset: u64,
26 file_offset: u64,
27 buffer: &mut [u8],
28 ) -> Result<(), Error> {
29 fxfs_trace::duration!("encrypt", "len" => buffer.len());
30 assert_eq!(file_offset % SECTOR_SIZE, 0);
31 let mut sector_offset = file_offset / SECTOR_SIZE;
32 assert_eq!(buffer.len() % (SECTOR_SIZE as usize), 0);
33 for sector in buffer.chunks_exact_mut(SECTOR_SIZE as usize) {
34 let mut tweak = Tweak(sector_offset as u128);
35 self.key.encrypt_block(GenericArray::from_mut_slice(tweak.as_mut_bytes()));
37 self.key.encrypt_with_backend(XtsProcessor::new(tweak, sector));
38 sector_offset += 1;
39 }
40 Ok(())
41 }
42
43 fn decrypt(
44 &self,
45 _ino: u64,
46 _device_offset: u64,
47 file_offset: u64,
48 buffer: &mut [u8],
49 ) -> Result<(), Error> {
50 fxfs_trace::duration!("decrypt", "len" => buffer.len());
51 assert_eq!(file_offset % SECTOR_SIZE, 0);
52 let mut sector_offset = file_offset / SECTOR_SIZE;
53 assert_eq!(buffer.len() % (SECTOR_SIZE as usize), 0);
54 for sector in buffer.chunks_exact_mut(SECTOR_SIZE as usize) {
55 let mut tweak = Tweak(sector_offset as u128);
56 self.key.encrypt_block(GenericArray::from_mut_slice(tweak.as_mut_bytes()));
58 self.key.decrypt_with_backend(XtsProcessor::new(tweak, sector));
59 sector_offset += 1;
60 }
61 Ok(())
62 }
63
64 fn encrypt_filename(&self, _object_id: u64, _buffer: &mut Vec<u8>) -> Result<(), Error> {
65 debug_assert!(false, "encrypt_filename called on fxfs cipher");
66 Err(zx_status::Status::NOT_SUPPORTED.into())
67 }
68
69 fn decrypt_filename(&self, _object_id: u64, _buffer: &mut Vec<u8>) -> Result<(), Error> {
70 warn!("decrypt_filename called on fxfs cipher");
72 Err(zx_status::Status::NOT_SUPPORTED.into())
73 }
74
75 fn hash_code(&self, _raw_filename: &[u8], _filename: &str) -> Option<u32> {
76 debug_assert!(false, "hash_code called on fxfs cipher");
77 None
78 }
79
80 fn hash_code_casefold(&self, _filename: &str) -> u32 {
81 debug_assert!(false, "hash_code_casefold called on fxfs cipher");
82 0
83 }
84
85 fn supports_inline_encryption(&self) -> bool {
86 false
87 }
88
89 fn crypt_ctx(&self, _ino: u64, _file_offset: u64) -> Option<(u32, u8)> {
90 None
91 }
92}