Merge a4226746a2 into dccd0c8ccf
This commit is contained in:
commit
893be4d159
|
|
@ -118,6 +118,14 @@ def lvm_vol_change(vol: LvmVolume, activate: bool) -> None:
|
|||
SysCommand(cmd)
|
||||
|
||||
|
||||
def lvm_vg_change(vg: LvmVolumeGroup, activate: bool) -> None:
|
||||
active_flag = 'y' if activate else 'n'
|
||||
cmd = ['vgchange', '-a', active_flag, vg.name]
|
||||
|
||||
debug(f'vgchange volume group: {" ".join(cmd)}')
|
||||
SysCommand(cmd)
|
||||
|
||||
|
||||
def lvm_export_vg(vg: LvmVolumeGroup) -> None:
|
||||
cmd = f'vgexport {vg.name}'
|
||||
|
||||
|
|
|
|||
|
|
@ -1,12 +1,18 @@
|
|||
import os
|
||||
from contextlib import suppress
|
||||
from pathlib import Path
|
||||
from typing import TYPE_CHECKING
|
||||
|
||||
from pydantic import BaseModel
|
||||
|
||||
from archinstall.lib.command import SysCommand
|
||||
from archinstall.lib.exceptions import DiskError, SysCallError
|
||||
from archinstall.lib.models.device import LsblkInfo
|
||||
from archinstall.lib.models.device import EncryptionType, FilesystemType, LsblkInfo
|
||||
from archinstall.lib.output import debug, info, warn
|
||||
|
||||
if TYPE_CHECKING:
|
||||
from archinstall.lib.installer import Installer
|
||||
|
||||
|
||||
class LsblkOutput(BaseModel):
|
||||
blockdevices: list[LsblkInfo]
|
||||
|
|
@ -196,3 +202,119 @@ def swapon(path: Path) -> None:
|
|||
SysCommand(['swapon', str(path)])
|
||||
except SysCallError as err:
|
||||
raise DiskError(f'Could not enable swap {path}:\n{err.message}')
|
||||
|
||||
|
||||
def teardown(installer: Installer) -> None:
|
||||
if not installer._layout_teardown_required:
|
||||
debug('No mounted layout registered for teardown')
|
||||
return
|
||||
|
||||
info('Tearing down installation target')
|
||||
|
||||
with suppress(Exception):
|
||||
os.sync()
|
||||
|
||||
_swapoff_layout(installer)
|
||||
|
||||
with suppress(SysCallError, DiskError):
|
||||
umount(installer.target, recursive=True)
|
||||
|
||||
match installer._disk_encryption.encryption_type:
|
||||
case EncryptionType.LUKS:
|
||||
_teardown_luks_partitions(installer)
|
||||
|
||||
case EncryptionType.LUKS_ON_LVM:
|
||||
_teardown_luks_lvm(installer)
|
||||
_teardown_lvm(installer)
|
||||
|
||||
case EncryptionType.LVM_ON_LUKS:
|
||||
_teardown_lvm(installer)
|
||||
_teardown_luks_partitions(installer)
|
||||
|
||||
case EncryptionType.NO_ENCRYPTION:
|
||||
_teardown_lvm(installer)
|
||||
|
||||
with suppress(SysCallError):
|
||||
udev_sync()
|
||||
|
||||
installer._layout_teardown_required = False
|
||||
|
||||
|
||||
def _swapoff_path(path: Path | None) -> None:
|
||||
if path is None:
|
||||
return
|
||||
|
||||
with suppress(SysCallError, DiskError):
|
||||
SysCommand(['swapoff', str(path)])
|
||||
|
||||
|
||||
def _swapoff_layout(installer: Installer) -> None:
|
||||
for mod in installer._disk_config.device_modifications:
|
||||
for part in mod.partitions:
|
||||
if part.is_swap():
|
||||
_swapoff_path(part.dev_path)
|
||||
|
||||
if part.mapper_name:
|
||||
_swapoff_path(Path('/dev/mapper') / part.mapper_name)
|
||||
|
||||
if not installer._disk_config.lvm_config:
|
||||
return
|
||||
|
||||
for vol in installer._disk_config.lvm_config.get_all_volumes():
|
||||
if vol.fs_type == FilesystemType.LINUX_SWAP:
|
||||
_swapoff_path(vol.dev_path)
|
||||
|
||||
if vol.mapper_name:
|
||||
_swapoff_path(Path('/dev/mapper') / vol.mapper_name)
|
||||
|
||||
|
||||
def _teardown_lvm(installer: Installer) -> None:
|
||||
from archinstall.lib.disk.lvm import lvm_vg_change, lvm_vol_change
|
||||
|
||||
lvm_config = installer._disk_config.lvm_config
|
||||
|
||||
if not lvm_config:
|
||||
return
|
||||
|
||||
for vg in reversed(lvm_config.vol_groups):
|
||||
for vol in reversed(vg.volumes):
|
||||
if not vol.dev_path:
|
||||
continue
|
||||
|
||||
with suppress(SysCallError, DiskError):
|
||||
lvm_vol_change(vol, False)
|
||||
|
||||
with suppress(SysCallError, DiskError):
|
||||
lvm_vg_change(vg, False)
|
||||
|
||||
|
||||
def _teardown_luks_partitions(installer: Installer) -> None:
|
||||
from archinstall.lib.disk.luks import Luks2
|
||||
|
||||
for part_mod in reversed(installer._disk_encryption.partitions):
|
||||
if not part_mod.dev_path or not part_mod.mapper_name:
|
||||
continue
|
||||
|
||||
luks_handler = Luks2(
|
||||
part_mod.dev_path,
|
||||
mapper_name=part_mod.mapper_name,
|
||||
)
|
||||
|
||||
with suppress(SysCallError, DiskError):
|
||||
luks_handler.lock()
|
||||
|
||||
|
||||
def _teardown_luks_lvm(installer: Installer) -> None:
|
||||
from archinstall.lib.disk.luks import Luks2
|
||||
|
||||
for vol in reversed(installer._disk_encryption.lvm_volumes):
|
||||
if not vol.dev_path or not vol.mapper_name:
|
||||
continue
|
||||
|
||||
luks_handler = Luks2(
|
||||
vol.dev_path,
|
||||
mapper_name=vol.mapper_name,
|
||||
)
|
||||
|
||||
with suppress(SysCallError, DiskError):
|
||||
luks_handler.lock()
|
||||
|
|
|
|||
|
|
@ -24,6 +24,7 @@ from archinstall.lib.disk.utils import (
|
|||
get_unique_path_for_device,
|
||||
mount,
|
||||
swapon,
|
||||
teardown,
|
||||
)
|
||||
from archinstall.lib.exceptions import DiskError, HardwareIncompatibilityError, RequirementError, ServiceException, SysCallError
|
||||
from archinstall.lib.hardware import SysInfo
|
||||
|
|
@ -131,45 +132,51 @@ class Installer:
|
|||
|
||||
self._zram_enabled = False
|
||||
self._disable_fstrim = False
|
||||
|
||||
self._layout_teardown_required = False
|
||||
self.pacman = Pacman(self.target, silent)
|
||||
|
||||
def __enter__(self) -> Self:
|
||||
return self
|
||||
|
||||
def __exit__(self, exc_type: type[BaseException] | None, exc_value: BaseException | None, traceback: TracebackType | None) -> bool | None:
|
||||
if exc_type is not None:
|
||||
error(str(exc_value))
|
||||
try:
|
||||
if exc_type is not None:
|
||||
error(str(exc_value))
|
||||
|
||||
self.sync_log_to_install_medium()
|
||||
self.sync_log_to_install_medium()
|
||||
|
||||
# We avoid printing /mnt/<log path> because that might confuse people if they note it down
|
||||
# and then reboot, and an identical log file will be found in the ISO medium anyway.
|
||||
print(tr('[!] A log file has been created here: {}').format(logger.path))
|
||||
print(tr('Please submit this issue (and file) to https://github.com/archlinux/archinstall/issues'))
|
||||
# We avoid printing /mnt/<log path> because that might confuse people if they note it down
|
||||
# and then reboot, and an identical log file will be found in the ISO medium anyway.
|
||||
print(tr('[!] A log file has been created here: {}').format(logger.path))
|
||||
print(tr('Please submit this issue (and file) to https://github.com/archlinux/archinstall/issues'))
|
||||
|
||||
# Return None to propagate the exception
|
||||
return None
|
||||
# Return None to propagate the exception
|
||||
return None
|
||||
|
||||
info(tr('Syncing the system...'))
|
||||
os.sync()
|
||||
info(tr('Syncing the system...'))
|
||||
os.sync()
|
||||
|
||||
if not (missing_steps := self.post_install_check()):
|
||||
msg = f'Installation completed without any errors.\nLog files temporarily available at {logger.directory}.\nYou may reboot when ready.\n'
|
||||
log(msg, fg='green')
|
||||
self.sync_log_to_install_medium()
|
||||
return True
|
||||
else:
|
||||
warn('Some required steps were not successfully installed/configured before leaving the installer:')
|
||||
if not (missing_steps := self.post_install_check()):
|
||||
msg = f'Installation completed without any errors.\nLog files temporarily available at {logger.directory}.\nYou may reboot when ready.\n'
|
||||
log(msg, fg='green')
|
||||
self.sync_log_to_install_medium()
|
||||
return True
|
||||
else:
|
||||
warn('Some required steps were not successfully installed/configured before leaving the installer:')
|
||||
|
||||
for step in missing_steps:
|
||||
warn(f' - {step}')
|
||||
for step in missing_steps:
|
||||
warn(f' - {step}')
|
||||
|
||||
warn(f'Detailed error logs can be found at: {logger.directory}')
|
||||
warn('Submit this zip file as an issue to https://github.com/archlinux/archinstall/issues')
|
||||
warn(f'Detailed error logs can be found at: {logger.directory}')
|
||||
warn('Submit this zip file as an issue to https://github.com/archlinux/archinstall/issues')
|
||||
|
||||
self.sync_log_to_install_medium()
|
||||
return False
|
||||
self.sync_log_to_install_medium()
|
||||
return False
|
||||
finally:
|
||||
try:
|
||||
teardown(self)
|
||||
except Exception as err:
|
||||
warn(f'Failed to teardown installation target: {err}')
|
||||
|
||||
def remove_mod(self, mod: str) -> None:
|
||||
if mod in self._modules:
|
||||
|
|
@ -257,6 +264,7 @@ class Installer:
|
|||
|
||||
def mount_ordered_layout(self) -> None:
|
||||
debug('Mounting ordered layout')
|
||||
self._layout_teardown_required = True
|
||||
|
||||
luks_handlers: dict[Any, Luks2] = {}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue