Change block cipher mode from XTS -> HCTR2

We will be using aes-hctr2-plain64 cipher for  encryptedstore.

Reason: With XTS, an attacker can tamper or replay at 16-byte
granularity. A bit flip in the encrypted text diffuses randomly in
plaintext, but only within an aligned 16-byte range. But with HCTR2 this
diffusion will be at crypto sector size.

For IV we use the 64 bytes' sector number referred to as "plain64".

Bug: 259253336
Test: Run a vm with --storage & --storage-size flag
Change-Id: I1ecd98072d6cb552d93fbc4053a3e6f004e0854e
diff --git a/encryptedstore/src/main.rs b/encryptedstore/src/main.rs
index d7d2382..5f27fd7 100644
--- a/encryptedstore/src/main.rs
+++ b/encryptedstore/src/main.rs
@@ -45,7 +45,7 @@
         .args(&[
             arg!(--blkdevice <FILE> "the block device backing the encrypted storage")
                 .required(true),
-            arg!(--key <KEY> "key (in hex) equivalent to 64 bytes)").required(true),
+            arg!(--key <KEY> "key (in hex) equivalent to 32 bytes)").required(true),
             arg!(--mountpoint <MOUNTPOINT> "mount point for the storage").required(true),
         ])
         .get_matches();
@@ -87,12 +87,12 @@
 fn enable_crypt(data_device: &Path, key: &str, name: &str) -> Result<PathBuf> {
     let dev_size = util::blkgetsize64(data_device)?;
     let key = hex::decode(key).context("Unable to decode hex key")?;
-    ensure!(key.len() == 64, "We need 64 bytes' key for aes-xts cipher for block encryption");
+    ensure!(key.len() == 32, "We need 32 bytes' key for aes-hctr2 cipher for block encryption");
 
     // Create the dm-crypt spec
     let target = dm::crypt::DmCryptTargetBuilder::default()
         .data_device(data_device, dev_size)
-        .cipher(CipherType::AES256XTS) // TODO(b/259253336) Move to HCTR2 based encryption.
+        .cipher(CipherType::AES256HCTR2)
         .key(&key)
         .build()
         .context("Couldn't build the DMCrypt target")?;
diff --git a/libs/devicemapper/src/crypt.rs b/libs/devicemapper/src/crypt.rs
index 9b715a5..75105ce 100644
--- a/libs/devicemapper/src/crypt.rs
+++ b/libs/devicemapper/src/crypt.rs
@@ -33,9 +33,21 @@
 
 /// Supported ciphers
 pub enum CipherType {
-    // TODO(b/253394457) Include ciphers with authenticated modes as well
+    // AES-256-HCTR2 takes a 32-byte key
+    AES256HCTR2,
+    // XTS requires key of twice the length of the underlying block cipher i.e., 64B for AES256
     AES256XTS,
 }
+impl CipherType {
+    fn get_kernel_crypto_name(&self) -> &str {
+        match *self {
+            // We use "plain64" as the IV/nonce generation algorithm -
+            // which basically is the sector number.
+            CipherType::AES256HCTR2 => "aes-hctr2-plain64",
+            CipherType::AES256XTS => "aes-xts-plain64",
+        }
+    }
+}
 
 pub struct DmCryptTarget(Box<[u8]>);
 
@@ -59,7 +71,7 @@
 impl<'a> Default for DmCryptTargetBuilder<'a> {
     fn default() -> Self {
         DmCryptTargetBuilder {
-            cipher: CipherType::AES256XTS,
+            cipher: CipherType::AES256HCTR2,
             key: None,
             iv_offset: 0,
             device_path: None,
@@ -121,7 +133,7 @@
         // <offset> [<#opt_params> <opt_params>]
         let mut body = String::new();
         use std::fmt::Write;
-        write!(&mut body, "{} ", get_kernel_crypto_name(&self.cipher))?;
+        write!(&mut body, "{} ", self.cipher.get_kernel_crypto_name())?;
         write!(&mut body, "{} ", key)?;
         write!(&mut body, "{} ", self.iv_offset)?;
         write!(&mut body, "{} ", device_path)?;
@@ -145,9 +157,3 @@
         Ok(DmCryptTarget(buf.into_boxed_slice()))
     }
 }
-
-fn get_kernel_crypto_name(cipher: &CipherType) -> &str {
-    match cipher {
-        CipherType::AES256XTS => "aes-xts-plain64",
-    }
-}
diff --git a/microdroid_manager/src/main.rs b/microdroid_manager/src/main.rs
index a706dbe..341105c 100644
--- a/microdroid_manager/src/main.rs
+++ b/microdroid_manager/src/main.rs
@@ -85,7 +85,7 @@
 const ENCRYPTEDSTORE_BACKING_DEVICE: &str = "/dev/block/by-name/encryptedstore";
 const ENCRYPTEDSTORE_BIN: &str = "/system/bin/encryptedstore";
 const ENCRYPTEDSTORE_KEY_IDENTIFIER: &str = "encryptedstore_key";
-const ENCRYPTEDSTORE_KEYSIZE: u32 = 64;
+const ENCRYPTEDSTORE_KEYSIZE: u32 = 32;
 const ENCRYPTEDSTORE_MOUNTPOINT: &str = "/mnt/encryptedstore";
 
 #[derive(thiserror::Error, Debug)]