Allow working on loop devices

This commit is contained in:
Roey Darwish Dror 2018-11-22 14:53:38 +02:00
parent 6e04daa846
commit 4e0940cc1f
4 changed files with 27 additions and 23 deletions

View File

@ -27,7 +27,8 @@ Dependencies will be handled for you if you install alma from AUR.
sudo alma create /dev/disk/by-id/usb-Generic_USB_Flash_Disk-0:0 sudo alma create /dev/disk/by-id/usb-Generic_USB_Flash_Disk-0:0
``` ```
This will wipe the entire disk and create a bootable installation of Arch Linux. This will wipe the entire disk and create a bootable installation of Arch Linux. You can use either
removable devices or loop devices. As a precaution, ALMA will not wipe non-removable devices.
After the installation is done you can either boot from it immediately or use `arch-chroot` to After the installation is done you can either boot from it immediately or use `arch-chroot` to
perform further customizations before your first boot. perform further customizations before your first boot.

View File

@ -23,7 +23,12 @@ impl BlockDevice {
path, real_path, device_name path, real_path, device_name
); );
Ok(Self { name: device_name }) let _self = Self { name: device_name };
if !(_self.is_removable()? || _self.is_loop_device()) {
return Err(ErrorKind::DangerousDevice)?;
}
Ok(_self)
} }
fn sys_path(&self) -> PathBuf { fn sys_path(&self) -> PathBuf {
@ -32,7 +37,7 @@ impl BlockDevice {
path path
} }
pub fn removable(&self) -> Result<bool, Error> { fn is_removable(&self) -> Result<bool, Error> {
let mut path = self.sys_path(); let mut path = self.sys_path();
path.push("removable"); path.push("removable");
@ -43,6 +48,12 @@ impl BlockDevice {
Ok(result == "1\n") Ok(result == "1\n")
} }
fn is_loop_device(&self) -> bool {
let mut path = self.sys_path();
path.push("loop");
path.exists()
}
pub fn device_path(&self) -> PathBuf { pub fn device_path(&self) -> PathBuf {
let mut path = PathBuf::from("/dev"); let mut path = PathBuf::from("/dev");
path.push(self.name.clone()); path.push(self.name.clone());

View File

@ -14,8 +14,8 @@ pub enum ErrorKind {
#[fail(display = "Invalid device name")] #[fail(display = "Invalid device name")]
InvalidDeviceName, InvalidDeviceName,
#[fail(display = "The given block device is not removable")] #[fail(display = "The given block device is neither removable nor a loop device")]
NotRemovableDevice, DangerousDevice,
#[fail(display = "Partition {} does not exist", _0)] #[fail(display = "Partition {} does not exist", _0)]
NoSuchPartition(u8), NoSuchPartition(u8),

View File

@ -62,7 +62,7 @@ enum Command {
struct CreateCommand { struct CreateCommand {
/// Path starting with /dev/disk/by-id for the USB drive /// Path starting with /dev/disk/by-id for the USB drive
#[structopt(parse(from_os_str),)] #[structopt(parse(from_os_str),)]
disk: PathBuf, block_device: PathBuf,
/// Additional pacakges to install /// Additional pacakges to install
#[structopt(short = "p", long = "extra-packages", value_name = "package",)] #[structopt(short = "p", long = "extra-packages", value_name = "package",)]
@ -77,7 +77,7 @@ struct CreateCommand {
struct ChrootCommand { struct ChrootCommand {
/// Path starting with /dev/disk/by-id for the USB drive /// Path starting with /dev/disk/by-id for the USB drive
#[structopt(parse(from_os_str),)] #[structopt(parse(from_os_str),)]
disk: PathBuf, block_device: PathBuf,
} }
fn create(command: CreateCommand) -> Result<(), Error> { fn create(command: CreateCommand) -> Result<(), Error> {
@ -88,18 +88,14 @@ fn create(command: CreateCommand) -> Result<(), Error> {
let mkfat = Tool::find("mkfs.fat")?; let mkfat = Tool::find("mkfs.fat")?;
let mkbtrfs = Tool::find("mkfs.btrfs")?; let mkbtrfs = Tool::find("mkfs.btrfs")?;
let disk = block::BlockDevice::from_path(command.disk)?; let block_device = block::BlockDevice::from_path(command.block_device)?;
if !disk.removable()? {
Err(ErrorKind::NotRemovableDevice)?;
}
let mount_point = tempdir().context(ErrorKind::TmpDirError)?; let mount_point = tempdir().context(ErrorKind::TmpDirError)?;
let boot_point = mount_point.path().join("boot"); let boot_point = mount_point.path().join("boot");
let mut mount_stack = MountStack::new(); let mut mount_stack = MountStack::new();
let disk_path = disk.device_path(); let disk_path = block_device.device_path();
info!("Partitioning the disk"); info!("Partitioning the block device");
debug!("{:?}", disk_path); debug!("{:?}", disk_path);
sgdisk sgdisk
@ -118,14 +114,14 @@ fn create(command: CreateCommand) -> Result<(), Error> {
thread::sleep(Duration::from_millis(1000)); thread::sleep(Duration::from_millis(1000));
info!("Formatting filesystems"); info!("Formatting filesystems");
let boot_partition = disk.partition_device_path(2)?; let boot_partition = block_device.partition_device_path(2)?;
mkfat mkfat
.execute() .execute()
.arg("-F32") .arg("-F32")
.arg(&boot_partition) .arg(&boot_partition)
.run(ErrorKind::Formatting)?; .run(ErrorKind::Formatting)?;
let root_partition = disk.partition_device_path(3)?; let root_partition = block_device.partition_device_path(3)?;
mkbtrfs mkbtrfs
.execute() .execute()
.arg("-f") .arg("-f")
@ -219,18 +215,14 @@ fn create(command: CreateCommand) -> Result<(), Error> {
fn chroot(command: ChrootCommand) -> Result<(), Error> { fn chroot(command: ChrootCommand) -> Result<(), Error> {
let arch_chroot = Tool::find("arch-chroot")?; let arch_chroot = Tool::find("arch-chroot")?;
let disk = block::BlockDevice::from_path(command.disk)?; let block_device = block::BlockDevice::from_path(command.block_device)?;
if !disk.removable()? {
Err(ErrorKind::NotRemovableDevice)?;
}
let mount_point = tempdir().context(ErrorKind::TmpDirError)?; let mount_point = tempdir().context(ErrorKind::TmpDirError)?;
let boot_point = mount_point.path().join("boot"); let boot_point = mount_point.path().join("boot");
let mut mount_stack = MountStack::new(); let mut mount_stack = MountStack::new();
info!("Mounting filesystems to {}", mount_point.path().display()); info!("Mounting filesystems to {}", mount_point.path().display());
let root_partition = disk.partition_device_path(3)?; let root_partition = block_device.partition_device_path(3)?;
mount_stack mount_stack
.mount( .mount(
&root_partition, &root_partition,
@ -239,7 +231,7 @@ fn chroot(command: ChrootCommand) -> Result<(), Error> {
None, None,
).context(ErrorKind::Mounting)?; ).context(ErrorKind::Mounting)?;
let boot_partition = disk.partition_device_path(2)?; let boot_partition = block_device.partition_device_path(2)?;
mount_stack mount_stack
.mount(&boot_partition, &boot_point, Filesystem::Vfat, None) .mount(&boot_partition, &boot_point, Filesystem::Vfat, None)
.context(ErrorKind::Mounting)?; .context(ErrorKind::Mounting)?;