diff --git a/src/args.rs b/src/args.rs index bf33d1f..7cd890f 100644 --- a/src/args.rs +++ b/src/args.rs @@ -66,10 +66,6 @@ pub struct ChrootCommand { #[structopt(parse(from_os_str))] pub block_device: PathBuf, - /// Open an encrypted root partition - #[structopt(short = "e", long = "encrypted-root")] - pub encrypted_root: bool, - /// Optional command to run #[structopt()] pub command: Vec, diff --git a/src/error.rs b/src/error.rs index 2df89e8..7b110bc 100644 --- a/src/error.rs +++ b/src/error.rs @@ -68,6 +68,9 @@ pub enum ErrorKind { #[fail(display = "Error closing the encrypted device")] LuksClose, + #[fail(display = "Error detecting whether the root partition is an encrypted device")] + LuksDetection, + #[fail(display = "Error setting the locale")] Locale, diff --git a/src/main.rs b/src/main.rs index 839e117..630e4cc 100644 --- a/src/main.rs +++ b/src/main.rs @@ -324,11 +324,7 @@ fn create(command: CreateCommand) -> Result<(), Error> { fn chroot(command: ChrootCommand) -> Result<(), Error> { let arch_chroot = Tool::find("arch-chroot")?; - let cryptsetup = if command.encrypted_root { - Some(Tool::find("cryptsetup")?) - } else { - None - }; + let mut cryptsetup; let mut loop_device: Option; let storage_device = match storage::StorageDevice::from_path(&command.block_device) { @@ -344,9 +340,10 @@ fn chroot(command: ChrootCommand) -> Result<(), Error> { let boot_filesystem = Filesystem::from_partition(&boot_partition, FilesystemType::Vfat); let root_partition_base = storage_device.get_partition(ROOT_PARTITION_INDEX)?; - let encrypted_root = if let Some(cryptsetup) = &cryptsetup { + let encrypted_root = if is_encrypted_device(&root_partition_base)? { + cryptsetup = Some(Tool::find("cryptsetup")?); Some(EncryptedDevice::open( - cryptsetup, + cryptsetup.as_ref().unwrap(), &root_partition_base, "alma_root".into(), )?) diff --git a/src/storage/crypt.rs b/src/storage/crypt.rs index 3270b00..11d5f41 100644 --- a/src/storage/crypt.rs +++ b/src/storage/crypt.rs @@ -2,10 +2,16 @@ use super::markers::BlockDevice; use crate::error::{Error, ErrorKind}; use crate::process::CommandExt; use crate::tool::Tool; +use failure::ResultExt; use log::{debug, warn}; +use std::fs; +use std::io::Read; use std::marker::PhantomData; use std::path::{Path, PathBuf}; +static LUKS_MAGIC_1: &'static [u8] = &[0x4c, 0x55, 0x4b, 0x53, 0xba, 0xbe]; +static LUKS_MAGIC_2: &'static [u8] = &[0x53, 0x4b, 0x55, 0x4c, 0xba, 0xbe]; + #[derive(Debug)] pub struct EncryptedDevice<'t, 'o> { cryptsetup: &'t Tool, @@ -78,3 +84,17 @@ impl<'t, 'o> BlockDevice for EncryptedDevice<'t, 'o> { &self.path } } + +pub fn is_encrypted_device(device: &BlockDevice) -> Result { + let mut f = fs::OpenOptions::new() + .read(true) + .write(false) + .open(device.path()) + .context(ErrorKind::LuksDetection)?; + + let mut buffer = [0; 6]; + f.read_exact(&mut buffer) + .context(ErrorKind::LuksDetection)?; + + Ok(buffer == LUKS_MAGIC_1 || buffer == LUKS_MAGIC_2) +} diff --git a/src/storage/mod.rs b/src/storage/mod.rs index 3f38d0b..983d5ab 100644 --- a/src/storage/mod.rs +++ b/src/storage/mod.rs @@ -6,7 +6,7 @@ mod mount_stack; mod partition; mod storage_device; -pub use crypt::EncryptedDevice; +pub use crypt::{is_encrypted_device, EncryptedDevice}; pub use filesystem::{Filesystem, FilesystemType}; pub use loop_device::LoopDevice; pub use markers::BlockDevice;