V8.00.000.2025.06.17
Signed-off-by: Marc S. Weidner <msw@coresecret.dev>
This commit is contained in:
@@ -1,503 +0,0 @@
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
recipe:
|
||||
guben0afx256r: # g=GPT || m=MBR
|
||||
# u=UEFI || b=BIOS
|
||||
# b=btrfs || 4=ext4 only
|
||||
# e=ephemeral "/tmp" and "SWAP" || n=non-ephemeral "/tmp" and "SWAP" (yet not supported)
|
||||
# n0=non RAID || m6=mdadm RAID6 || m5=mdadm RAID5 || b1=btrfs RAID1 (yet not supported)
|
||||
# a="/dev/sda" only setup || b="/dev/sdb" || c="/dev/sdc" and so forth
|
||||
# f=fixed size || a=automatic size (yet not supported)
|
||||
# x256=size of device in GiB
|
||||
# r=rescue partition || n=no rescue partition
|
||||
#######################################
|
||||
# EFI System Partition | EF00 | UEFI Bootloader (ESP, FAT32) | filesystem.version: fat32
|
||||
# BIOS Boot Partition | EF02 | BIOS Bootloader area (GRUB) | filesystem.version: BIOS
|
||||
# Linux SWAP | 8200 | Linux Swap | filesystem.version: SWAP
|
||||
# Linux ext4/btrfs | 8300 | Linux Filesystem (root, home)| filesystem.version: ext4 || btrfs
|
||||
#######################################
|
||||
active: true # Choose this recipe.
|
||||
control:
|
||||
description: "CISS 2025 - GPT - BTRFS - Ephemeral - non RAID - 256GiB - rescue"
|
||||
firmware: "UEFI" # MUST be "UEFI" for "gpt" || "BIOS":
|
||||
id: "guben0afx256r" # MUST be equal to the second part of the recipe-variables string.
|
||||
name: "ciss.2025.gpt.btrfs.ephemeral.non-raid.256GiB.rescue"
|
||||
nuke: true # Activates Nuke-Mechanism in '/etc/crypttab' keyscript and via dropbear SSH forced command.
|
||||
raid: # mdadm RAID settings only (not yet supported).
|
||||
enable: false
|
||||
disks:
|
||||
member: 4
|
||||
spare: 1
|
||||
level: 6 # Only Level "1", "5", "6" and "10" are supported.
|
||||
meta: 1.2 # Metadata Format. Default to '1.2'.
|
||||
table: "gpt" # MUST be "gpt" for "UEFI" || "msdos":
|
||||
syntax: true # This is set to "false" by default, otherwise if the recipe is tested by the authors to "true".
|
||||
### Version of the specific recipe.
|
||||
version: "1.1.7"
|
||||
dev:
|
||||
sda:
|
||||
1:
|
||||
begin: "2MiB"
|
||||
end: "1024MiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: false # MUST be "false" for "/boot/efi"
|
||||
ephemeral: false # MUST be "false" for "/boot/efi"
|
||||
integrity: false # MUST be "false" for "/boot/efi"
|
||||
cipher: ""
|
||||
hash: ""
|
||||
itertime: ""
|
||||
key: ""
|
||||
label: ""
|
||||
metadatasize: ""
|
||||
pbkdf: ""
|
||||
rng: ""
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: ""
|
||||
compress: ""
|
||||
level: ""
|
||||
mdup: ""
|
||||
subvolume: ""
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "ESP"
|
||||
options: ""
|
||||
version: "fat32"
|
||||
label: ""
|
||||
mount:
|
||||
enable: true # MUST be "true" for "/boot/efi"
|
||||
options: "umask=0077,uid=0,gid=0"
|
||||
optsnap: ""
|
||||
path: "/boot/efi"
|
||||
primary: primary
|
||||
2:
|
||||
begin: "1024MiB"
|
||||
end: "2GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false # MUST be "false" for "/boot"
|
||||
integrity: false # MUST be "false" for "/boot"
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_boot"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "pbkdf2" # MUST be "pbkdf2" for "/boot"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "0"
|
||||
mdup: true
|
||||
subvolume: "@boot"
|
||||
snapshot: ""
|
||||
format: true
|
||||
version: "btrfs"
|
||||
label: "btrfs_boot"
|
||||
options: ""
|
||||
label: "part_boot"
|
||||
mount:
|
||||
enable: true # MUST be "true" for "/boot"
|
||||
options: "defaults,nodev,nosuid,noexec,noatime,compress=no,discard=async,subvol=@boot"
|
||||
optsnap: ""
|
||||
path: "/boot"
|
||||
primary: primary
|
||||
3:
|
||||
begin: "2GiB"
|
||||
end: "10GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_rescue"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: ""
|
||||
compress: ""
|
||||
level: ""
|
||||
mdup: ""
|
||||
subvolume: ""
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "ext4_rescue"
|
||||
options: ""
|
||||
version: "ext4"
|
||||
label: "part_recovery"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev"
|
||||
optsnap: ""
|
||||
path: "/recovery"
|
||||
primary: primary
|
||||
4:
|
||||
begin: "10GiB"
|
||||
end: "14GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true # MUST be "true" for ephemeral "SWAP"
|
||||
ephemeral: true # MUST be "true" for ephemeral "SWAP"
|
||||
integrity: false # MUST be "false" for ephemeral "SWAP"
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_ephemeral_swap"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: ""
|
||||
compress: ""
|
||||
level: ""
|
||||
mdup: ""
|
||||
subvolume: ""
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "host_swap" # MUST be "host_swap" for ephemeral "SWAP"
|
||||
options: ""
|
||||
version: "ext4" # MUST be "ext4" for ephemeral "SWAP"
|
||||
label: "part_ephem_swap"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,discard"
|
||||
optsnap: ""
|
||||
path: "SWAP"
|
||||
primary: primary
|
||||
5:
|
||||
begin: "14GiB"
|
||||
end: "18GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true # MUST be "true" for ephemeral "/tmp"
|
||||
ephemeral: true # MUST be "true" for ephemeral "/tmp"
|
||||
integrity: false # MUST be "false" for ephemeral "/tmp"
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_ephemeral_tmp"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: ""
|
||||
compress: ""
|
||||
level: ""
|
||||
mdup: ""
|
||||
subvolume: ""
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "host_tmp" # MUST be "host_tmp" for ephemeral "/tmp"
|
||||
options: ""
|
||||
version: "ext4" # MUST be "ext4" for ephemeral "/tmp"
|
||||
label: "part_ephem_tmp"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,rw,nodev,nosuid,noatime,discard,mode=1777"
|
||||
optsnap: ""
|
||||
path: "/tmp"
|
||||
primary: primary
|
||||
6:
|
||||
begin: "18GiB"
|
||||
end: "42GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_root"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@root"
|
||||
snapshot: "@root_snap"
|
||||
format: true
|
||||
label: "btrfs_root"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_root"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,errors=remount-ro,noatime,discard=async,autodefrag,subvol=@root"
|
||||
optsnap: "ro,nodev,nosuid,noexec,nodatacow,subvol=@root_snap"
|
||||
path: "/"
|
||||
primary: primary
|
||||
7:
|
||||
begin: "42GiB"
|
||||
end: "84GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_home"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@home"
|
||||
snapshot: "@home_snap"
|
||||
format: true
|
||||
label: "btrfs_home"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_home"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,nosuid,relatime,discard=async,autodefrag,subvol=@home"
|
||||
optsnap: "ro,nodev,nosuid,noexec,nodatacow,subvol=@home_snap"
|
||||
path: "/home"
|
||||
primary: primary
|
||||
8:
|
||||
begin: "84GiB"
|
||||
end: "126GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_usr"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@usr"
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "btrfs_usr"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_usr"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,relatime,discard=async,subvol=@usr"
|
||||
optsnap: ""
|
||||
path: "/usr"
|
||||
primary: primary
|
||||
9:
|
||||
begin: "126GiB"
|
||||
end: "190GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_var"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@var"
|
||||
snapshot: "@var_snap"
|
||||
format: true
|
||||
label: "btrfs_var"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_var"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,nosuid,relatime,discard=async,subvol=@var"
|
||||
optsnap: "ro,nodev,nosuid,noexec,nodatacow,subvol=@var_snap"
|
||||
path: "/var"
|
||||
primary: primary
|
||||
10:
|
||||
begin: "190GiB"
|
||||
end: "206GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_var_log"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@var_log"
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "btrfs_var_log"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_var_log"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,nosuid,noexec,noatime,nodatacow,discard=async,subvol=@var_log"
|
||||
optsnap: ""
|
||||
path: "/var/log"
|
||||
primary: primary
|
||||
11:
|
||||
begin: "206GiB"
|
||||
end: "222GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_var_log_audit"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@var_log_audit"
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "btrfs_var_log_audit"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_var_log_audit"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,nosuid,noexec,noatime,nodatacow,discard=async,subvol=@var_log_audit"
|
||||
optsnap: ""
|
||||
path: "/var/log/audit"
|
||||
primary: primary
|
||||
12:
|
||||
begin: "222GiB"
|
||||
end: "238GiB"
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_var_tmp"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@var_tmp"
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "btrfs_var_tmp"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_var_tmp"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,nosuid,noatime,nodatacow,discard=async,subvol=@var_tmp"
|
||||
optsnap: ""
|
||||
path: "/var/tmp"
|
||||
primary: primary
|
||||
13:
|
||||
begin: "238GiB"
|
||||
end: "max" # The last 16 MiB will be reserved for GPT metadata.
|
||||
bootable: false
|
||||
encryption:
|
||||
enable: true
|
||||
ephemeral: false
|
||||
integrity: false
|
||||
cipher: "aes-xts-plain64"
|
||||
hash: "sha512"
|
||||
itertime: "3000"
|
||||
key: "512"
|
||||
label: "crypt_opt"
|
||||
metadatasize: "4096k"
|
||||
pbkdf: "argon2id"
|
||||
rng: "use-random"
|
||||
filesystem:
|
||||
btrfs:
|
||||
checksum: "sha256"
|
||||
compress: "zstd"
|
||||
level: "7"
|
||||
mdup: true
|
||||
subvolume: "@opt"
|
||||
snapshot: ""
|
||||
format: true
|
||||
label: "btrfs_opt"
|
||||
options: ""
|
||||
version: "btrfs"
|
||||
label: "part_opt"
|
||||
mount:
|
||||
enable: true
|
||||
options: "defaults,nodev,nosuid,relatime,discard=async,subvol=@opt"
|
||||
optsnap: ""
|
||||
path: "/opt"
|
||||
primary: primary
|
||||
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=yaml
|
||||
@@ -1,81 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
#######################################
|
||||
# Performing Branch Selection
|
||||
# Globals:
|
||||
# BASH_COMMAND
|
||||
# BRANCH_URL
|
||||
# HANDLER_BRA
|
||||
# LINENO
|
||||
# LOG_ERR
|
||||
# MODULE_ERR
|
||||
# PPID
|
||||
# PWD
|
||||
# Arguments:
|
||||
# None
|
||||
#######################################
|
||||
0000_performing_branch_confirmation() {
|
||||
clear
|
||||
|
||||
declare BRANCH_SELECTION=""
|
||||
|
||||
exec 2>&1
|
||||
|
||||
if [[ ${HANDLER_BRA,,} = 1 ]]; then
|
||||
|
||||
dialog --create-rc ~/.dialogrc
|
||||
sed -i 's/screen_color = (CYAN,BLUE,ON)/screen_color = (WHITE,RED,ON)/' ~/.dialogrc
|
||||
sed -i 's/title_color = (BLUE,WHITE,ON)/title_color = (RED,WHITE,ON)/' ~/.dialogrc
|
||||
|
||||
if BRANCH_SELECTION=$(dialog --ascii-lines \
|
||||
--colors \
|
||||
--title "! WARNING !" \
|
||||
--backtitle "CISS.2025.hardened.debian.installer" \
|
||||
--yes-label "yes" \
|
||||
--no-label "No" \
|
||||
--yesno "You are on:\nBranch 'Testing'.\nPlease confirm to proceed.\nHit 'Yes' to stay on Branch 'Testing'.\nHit 'No' to exit." 9 60 3>&1 1>&2 2>&3 3>&-); then
|
||||
declare -g -r -x BRANCH_URL="https://cendev.eu/marc.weidner/CISS.2025.debian.installer/raw/branch/testing/"
|
||||
|
||||
else
|
||||
|
||||
clear
|
||||
|
||||
rm -f ~/.dialogrc
|
||||
|
||||
do_clean_exit "0" "${LINENO}" "${BASH_COMMAND}" "${MODULE_ERR}" "$$" "${PPID}" "${PWD}" "$-"
|
||||
|
||||
fi
|
||||
|
||||
else
|
||||
|
||||
declare -g -r -x BRANCH_URL="https://cendev.eu/marc.weidner/CISS.2025.debian.installer/raw/branch/master/"
|
||||
|
||||
fi
|
||||
|
||||
exec 2>> "${LOG_ERR}"
|
||||
|
||||
clear
|
||||
|
||||
if [[ ${HANDLER_BRA} = 1 ]]; then
|
||||
|
||||
do_log "info" "file_only" "Branch 'testing' confirmed: '${BRANCH_SELECTION}'."
|
||||
|
||||
fi
|
||||
|
||||
if [[ -f ~/.dialogrc ]]; then
|
||||
|
||||
rm -f ~/.dialogrc
|
||||
|
||||
fi
|
||||
}
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh:
|
||||
@@ -1,164 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
guard_sourcing
|
||||
|
||||
#######################################
|
||||
# Reading and extracting variables from "${PRESEED}".
|
||||
# Globals:
|
||||
# HMP_RECIPE_DEV_PARTITIONS
|
||||
# VAR_ARCHITECTURE
|
||||
# VAR_NUKE
|
||||
# VAR_PRESEED
|
||||
# VAR_RECIPE_FIRMWARE
|
||||
# VAR_RECIPE_HIGHEST_DEVICE
|
||||
# VAR_RECIPE_STRING
|
||||
# VAR_RECIPE_TABLE
|
||||
# architecture
|
||||
# Arguments:
|
||||
# None
|
||||
# Returns:
|
||||
# 0: on success
|
||||
# ERR_NO_VALID_RECIPE
|
||||
#######################################
|
||||
yaml_reader() {
|
||||
### Declare Arrays, HashMaps, and Variables.
|
||||
declare -Ag HMP_RECIPE_DEV_PARTITIONS=()
|
||||
declare -gx VAR_RECIPE_STRING="" VAR_RECIPE_HIGHEST_DEVICE="" VAR_ARCHITECTURE="" VAR_RECIPE_FIRMWARE="" VAR_NUKE="" \
|
||||
VAR_RECIPE_TABLE=""
|
||||
|
||||
### Declare and substitute input files
|
||||
declare -r var_if="${VAR_PRESEED}"
|
||||
### Search pattern for variables (recipe_<string>_active='true')
|
||||
declare -r var_search_pattern="^recipe_.*_active='true'"
|
||||
declare var_line="" var_middle_part="" var_highest_dev="" var_device="" var_fields="" var_partition="" \
|
||||
recipe_firmware_var="" recipe_nuke_var="" recipe_table_var=""
|
||||
|
||||
### Read "${var_if}" line by line
|
||||
while IFS= read -r var_line; do
|
||||
### Check, if line matches the search pattern
|
||||
if [[ "${var_line}" =~ ^recipe_([^_]+)_active=\'true\' ]]; then
|
||||
var_middle_part="${BASH_REMATCH[1]}"
|
||||
VAR_RECIPE_STRING="${var_middle_part}"
|
||||
break
|
||||
fi
|
||||
#if [[ "${var_line}" =~ ${var_search_pattern} ]]; then
|
||||
# ### Extract the middle part or second position
|
||||
# var_middle_part=$(echo "${var_line}" | sed -E "s/^recipe_([^_]+)_active='true'/\1/")
|
||||
# VAR_RECIPE_STRING="${var_middle_part}"
|
||||
# ### Exit after first occurrence
|
||||
# break
|
||||
#fi
|
||||
done < "${var_if}"
|
||||
|
||||
if [[ -n "${VAR_RECIPE_STRING}" ]]; then
|
||||
do_log "info" "file_only" "1251() Found active recipe string: '${VAR_RECIPE_STRING}'."
|
||||
else
|
||||
do_log "fatal" "file_only" "1251() Found NO active recipe string: '${VAR_RECIPE_STRING}'."
|
||||
exit "${ERR_NO_VALID_RECIPE}"
|
||||
fi
|
||||
|
||||
### Search "${var_if}" for matching recipe_${VAR_RECIPE_STRING}_dev_* entries and find the highest dev letter.
|
||||
# shellcheck disable=SC2312
|
||||
var_highest_dev=$(grep -E "^recipe_${VAR_RECIPE_STRING}_dev_" "${var_if}" | awk -F'_' '
|
||||
{
|
||||
if (NF >= 4) {
|
||||
### Extract 4th position (e.g., "recipe_${VAR_RECIPE_STRING}_dev_sda" or "recipe_${VAR_RECIPE_STRING}_dev_vda")
|
||||
device_field = $4
|
||||
### Check, if field is at least 3 char wide and last char contains a letter
|
||||
if (length(device_field) >= 3) {
|
||||
last_char = substr(device_field, length(device_field), 1) ### Extract last letter of respective field
|
||||
if (last_char ~ /^[a-z]$/ && last_char > max) {
|
||||
max = last_char
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
END { print max }
|
||||
')
|
||||
|
||||
### Save the result in VAR_RECIPE_HIGHEST_DEVICE.
|
||||
VAR_RECIPE_HIGHEST_DEVICE="${var_highest_dev}"
|
||||
|
||||
if [[ -n "${VAR_RECIPE_HIGHEST_DEVICE}" ]]; then
|
||||
do_log "info" "file_only" "1251() Found highest recipe device: '${VAR_RECIPE_HIGHEST_DEVICE}'."
|
||||
else
|
||||
do_log "fatal" "file_only" "1251() Found NO highest recipe device: '${VAR_RECIPE_HIGHEST_DEVICE}'."
|
||||
exit "${ERR_NO_VALID_RECIPE}"
|
||||
fi
|
||||
|
||||
### Read var_if and iterate through all matching entries without executing in a subshell
|
||||
# shellcheck disable=SC2312
|
||||
while read -r var_line; do
|
||||
### Extract fields of line
|
||||
IFS='_' read -ra var_fields <<< "${var_line}"
|
||||
|
||||
### Check that enough fields are available
|
||||
if [[ "${#var_fields[@]}" -ge 5 ]]; then
|
||||
var_device="${var_fields[3]}" ### The fourth position includes the device (e.g., sda, vda, xvda)
|
||||
var_partition="${var_fields[4]}" ### The fifth position includes the partition (e.g., 13)
|
||||
|
||||
### Check, if the partition is a number and higher than the current value
|
||||
if [[ "${var_partition}" =~ ^[0-9]+$ ]]; then
|
||||
declare -i cur="${HMP_RECIPE_DEV_PARTITIONS[${var_device}]:-0}"
|
||||
if (( var_partition > cur )); then
|
||||
|
||||
#if [[ -z "${HMP_RECIPE_DEV_PARTITIONS[${var_device}]:-}" || "${var_partition}" -gt ${HMP_RECIPE_DEV_PARTITIONS[${var_device}]:-0} ]]; then
|
||||
# shellcheck disable=SC2004
|
||||
HMP_RECIPE_DEV_PARTITIONS[${var_device}]="${var_partition}"
|
||||
fi
|
||||
|
||||
fi
|
||||
|
||||
fi
|
||||
done < <(grep -E "^recipe_${VAR_RECIPE_STRING}_dev_" "${var_if}")
|
||||
|
||||
for var_device in "${!HMP_RECIPE_DEV_PARTITIONS[@]}"; do
|
||||
do_log "info" "file_only" "1251() Highest number of partitions: [${var_device}:${HMP_RECIPE_DEV_PARTITIONS[${var_device}]}]."
|
||||
done
|
||||
|
||||
### Extract architecture.
|
||||
VAR_ARCHITECTURE="${architecture}"
|
||||
|
||||
### Extract chosen firmware.
|
||||
recipe_firmware_var="recipe_${VAR_RECIPE_STRING}_control_firmware"
|
||||
VAR_RECIPE_FIRMWARE="${!recipe_firmware_var}"
|
||||
|
||||
### Extract the chosen Nuke mechanism.
|
||||
recipe_nuke_var="recipe_${VAR_RECIPE_STRING}_control_nuke"
|
||||
VAR_NUKE="${!recipe_nuke_var}"
|
||||
|
||||
### Extract chosen partition table.
|
||||
recipe_table_var="recipe_${VAR_RECIPE_STRING}_control_table"
|
||||
VAR_RECIPE_TABLE="${!recipe_table_var}"
|
||||
|
||||
if [[ "${VAR_RECIPE_TABLE,,}" == "gpt" && "${VAR_RECIPE_FIRMWARE,,}" == "uefi" ]]; then
|
||||
|
||||
do_log "info" "file_only" "1251() Partition table: '${VAR_RECIPE_TABLE}' and firmware: '${VAR_RECIPE_FIRMWARE}' > ESP 'EF00' necessary."
|
||||
|
||||
elif [[ "${VAR_RECIPE_TABLE,,}" == "gpt" && "${VAR_RECIPE_FIRMWARE,,}" == "bios" ]]; then
|
||||
|
||||
do_log "info" "file_only" "1251() Partition table: '${VAR_RECIPE_TABLE}' and firmware: '${VAR_RECIPE_FIRMWARE}' > BIOS Boot Partition 'EF02' necessary."
|
||||
|
||||
elif [[ "${VAR_RECIPE_TABLE,,}" == "msdos" && "${VAR_RECIPE_FIRMWARE,,}" == "uefi" ]]; then
|
||||
|
||||
do_log "info" "file_only" "1251() Partition table: '${VAR_RECIPE_TABLE}' and firmware: '${VAR_RECIPE_FIRMWARE}' > ESP on MBR needs partition type '0xEF'."
|
||||
|
||||
elif [[ "${VAR_RECIPE_TABLE,,}" == "msdos" && "${VAR_RECIPE_FIRMWARE,,}" == "bios" ]]; then
|
||||
|
||||
do_log "info" "file_only" "1251() Partition table: '${VAR_RECIPE_TABLE}' and firmware: '${VAR_RECIPE_FIRMWARE}' > No special firmware partition necessary."
|
||||
|
||||
fi
|
||||
|
||||
return 0
|
||||
}
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh
|
||||
@@ -1,200 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
guard_sourcing
|
||||
|
||||
#######################################
|
||||
# Function to encrypt the respective partition on each device according to the chosen recipe string.
|
||||
# Globals:
|
||||
# DIR_BAK
|
||||
# DIR_CNF
|
||||
# DIR_LOG
|
||||
# HMP_EPHEMERAL_ENCLABEL
|
||||
# HMP_EPHEMERAL_FS_LABEL
|
||||
# HMP_PATH_ENCLABEL
|
||||
# HMP_PATH_LUKSUUID
|
||||
# VAR_CRYPT_RECOVERY
|
||||
# VAR_CRYPT_ROOT
|
||||
# VAR_ITER_TIME
|
||||
# VAR_KDF_ITERATIONS
|
||||
# VAR_KDF_MEMORY
|
||||
# VAR_KDF_THREADS
|
||||
# VAR_RECIPE_STRING
|
||||
# VAR_SETUP_PART
|
||||
# Arguments:
|
||||
# None
|
||||
# Returns:
|
||||
# 0: on success
|
||||
#######################################
|
||||
partition_encryption() {
|
||||
### Declare Arrays, HashMaps, and Variables.
|
||||
declare -Ag HMP_PATH_LUKSUUID # Used in: 3290() - [Mount Path:LUKS UUID].
|
||||
# Used in: 4060() - [Mount Path:LUKS UUID].
|
||||
declare -Ag HMP_EPHEMERAL_ENCLABEL
|
||||
declare -Ag HMP_EPHEMERAL_FS_LABEL
|
||||
|
||||
declare -Ag HMP_PATH_ENCLABEL
|
||||
|
||||
declare -gx VAR_CRYPT_ROOT="" # LUKS UUID of '/'.
|
||||
declare -gx VAR_CRYPT_RECOVERY="" # LUKS UUID of '/recovery'.
|
||||
|
||||
declare var_dev="" var_part="" \
|
||||
var_encryption_enable="" var_encryption_ephemeral="" var_encryption_integrity="" var_encryption_cipher="" \
|
||||
var_encryption_hash="" var_encryption_key="" var_encryption_label="" var_encryption_meta="" var_encryption_slot="" \
|
||||
var_encryption_pbkdf="" var_encryption_rng="" var_filesystem_label="" var_mount_path="" var_uuid="" var_fs=""
|
||||
|
||||
declare -a ary_devs=() ary_parts=() ary_luks_opts=()
|
||||
|
||||
### Iterate over all devices in the recipe.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_devs < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_dev in "${ary_devs[@]}"; do
|
||||
|
||||
touch "${DIR_LOG}/${var_dev}_cryptsetup_luksdump.log"
|
||||
chmod 0600 "${DIR_LOG}/${var_dev}_cryptsetup_luksdump.log"
|
||||
|
||||
### Iterate over all partitions for this device.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_parts < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev} | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_part in "${ary_parts[@]}"; do
|
||||
|
||||
### Extract parameters from YAML.
|
||||
var_encryption_enable=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.enable" "${VAR_SETUP_PART}")
|
||||
var_encryption_ephemeral=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.ephemeral" "${VAR_SETUP_PART}")
|
||||
var_encryption_integrity=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.integrity" "${VAR_SETUP_PART}")
|
||||
var_encryption_cipher=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.cipher" "${VAR_SETUP_PART}")
|
||||
var_encryption_hash=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.hash" "${VAR_SETUP_PART}")
|
||||
var_encryption_key=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.key" "${VAR_SETUP_PART}")
|
||||
var_encryption_slot=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.keyslotssize" "${VAR_SETUP_PART}")
|
||||
var_encryption_meta=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.metadatasize" "${VAR_SETUP_PART}")
|
||||
var_encryption_pbkdf=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.pbkdf" "${VAR_SETUP_PART}")
|
||||
var_encryption_rng=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.rng" "${VAR_SETUP_PART}")
|
||||
var_fs=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.version" "${VAR_SETUP_PART}")
|
||||
var_mount_path=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.path" "${VAR_SETUP_PART}")
|
||||
|
||||
if [[ "${var_encryption_enable,,}" != "true" ]]; then
|
||||
continue
|
||||
fi
|
||||
|
||||
var_encryption_label=$(get_label "${var_mount_path}" "${var_fs}" "luks")
|
||||
|
||||
if [[ "${var_mount_path,,}" == "/boot" ]]; then
|
||||
ary_luks_opts=( --key-file "${DIR_CNF}/password_luks_boot.txt" )
|
||||
ary_luks_opts+=(
|
||||
--iter-time "${VAR_ITER_TIME:-3000}"
|
||||
)
|
||||
else
|
||||
ary_luks_opts=( --key-file "${DIR_CNF}/password_luks_common.txt" )
|
||||
ary_luks_opts+=(
|
||||
--pbkdf-parallel "${VAR_KDF_THREADS:-1}"
|
||||
--pbkdf-memory "${VAR_KDF_MEMORY:-4}"
|
||||
--pbkdf-force-iterations "${VAR_KDF_ITERATIONS:-4}"
|
||||
)
|
||||
fi
|
||||
|
||||
ary_luks_opts+=(
|
||||
--type luks2
|
||||
--cipher "${var_encryption_cipher:-aes-xts-plain64}"
|
||||
--hash "${var_encryption_hash:-sha512}"
|
||||
--key-size "${var_encryption_key:-512}"
|
||||
--label "${var_encryption_label}"
|
||||
--luks2-keyslots-size "${var_encryption_slot:-16777216}"
|
||||
--luks2-metadata-size "${var_encryption_meta:-4194304}"
|
||||
--pbkdf "${var_encryption_pbkdf:-argon2id}"
|
||||
"--${var_encryption_rng}"
|
||||
--batch-mode
|
||||
--verbose
|
||||
)
|
||||
|
||||
[[ "${var_encryption_integrity,,}" == "true" ]] && ary_luks_opts+=( --integrity hmac-sha512 )
|
||||
|
||||
if [[ "${var_encryption_ephemeral,,}" == "true" ]]; then
|
||||
|
||||
case "${var_mount_path,,}" in
|
||||
|
||||
swap|/tmp)
|
||||
|
||||
var_filesystem_label=$(get_label "${var_mount_path}" "${var_fs}" "file")
|
||||
|
||||
mkfs.ext4 -L "${var_filesystem_label}" "/dev/${var_dev}${var_part}" 1M
|
||||
do_log "info" "file_only" "3220() Ephemeral: '${var_mount_path}' prepared on: '/dev/${var_dev}${var_part}'."
|
||||
|
||||
|
||||
HMP_EPHEMERAL_ENCLABEL["${var_mount_path}"]="${var_encryption_label}"
|
||||
HMP_EPHEMERAL_FS_LABEL["${var_mount_path}"]="${var_filesystem_label}"
|
||||
|
||||
do_log "debug" "file_only" "3220() Stored in HashMap [HMP_EPHEMERAL_ENCLABEL]: '${var_mount_path}' -> '${HMP_EPHEMERAL_ENCLABEL["${var_mount_path}"]}'"
|
||||
do_log "debug" "file_only" "3220() Stored in HashMap [HMP_EPHEMERAL_FS_LABEL]: '${var_mount_path}' -> '${HMP_EPHEMERAL_FS_LABEL["${var_mount_path}"]}'"
|
||||
continue
|
||||
;;
|
||||
|
||||
*)
|
||||
do_log "error" "file_only" "3220() Invalid mount path: '${var_mount_path}' for partition: '/dev/${var_dev}${var_part}'."
|
||||
continue
|
||||
;;
|
||||
|
||||
esac
|
||||
|
||||
fi
|
||||
|
||||
cryptsetup luksFormat "${ary_luks_opts[@]}" "/dev/${var_dev}${var_part}"
|
||||
|
||||
if [[ "${var_encryption_integrity,,}" == "true" ]]; then
|
||||
|
||||
do_log "debug" "file_only" "3220() [cryptsetup luksFormat ${ary_luks_opts[*]} /dev/${var_dev}${var_part}]."
|
||||
do_log "info" "file_only" "3220() Partition: '/dev/${var_dev}${var_part}' dm-integrity encrypted."
|
||||
|
||||
else
|
||||
|
||||
do_log "debug" "file_only" "3220() [cryptsetup luksFormat ${ary_luks_opts[*]} /dev/${var_dev}${var_part}]."
|
||||
do_log "info" "file_only" "3220() Partition: '/dev/${var_dev}${var_part}' encrypted."
|
||||
|
||||
fi
|
||||
|
||||
cryptsetup luksHeaderBackup --header-backup-file="${DIR_BAK}/luks_header_${var_dev}${var_part}.bak" "/dev/${var_dev}${var_part}"
|
||||
do_log "info" "file_only" "3220() Partition: '/dev/${var_dev}${var_part}' LUKS Header saved: '${DIR_BAK}/luks_header_${var_dev}${var_part}.bak'."
|
||||
|
||||
### Opening encrypted container.
|
||||
if [[ "${var_mount_path,,}" == "/boot" ]]; then
|
||||
cryptsetup luksOpen "/dev/${var_dev}${var_part}" \
|
||||
--key-file="${DIR_CNF}/password_luks_boot.txt" \
|
||||
"${var_encryption_label}"
|
||||
else
|
||||
cryptsetup luksOpen "/dev/${var_dev}${var_part}" \
|
||||
--key-file="${DIR_CNF}/password_luks_common.txt" \
|
||||
"${var_encryption_label}"
|
||||
fi
|
||||
do_log "info" "file_only" "3220() Partition: '/dev/${var_dev}${var_part}' opened as '/dev/mapper/${var_encryption_label}'."
|
||||
|
||||
### Create luksDump log entry.
|
||||
printf "#------------------------------------------------------------------#\n" >> "${DIR_LOG}/${var_dev}_cryptsetup_luksdump.log"
|
||||
cryptsetup luksDump "/dev/${var_dev}${var_part}" >> "${DIR_LOG}/${var_dev}_cryptsetup_luksdump.log"
|
||||
|
||||
### Store UUID of the LUKS container.
|
||||
var_uuid=$(blkid -s UUID -o value "/dev/${var_dev}${var_part}")
|
||||
|
||||
[[ "${var_mount_path}" == "/" ]] && declare -grx VAR_CRYPT_ROOT="${var_uuid}"
|
||||
[[ "${var_mount_path}" == "/recovery" ]] && declare -grx VAR_CRYPT_RECOVERY="${var_uuid}"
|
||||
|
||||
HMP_PATH_LUKSUUID["${var_mount_path}"]="${var_uuid}"
|
||||
HMP_PATH_ENCLABEL["LABEL_${var_mount_path}"]="${var_encryption_label}"
|
||||
|
||||
do_log "debug" "file_only" "3220() Stored in HashMap [HMP_PATH_LUKSUUID] : '${var_mount_path}' -> '${HMP_PATH_LUKSUUID["${var_mount_path}"]}'"
|
||||
do_log "debug" "file_only" "3220() Stored in HashMap [HMP_PATH_ENCLABEL] : '${var_mount_path}' -> '${HMP_PATH_ENCLABEL["LABEL_${var_mount_path}"]}'"
|
||||
|
||||
done
|
||||
|
||||
done
|
||||
|
||||
return 0
|
||||
}
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh
|
||||
@@ -1,138 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
guard_sourcing
|
||||
|
||||
#######################################
|
||||
# Function to format the respective partition on each device according to the recipe string chosen.
|
||||
# Globals:
|
||||
# DIR_LOG
|
||||
# HMP_PATH_FSUUID
|
||||
# VAR_RECIPE_STRING
|
||||
# VAR_SETUP_PART
|
||||
# Arguments:
|
||||
# None
|
||||
# Returns:
|
||||
# 0: on success
|
||||
#######################################
|
||||
partition_formatting() {
|
||||
### Declare Arrays, HashMaps, and Variables.
|
||||
declare -Ag HMP_PATH_FSUUID # Used in: 3290() - [Mount Path:Filesystem UUID].
|
||||
# Used in: 4060() - [Mount Path:Filesystem UUID].
|
||||
declare var_dev="" var_part="" \
|
||||
var_encryption_enable="" var_encryption_label="" var_fs_btrfs_checksum="" var_fs_btrfs_compress="" var_fs_btrfs_mdup="" \
|
||||
var_fs_format="" var_fs_label="" var_fs_options="" var_fs_version="" var_mount_path="" var_node="" var_fs_uuid=""
|
||||
|
||||
declare -a ary_devs=() ary_parts=() ary_opts=() ary_fmt_opts=()
|
||||
|
||||
### Iterate over all devices in the recipe.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_devs < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_dev in "${ary_devs[@]}"; do
|
||||
|
||||
### Iterate over all partitions for this device.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_parts < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev} | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_part in "${ary_parts[@]}"; do
|
||||
|
||||
### Extract parameters from YAML.
|
||||
var_encryption_enable=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.enable" "${VAR_SETUP_PART}")
|
||||
var_fs_btrfs_checksum=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.btrfs.checksum" "${VAR_SETUP_PART}")
|
||||
var_fs_btrfs_compress=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.btrfs.compress" "${VAR_SETUP_PART}")
|
||||
var_fs_btrfs_mdup=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.btrfs.mdup" "${VAR_SETUP_PART}")
|
||||
var_fs_format=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.format" "${VAR_SETUP_PART}")
|
||||
var_fs_options=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.options" "${VAR_SETUP_PART}")
|
||||
var_fs_version=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.version" "${VAR_SETUP_PART}")
|
||||
var_mount_path=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.path" "${VAR_SETUP_PART}")
|
||||
|
||||
[[ "${var_fs_format,,}" != "true" ]] && continue
|
||||
|
||||
### Preparation of Ephemeral 'SWAP' and '/tmp' as per https://wiki.archlinux.org/title/Dm-crypt/Swap_encryption#UUID_and_LABEL
|
||||
case "${var_mount_path,,}" in
|
||||
swap|/tmp)
|
||||
do_log "info" "file_only" "3240() Partition: '/dev/${var_dev}${var_part}' ephemeral encryption already prepared in 3220(): '${var_mount_path}'."
|
||||
continue
|
||||
;;
|
||||
esac
|
||||
|
||||
if [[ "${var_encryption_enable,,}" == "true" ]]; then
|
||||
var_encryption_label=$(get_label "${var_mount_path}" "${var_fs_version}" "luks")
|
||||
var_node="/dev/mapper/${var_encryption_label}"
|
||||
else
|
||||
var_node="/dev/${var_dev}${var_part}"
|
||||
fi
|
||||
|
||||
var_fs_label=$(get_label "${var_mount_path}" "${var_fs_version}" "file")
|
||||
|
||||
case "${var_fs_version,,}" in
|
||||
|
||||
btrfs)
|
||||
ary_opts=( -L "${var_fs_label}" -f --csum "${var_fs_btrfs_checksum}" )
|
||||
[[ "${var_fs_btrfs_mdup,,}" == "true" ]] && ary_opts+=( -m dup )
|
||||
|
||||
mkfs.btrfs "${ary_opts[@]}" "${var_node}"
|
||||
|
||||
do_log "debug" "file_only" "3240() [mkfs.btrfs ${ary_opts[*]} ${var_node}]."
|
||||
do_log "info" "file_only" "3240() Partition: '${var_node}' formatted: 'btrfs' options: '${ary_opts[*]}'."
|
||||
|
||||
echo "Partition: '${var_node}':" >> "${DIR_LOG}/btrfs.log"
|
||||
btrfs filesystem show "${var_node}" >> "${DIR_LOG}/btrfs.log"
|
||||
|
||||
var_fs_uuid=$(blkid -s UUID -o value "${var_node}")
|
||||
### Gathering information for '/etc/fstab'-generation in 4040().
|
||||
HMP_PATH_FSUUID["${var_mount_path}"]="${var_fs_uuid}"
|
||||
;;
|
||||
|
||||
ext4)
|
||||
read -r -a ary_fmt_opts <<< "${var_fs_options}"
|
||||
|
||||
mkfs.ext4 -L "${var_fs_label}" "${ary_fmt_opts[@]}" "${var_node}"
|
||||
|
||||
do_log "debug" "file_only" "3240() [mkfs.ext4 -L ${var_fs_label} ${ary_fmt_opts[*]} ${var_node}]."
|
||||
do_log "info" "file_only" "3240() Partition: '${var_node}' formatted: 'ext4' options: '${ary_fmt_opts[*]}'."
|
||||
|
||||
echo "Partition: '${var_node}':" >> "${DIR_LOG}/ext4.log"
|
||||
tune2fs -l "${var_node}" >> "${DIR_LOG}/ext4.log"
|
||||
|
||||
var_fs_uuid=$(blkid -s UUID -o value "${var_node}")
|
||||
### Gathering information for '/etc/fstab'-generation in 4040().
|
||||
HMP_PATH_FSUUID["${var_mount_path}"]="${var_fs_uuid}"
|
||||
;;
|
||||
|
||||
fat32)
|
||||
mkfs.fat -F 32 -n "${var_fs_label}" "${var_node}"
|
||||
|
||||
do_log "debug" "file_only" "3240() [mkfs.fat -F 32 -n ${var_fs_label} ${var_node}]."
|
||||
do_log "info" "file_only" "3240() Partition: '${var_node}' formatted: 'FAT32'."
|
||||
|
||||
var_fs_uuid=$(blkid -s UUID -o value "${var_node}")
|
||||
### Gathering information for '/etc/fstab'-generation in 4040().
|
||||
HMP_PATH_FSUUID["${var_mount_path}"]="${var_fs_uuid}"
|
||||
;;
|
||||
|
||||
*)
|
||||
do_log "error" "file_only" "3240() Unsupported filesystem format: '${var_fs_version}'."
|
||||
;;
|
||||
|
||||
esac
|
||||
|
||||
done
|
||||
|
||||
lsblk -o NAME,MAJ:MIN,FSTYPE,FSVER,SIZE,UUID,MOUNTPOINT,PATH "/dev/${var_dev}" >| "${DIR_LOG}/${var_dev}_overview.log"
|
||||
printf "%b" "${NL}" >> "${DIR_LOG}/${var_dev}_overview.log"
|
||||
lsblk "/dev/${var_dev}" >> "${DIR_LOG}/${var_dev}_overview.log"
|
||||
|
||||
done
|
||||
|
||||
return 0
|
||||
}
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh
|
||||
@@ -1,82 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
guard_sourcing
|
||||
|
||||
#######################################
|
||||
# Function to prepare the filesystem to mount each partition on the respective path.
|
||||
# Globals:
|
||||
# HMP_MOUNTPATH_DEV
|
||||
# VAR_RECIPE_STRING
|
||||
# VAR_SETUP_PART
|
||||
# Arguments:
|
||||
# None
|
||||
# Returns:
|
||||
# 0: on success
|
||||
#######################################
|
||||
setup_filesystem() {
|
||||
### Declare Arrays, HashMaps, and Variables.
|
||||
declare -Ag HMP_MOUNTPATH_DEV # HMP_MOUNTPATH_DEV["${var_mount_path}"]="${var_node}"
|
||||
|
||||
declare var_dev="" var_part="" \
|
||||
var_encryption_enable="" var_encryption_label="" var_fs_version="" var_mount_enable="" var_mount_path="" var_node=""
|
||||
|
||||
declare -a ary_devs ary_parts
|
||||
|
||||
### Iterate over all devices in the recipe.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_devs < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_dev in "${ary_devs[@]}"; do
|
||||
|
||||
### Iterate over all partitions for this device.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_parts < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev} | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_part in "${ary_parts[@]}"; do
|
||||
|
||||
### Extract parameters from YAML.
|
||||
var_encryption_enable=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.enable" "${VAR_SETUP_PART}")
|
||||
var_fs_version=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.version" "${VAR_SETUP_PART}")
|
||||
var_mount_enable=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.enable" "${VAR_SETUP_PART}")
|
||||
var_mount_path=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.path" "${VAR_SETUP_PART}")
|
||||
|
||||
[[ -z "${var_mount_path}" ]] && continue
|
||||
|
||||
[[ "${var_mount_enable,,}" != "true" ]] && continue
|
||||
|
||||
[[ "${var_mount_path,,}" == "swap" || "${var_mount_path,,}" == "/tmp" ]] && continue
|
||||
|
||||
if [[ "${var_encryption_enable}" == "true" ]]; then
|
||||
|
||||
var_encryption_label=$(get_label "${var_mount_path}" "${var_fs_version}" "luks")
|
||||
var_node="/dev/mapper/${var_encryption_label}"
|
||||
|
||||
elif [[ "${var_encryption_enable}" == "false" ]]; then
|
||||
|
||||
var_node="/dev/${var_dev}${var_part}"
|
||||
|
||||
else
|
||||
|
||||
do_log "error" "file_only" "3260() Invalid value for encryption_enable: '${var_encryption_enable}', should be true or false."
|
||||
continue
|
||||
|
||||
fi
|
||||
|
||||
HMP_MOUNTPATH_DEV["${var_mount_path}"]="${var_node}"
|
||||
do_log "info" "file_only" "3260() Saved in HashMap HMP_MOUNTPATH_DEV: '${var_mount_path}' -> '${HMP_MOUNTPATH_DEV["${var_mount_path}"]}'"
|
||||
|
||||
done
|
||||
|
||||
done
|
||||
|
||||
return 0
|
||||
}
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh
|
||||
@@ -1,323 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
guard_sourcing
|
||||
|
||||
#######################################
|
||||
# Validates var_mount_path to be processed.
|
||||
# Arguments:
|
||||
# 1 var_mount_path
|
||||
# Returns:
|
||||
# 0: Skip mounting
|
||||
# 1: Process mount
|
||||
#######################################
|
||||
skip_path() {
|
||||
declare -a ary_skip=( "/" "/boot" "/boot/efi" "/recovery" )
|
||||
declare p=""
|
||||
for p in "${ary_skip[@]}"; do [[ "$1" == "${p}" ]] && return 0; done
|
||||
return 1
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Function to create the mount command, incl. mount path and options, and mount the respective device.
|
||||
# Globals:
|
||||
# ERR_MOUNTING_DEV
|
||||
# TARGET
|
||||
# Arguments:
|
||||
# 1: MOUNT_PATH
|
||||
# 2: MOUNT_DEVICE
|
||||
# 3: MOUNT_OPTIONS
|
||||
# Returns:
|
||||
# 0: on success
|
||||
#######################################
|
||||
mount_with_dir() {
|
||||
declare var_mount_path="$1" var_mount_device="$2" var_mount_options="${3:-}"
|
||||
declare -a ary_cmd=(mount)
|
||||
|
||||
if [[ "${var_mount_device}" =~ ^[0-9a-fA-F-]{8,}$ ]]; then
|
||||
|
||||
if [[ -e "/dev/disk/by-uuid/${var_mount_device}" ]]; then
|
||||
|
||||
var_mount_device="/dev/disk/by-uuid/${var_mount_device}"
|
||||
|
||||
else
|
||||
|
||||
do_log "error" "file_only" "3280() FS-UUID for mount path: '${var_mount_device}' not found by '/dev/disk/by-uuid/${var_mount_device}'."
|
||||
return "${ERR_MOUNTING_DEV}"
|
||||
|
||||
fi
|
||||
|
||||
fi
|
||||
|
||||
[[ "${var_mount_path}" != "/" ]] && mkdir -p "${TARGET}${var_mount_path}"
|
||||
|
||||
### Build the command in an array to keep word boundaries intact.
|
||||
[[ -n "${var_mount_options}" ]] && ary_cmd+=("-o" "${var_mount_options}")
|
||||
ary_cmd+=("${var_mount_device}" "${TARGET}${var_mount_path}")
|
||||
|
||||
safe_exec "${ary_cmd[@]}" "${ERR_MOUNTING_DEV}" || return
|
||||
do_log "debug" "file_only" "3280() [safe_exec ${ary_cmd[*]} ${ERR_MOUNTING_DEV}]."
|
||||
do_log "info" "file_only" "3280() Mounted: '${var_mount_device}' on: '${TARGET}${var_mount_path}' (Options='${var_mount_options}')."
|
||||
|
||||
return 0
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Device Path Resolver.
|
||||
# Outputs '/dev/mapper/<encryption_label>'
|
||||
# Outputs '/dev/<dev><partition>'
|
||||
# Arguments:
|
||||
# 1: Device
|
||||
# 2: Partition
|
||||
# 3: Boolean Encryption
|
||||
# 4: Encryption Label
|
||||
#######################################
|
||||
resolve_device() {
|
||||
declare local_var_dev="$1" local_var_partition="$2" local_var_enc_boolean="$3" local_var_enc_label="$4"
|
||||
if [[ "${local_var_enc_boolean,,}" == "true" ]]; then
|
||||
printf '/dev/mapper/%s' "${local_var_enc_label}"
|
||||
else
|
||||
printf '/dev/%s%s' "${local_var_dev}" "${local_var_partition}"
|
||||
fi
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Validates btrfs compression algo and level.
|
||||
# Arguments:
|
||||
# 1 var_fs_btrfs_compress
|
||||
# 2 var_fs_btrfs_level
|
||||
# Returns:
|
||||
# 0: Valid combination.
|
||||
# 1: Invalid combination.
|
||||
#######################################
|
||||
validate_btrfs_compression() {
|
||||
declare var_algo="$1" var_level="$2"
|
||||
case "${var_algo}:${var_level}" in
|
||||
zstd:|zstd:[0-9]|zstd:1[0-9]|zstd:2[0-2]|lzo:) return 0 ;;
|
||||
*) do_log "error" "file_only" "3280() Invalid btrfs compression: '${var_algo}:${var_level}'"; return "${ERR_BTRFS_OPTION}" ;;
|
||||
esac
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Function for mounting all partitions for debootstrap, including the generation of btrfs subvolumes.
|
||||
# Globals:
|
||||
# HMP_MOUNTPATH_DEV
|
||||
# TARGET
|
||||
# VAR_RECIPE_STRING
|
||||
# VAR_SAFE_MNT_BASE
|
||||
# VAR_SETUP_PART
|
||||
# Arguments:
|
||||
# None
|
||||
# Returns:
|
||||
# 0: on success
|
||||
# ERR_BTRFS_INITPH
|
||||
# ERR_BTRFS_OPTION
|
||||
# ERR_BTRFS_SUBVOL
|
||||
# ERR_MOUNTING_DEV
|
||||
# ERR_MOUNTING_ROOT
|
||||
#######################################
|
||||
mount_partition() {
|
||||
### Declare Arrays, HashMaps, and Variables.
|
||||
declare -Ag HMP_FSTAB_MOUNT_OPTS # Used in: 4040() - [Mount Path:Mount Options].
|
||||
declare -r var_mount_path_root="/"
|
||||
|
||||
declare var_path="" var_dev="" var_part="" \
|
||||
var_fs_btrfs_compress="" var_fs_btrfs_level="" var_fs_btrfs_subvolume="" var_fs_btrfs_snapshot="" \
|
||||
var_encryption_enable="" var_encryption_label="" var_fs_options="" var_fs_version="" var_mount_path="" \
|
||||
var_mount_options="" var_snapshot="" var_mount_optsnap="" var_fs_uuid=""
|
||||
|
||||
declare -a ary_devs=() ary_parts=()
|
||||
|
||||
### Mount "/"-filesystem
|
||||
if [[ -n "${HMP_PATH_FSUUID["${var_mount_path_root}"]}" ]]; then
|
||||
mount_with_dir "${var_mount_path_root}" "${HMP_PATH_FSUUID["${var_mount_path_root}"]}" || return "${ERR_MOUNTING_DEV}"
|
||||
else
|
||||
do_log "error" "file_only" "3280() Root-filesystem '${var_mount_path_root}' not found in Hashmap: 'HMP_PATH_FSUUID'."
|
||||
return "${ERR_MOUNTING_ROOT}"
|
||||
fi
|
||||
|
||||
#if [[ -n "${HMP_MOUNTPATH_DEV[${var_mount_path_root}]}" ]]; then
|
||||
# mount_with_dir "${var_mount_path_root}" "${HMP_MOUNTPATH_DEV[${var_mount_path_root}]}" || return "${ERR_MOUNTING_DEV}"
|
||||
#else
|
||||
# do_log "error" "file_only" "3280() Root-filesystem '${var_mount_path_root}' not found in Hashmap: 'HMP_MOUNTPATH_DEV'."
|
||||
# return "${ERR_MOUNTING_ROOT}"
|
||||
#fi
|
||||
|
||||
### Ensure order of "/boot" and "/boot/efi"
|
||||
for var_path in "/boot" "/boot/efi"; do
|
||||
if [[ -n "${HMP_PATH_FSUUID["${var_path}"]}" ]]; then
|
||||
mount_with_dir "${var_path}" "${HMP_PATH_FSUUID["${var_path}"]}" || return "${ERR_MOUNTING_DEV}"
|
||||
else
|
||||
do_log "info" "file_only" "3280() Entry '${var_path}' not found in Hashmap: 'HMP_PATH_FSUUID'."
|
||||
fi
|
||||
done
|
||||
|
||||
#for var_path in "/boot" "/boot/efi"; do
|
||||
# if [[ -n "${HMP_MOUNTPATH_DEV[${var_path}]}" ]]; then
|
||||
# mount_with_dir "${var_path}" "${HMP_MOUNTPATH_DEV[${var_path}]}" || return "${ERR_MOUNTING_DEV}"
|
||||
# else
|
||||
# do_log "info" "file_only" "3280() Entry '${var_path}' not found in Hashmap: 'HMP_MOUNTPATH_DEV'."
|
||||
# fi
|
||||
#done
|
||||
|
||||
### Iterate over all devices in the recipe.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_devs < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_dev in "${ary_devs[@]}"; do
|
||||
|
||||
### Iterate over all partitions for this device.
|
||||
# shellcheck disable=SC2312
|
||||
readarray -t ary_parts < <(yq e -r ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev} | keys | .[]" "${VAR_SETUP_PART}")
|
||||
for var_part in "${ary_parts[@]}"; do
|
||||
|
||||
### Extract parameters from YAML.
|
||||
var_fs_btrfs_compress=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.btrfs.compress" "${VAR_SETUP_PART}")
|
||||
var_fs_btrfs_level=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.btrfs.level" "${VAR_SETUP_PART}")
|
||||
var_fs_btrfs_snapshot=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.btrfs.snapshot" "${VAR_SETUP_PART}")
|
||||
var_encryption_enable=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.encryption.enable" "${VAR_SETUP_PART}")
|
||||
var_fs_options=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.options" "${VAR_SETUP_PART}")
|
||||
var_fs_version=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.filesystem.version" "${VAR_SETUP_PART}")
|
||||
var_mount_path=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.path" "${VAR_SETUP_PART}")
|
||||
var_mount_options=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.options" "${VAR_SETUP_PART}")
|
||||
var_mount_optsnap=$(yq_val ".recipe.${VAR_RECIPE_STRING}.dev.${var_dev}.${var_part}.mount.optsnap" "${VAR_SETUP_PART}")
|
||||
|
||||
### Skip already mounted paths ("/", "/boot", "/boot/efi") and skip ("/recovery")
|
||||
skip_path "${var_mount_path}" && continue
|
||||
|
||||
var_encryption_label=$(get_label "${var_mount_path}" "${var_fs_version}" "luks")
|
||||
var_fs_uuid="${HMP_PATH_FSUUID["${var_path}"]}"
|
||||
|
||||
if [[ "${var_mount_path,,}" == "swap" ]]; then
|
||||
|
||||
#var_fs_label=$(get_label "${var_mount_path}" "${var_fs_version}" "file")
|
||||
|
||||
cryptsetup open --type plain --key-file /dev/random \
|
||||
--offset 2048 --cipher aes-xts-plain64 --key-size 512 \
|
||||
--sector-size 4096 "/dev/disk/by-uuid/${var_fs_uuid}" "${var_encryption_label}"
|
||||
#--sector-size 4096 "/dev/disk/by-label/${var_fs_label}" "${var_encryption_label}"
|
||||
|
||||
mkswap "/dev/mapper/${var_encryption_label}"
|
||||
do_log "debug" "file_only" "3280() [mkswap /dev/mapper/${var_encryption_label}]."
|
||||
|
||||
swapon "/dev/mapper/${var_encryption_label}"
|
||||
do_log "debug" "file_only" "3280() [swapon /dev/mapper/${var_encryption_label}]."
|
||||
do_log "info" "file_only" "3280() Mounted: '${var_mount_path}' on: '/dev/mapper/${var_encryption_label}'."
|
||||
|
||||
continue
|
||||
|
||||
elif [[ "${var_mount_path,,}" == "/tmp" ]]; then
|
||||
|
||||
cryptsetup open --type plain --key-file /dev/random \
|
||||
--offset 2048 --cipher aes-xts-plain64 --key-size 512 \
|
||||
--sector-size 4096 "/dev/disk/by-uuid/${var_fs_uuid}" "${var_encryption_label}"
|
||||
|
||||
mkdir -p "${TARGET}/tmp"
|
||||
|
||||
echo "safe_exec mkfs.ext4 -E nodiscard,lazy_itable_init=1,lazy_journal_init=1 /dev/mapper/${var_encryption_label} ${ERR_MOUNTING_DEV}"
|
||||
safe_exec mkfs.ext4 -E nodiscard,lazy_itable_init=1,lazy_journal_init=1 "/dev/mapper/${var_encryption_label}" "${ERR_MOUNTING_DEV}" || return "${ERR_MOUNTING_DEV}"
|
||||
|
||||
### Build the command in an array to keep word boundaries intact
|
||||
declare -a ary_cmd2=(mount)
|
||||
|
||||
ary_cmd2+=("/dev/mapper/${var_encryption_label}" "${TARGET}${var_mount_path}")
|
||||
|
||||
safe_exec "${ary_cmd2[@]}" "${ERR_MOUNTING_DEV}" || return "${ERR_MOUNTING_DEV}"
|
||||
do_log "info" "file_only" "3280() Mounted: '${var_mount_path}' on: '/dev/mapper/${var_encryption_label}'."
|
||||
|
||||
continue
|
||||
|
||||
fi
|
||||
|
||||
#var_resolved_dev=$(resolve_device "${var_dev}" "${var_part}" "${var_encryption_enable}" "${var_encryption_label}")
|
||||
|
||||
if [[ "${var_fs_version,,}" == "btrfs" ]]; then
|
||||
|
||||
var_fs_btrfs_subvolume=$(get_label "${var_mount_path}" "${var_fs_version}" "sub")
|
||||
|
||||
### Mount toplevel (subvolid=0) without extra options.
|
||||
declare -a ary_cmd_mount=(mount -o "subvolid=0" "${var_fs_uuid}" "${VAR_SAFE_MNT_BASE}")
|
||||
safe_exec "${ary_cmd_mount[@]}" "${ERR_BTRFS_INITPH}" || return "${ERR_BTRFS_INITPH}"
|
||||
|
||||
btrfs subvolume create "${VAR_SAFE_MNT_BASE}/${var_fs_btrfs_subvolume}"
|
||||
do_log "debug" "file_only" "3280() [btrfs subvolume create ${VAR_SAFE_MNT_BASE}/${var_fs_btrfs_subvolume}]."
|
||||
do_log "info" "file_only" "3280() btrfs subvolid=0 created: '${var_mount_path}' on: '/dev/mapper/${var_encryption_label}'."
|
||||
|
||||
if [[ "${var_fs_btrfs_snapshot}" == "true" ]]; then
|
||||
|
||||
var_snapshot=$(get_label "${var_mount_path}" "${var_fs_version}" "snap")
|
||||
|
||||
btrfs subvolume create "${VAR_SAFE_MNT_BASE}/${var_snapshot}" || return "${ERR_BTRFS_SUBVOL}"
|
||||
do_log "debug" "file_only" "3280() [btrfs subvolume create ${VAR_SAFE_MNT_BASE}/${var_snapshot}]."
|
||||
do_log "info" "file_only" "3280() btrfs subvolid=${var_snapshot} created: '${var_mount_path}' on: '/dev/mapper/${var_encryption_label}'."
|
||||
fi
|
||||
|
||||
umount "${VAR_SAFE_MNT_BASE}"
|
||||
do_log "info" "file_only" "3280() btrfs subvolume umount: '${var_mount_path}' on: '/dev/mapper/${var_encryption_label}'."
|
||||
|
||||
fi
|
||||
|
||||
case "${var_fs_version,,}:${var_encryption_enable,,}" in
|
||||
|
||||
btrfs:*)
|
||||
|
||||
validate_btrfs_compression "${var_fs_btrfs_compress}" "${var_fs_btrfs_level}" || return "${ERR_BTRFS_OPTION}"
|
||||
|
||||
declare var_btrfs_compression_options="compress=${var_fs_btrfs_compress}:${var_fs_btrfs_level}"
|
||||
|
||||
[[ -n "${var_mount_options}" ]] && var_btrfs_compression_options+=",${var_mount_options},subvol=${var_fs_btrfs_subvolume}"
|
||||
|
||||
### Gathering information for '/etc/fstab'-generation in 4040().
|
||||
HMP_FSTAB_MOUNT_OPTS["${var_mount_path}"]="${var_btrfs_compression_options[*]}"
|
||||
do_log "debug" "file_only" "3280() Stored in HashMap [HMP_FSTAB_MOUNT_OPTS] : '${var_mount_path}' -> '${HMP_FSTAB_MOUNT_OPTS["${var_mount_path}"]}'."
|
||||
|
||||
mount_with_dir "${var_mount_path}" "${var_fs_uuid}" "${var_btrfs_compression_options}" || return "${ERR_MOUNTING_DEV}"
|
||||
|
||||
if [[ "${var_fs_btrfs_snapshot}" == "true" ]]; then
|
||||
|
||||
### Preparing "/.snapshot"-directory
|
||||
mkdir -p "${TARGET}${var_mount_path}/.snapshots"
|
||||
do_log "info" "file_only" "3280() Created: '${TARGET}${var_mount_path}/.snapshots'."
|
||||
|
||||
var_mount_optsnap="${var_mount_optsnap},subvol=${var_snapshot}"
|
||||
|
||||
### Gathering information for '/etc/fstab'-generation in 4040().
|
||||
HMP_FSTAB_MOUNT_OPTS["${var_mount_path}/.snapshots"]="${var_mount_optsnap[*]}"
|
||||
do_log "debug" "file_only" "3280() Stored in HashMap [HMP_FSTAB_MOUNT_OPTS] : '${var_mount_path}/.snapshots' -> '${HMP_FSTAB_MOUNT_OPTS["${var_mount_path}/.snapshots"]}'."
|
||||
|
||||
mount_with_dir "${var_mount_path}/.snapshots" "${var_fs_uuid}" "${var_mount_optsnap}"
|
||||
|
||||
do_log "info" "file_only" "3280() Mounted: '${var_fs_uuid}' on: '${TARGET}${var_mount_path}/.snapshots' (Options='${var_mount_optsnap}')."
|
||||
|
||||
fi
|
||||
;;
|
||||
|
||||
ext4:*)
|
||||
|
||||
mount_with_dir "${var_mount_path}" "${var_fs_uuid}" "${var_mount_options}" || return "${ERR_MOUNTING_DEV}"
|
||||
;;
|
||||
|
||||
*) do_log "error" "file_only" "3280() Unsupported fs/encryption combination."
|
||||
return "${ERR_MOUNTING_DEV}" ;;
|
||||
|
||||
esac
|
||||
|
||||
done
|
||||
|
||||
lsblk -o NAME,MAJ:MIN,FSTYPE,FSVER,SIZE,UUID,MOUNTPOINT,PATH "/dev/${var_dev}" >| "${DIR_LOG}/${var_dev}_overview_full.log"
|
||||
printf "%b" "${NL}" >> "${DIR_LOG}/${var_dev}_overview_full.log"
|
||||
lsblk "/dev/${var_dev}" >> "${DIR_LOG}/${var_dev}_overview_full.log"
|
||||
|
||||
done
|
||||
|
||||
return 0
|
||||
}
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh
|
||||
@@ -1,24 +0,0 @@
|
||||
#!/bin/bash
|
||||
do_log "info" "file_only" "Live environment DHCP information collection: timeout='${network_timeout_dhcp}' seconds. Please wait."
|
||||
|
||||
dhclient -v -1 "${var_auto_nic}" 2>&1 | timeout "${network_timeout_dhcp}" dhcpdump -i "${var_auto_nic}" >> "${LOG_NIC}" || true
|
||||
awk 'BEGIN {RS="---------------------------------------------------------------------------"; \
|
||||
ORS="---------------------------------------------------------------------------"} \
|
||||
NF {last=$0} END {print last}' "${LOG_NIC}" > "${LOG_NIC}".tmp && mv "${LOG_NIC}".tmp "${LOG_NIC}"
|
||||
|
||||
do_log "info" "file_only" "Live environment DHCP information collection: collection completed."
|
||||
|
||||
### Extract 'FQDN' from '${LOG_NIC}'
|
||||
var_auto_fqdn=$(awk -F 'Host name' '/Host name/ {print $2}' "${LOG_NIC}" | xargs)
|
||||
|
||||
### Extract 'YIADDR' (Your IP Address) from '${LOG_NIC}'
|
||||
var_dhcp_yiaddr=$(awk -F 'YIADDR:' '/YIADDR/ {print $2}' "${LOG_NIC}" | awk '{print $1}' | xargs)
|
||||
|
||||
### Extract 'SIADDR' (Server IP Address) from '${LOG_NIC}'
|
||||
var_dhcp_siaddr=$(awk -F 'SIADDR:' '/SIADDR/ {print $2}' "${LOG_NIC}" | awk '{print $1}' | xargs)
|
||||
|
||||
### Extract 'Server Identifier' from '${LOG_NIC}'
|
||||
var_dhcp_srv=$(awk -F 'Server identifier' '/Server identifier/ {print $2}' "${LOG_NIC}" | xargs)
|
||||
|
||||
### Extract 'GIADDR' (Gateway IP Address) from '${LOG_NIC}'
|
||||
var_dhcp_giaddr=$(awk -F 'GIADDR:' '/GIADDR/ {print $2}' "${LOG_NIC}" | awk '{print $1}' | xargs)
|
||||
@@ -1,37 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
|
||||
### Remarks
|
||||
# lsinitramfs /boot/initrd.img-"$(uname -r)" | grep -E 'bin/(bash|sha|reboot|sync|sleep|sh)'
|
||||
# readelf -h /bin/busybox | grep Type
|
||||
# command="/usr/local/bin/unlock_wrapper.sh",no-agent-forwarding,no-port-forwarding,no-X11-forwarding ssh-ed25519 ...
|
||||
# /usr/share/initramfs-tools/scripts/init-premount
|
||||
# /dev/sdaN: UUID="468ad656-0e2f-4fff-9501-c691bab9f553" TYPE="crypto_LUKS" PARTLABEL="crypt_system" PARTUUID="78c0f711-f84f-425e-9455-a46430f40794"
|
||||
# GRUB_CMDLINE_LINUX="cryptdevice=UUID=468ad656-0e2f-4fff-9501-c691bab9f553:cryptroot root=/dev/mapper/vg_system-root"
|
||||
# declare var_nic_module; var_nic_module=$(lspci -k | grep -A2 -i ethernet | grep 'Kernel driver in use' | awk '{print $5}')
|
||||
# echo "${var_nic_module}"
|
||||
|
||||
### Nuke Hints
|
||||
# /usr/share/cryptsetup/initramfs/bin/cryptroot-unlock
|
||||
# Before (Default)
|
||||
# ASKPASS=/lib/cryptsetup/askpass
|
||||
# After
|
||||
# ASKPASS=/lib/cryptsetup/askpass.cryptsetup
|
||||
|
||||
# apt-get cryptsetup-nuke-password
|
||||
# dpkg-reconfigure cryptsetup-nuke-password
|
||||
|
||||
#debconf-set-selections << END
|
||||
#cryptsetup-nuke-password cryptsetup-nuke-password/password string Th3Pa$$w0rd
|
||||
#cryptsetup-nuke-password cryptsetup-nuke-password/password-again string Th3Pa$$w0rd
|
||||
#END
|
||||
#sudo dpkg-reconfigure -f noninteractive cryptsetup-nuke-password
|
||||
@@ -1,56 +0,0 @@
|
||||
#!/bin/bash
|
||||
#######################################
|
||||
# Detects and collects all boot devices for GRUB installation.
|
||||
# Supports /dev/sdX, /dev/vdX, /dev/hdX, /dev/nvmeXn1, /dev/mmcblkX.
|
||||
# Globals:
|
||||
# VAR_RECIPE_HIGHEST_DEVICE
|
||||
# ary_bootdev_all
|
||||
# grub_bootdev
|
||||
# Arguments:
|
||||
# None
|
||||
# Returns:
|
||||
# 0: on success
|
||||
#######################################
|
||||
get_all_boot_devs() {
|
||||
### Declare Arrays, HashMaps, and Variables.
|
||||
declare -ag ary_bootdev_all=()
|
||||
declare dev="" dev_prefix="" dev_path="" letter=""
|
||||
declare -i ascii=0 ascii_end=0 ascii_start=0
|
||||
|
||||
### Determine prefix from grub_bootdev (e.g., "sd", "vd", "nvme", "mmcblk")
|
||||
dev_prefix=$(basename "${grub_bootdev}" | sed -E 's/^([a-z]+)[a-z0-9]*$/\1/')
|
||||
|
||||
case "${dev_prefix}" in
|
||||
|
||||
sd|vd|hd)
|
||||
ascii_start=$(printf '%d' "'a")
|
||||
ascii_end=$(printf '%d' "'${VAR_RECIPE_HIGHEST_DEVICE}")
|
||||
for ((ascii = ascii_start; ascii <= ascii_end; ascii++)); do
|
||||
letter=$(printf "%b" "\\$(printf '%03o' "${ascii}")")
|
||||
dev_path="/dev/${dev_prefix}${letter}"
|
||||
[[ -b "${dev_path}" ]] && ary_bootdev_all+=("${dev_path}")
|
||||
done
|
||||
;;
|
||||
|
||||
nvme)
|
||||
# shellcheck disable=SC2312
|
||||
while read -r dev; do
|
||||
ary_bootdev_all+=("/dev/${dev}")
|
||||
done < <(lsblk -dn -o NAME | grep -E '^nvme[0-9]+n1$')
|
||||
;;
|
||||
|
||||
mmcblk)
|
||||
# shellcheck disable=SC2312
|
||||
while read -r dev; do
|
||||
ary_bootdev_all+=("/dev/${dev}")
|
||||
done < <(lsblk -dn -o NAME | grep -E '^mmcblk[0-9]+$')
|
||||
;;
|
||||
|
||||
*)
|
||||
do_log "warning" "file_only" "4230() Unrecognized boot device prefix: ${dev_prefix}"
|
||||
;;
|
||||
|
||||
esac
|
||||
|
||||
return 0
|
||||
}
|
||||
@@ -1,376 +0,0 @@
|
||||
#!/bin/bash
|
||||
# SPDX-Version: 3.0
|
||||
# SPDX-CreationInfo: 2025-06-17; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-ExternalRef: GIT https://git.coresecret.dev/msw/CISS.debian.installer.git
|
||||
# SPDX-FileContributor: WEIDNER, Marc S.; Centurion Intelligence Consulting Agency
|
||||
# SPDX-FileCopyrightText: 2024-2025; WEIDNER, Marc S.; <msw@coresecret.dev>
|
||||
# SPDX-FileType: SOURCE
|
||||
# SPDX-License-Identifier: EUPL-1.2 OR LicenseRef-CCLA-1.0
|
||||
# SPDX-LicenseComment: This file is part of the CISS.debian.installer.secure framework.
|
||||
# SPDX-PackageName: CISS.debian.installer
|
||||
# SPDX-Security-Contact: security@coresecret.eu
|
||||
# SPDX-Comment: unlock_wrapper.sh to be executed after dropbear SSH login as forced command
|
||||
|
||||
set -Ceuo pipefail
|
||||
IFS=$(printf ' \n\t')
|
||||
|
||||
# shellcheck disable=SC2155
|
||||
declare -gr CURRENTDATE=$(date +"%F %T")
|
||||
declare -gir MAX_RETRIES=2
|
||||
|
||||
#######################################
|
||||
# Generates informative shell prompt.
|
||||
# Globals:
|
||||
# PS1
|
||||
# Arguments:
|
||||
# None
|
||||
#######################################
|
||||
prompt_string() {
|
||||
declare -gx PS1="\
|
||||
\[\033[1;91m\]\d\[\033[0m\]|\[\033[1;91m\]\u\[\033[0m\]@\
|
||||
\[\033[1;95m\]\h\[\033[0m\]:\
|
||||
\[\033[1;96m\]\w\[\033[0m\]/>>\
|
||||
\$(if [[ \$? -eq 0 ]]; then \
|
||||
# Show exit status in green if zero
|
||||
echo -e \"\[\033[1;92m\]\$?\[\033[0m\]\"; \
|
||||
else \
|
||||
# Show exit status in red otherwise
|
||||
echo -e \"\[\033[1;91m\]\$?\[\033[0m\]\"; \
|
||||
fi)\
|
||||
|~\$ "
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Trap function to be called on 'ERR'.
|
||||
# Arguments:
|
||||
# $1: ${?}
|
||||
# $2: ${BASH_SOURCE[0]}
|
||||
# $3: ${LINENO}
|
||||
# $4: ${FUNCNAME[0]:-main}
|
||||
# $5: ${BASH_COMMAND}
|
||||
#######################################
|
||||
trap_on_err() {
|
||||
declare -r errcode="$1"
|
||||
declare -r errscrt="$2"
|
||||
declare -r errline="$3"
|
||||
declare -r errfunc="$4"
|
||||
declare -r errcmmd="$5"
|
||||
trap - ERR
|
||||
stty echo
|
||||
if [[ ${errcode} -eq 0 ]]; then
|
||||
print_scr_scc
|
||||
prompt_string
|
||||
exit 0
|
||||
else
|
||||
print_scr_err "${errcode}" "${errscrt}" "${errline}" "${errfunc}" "${errcmmd}"
|
||||
sleep 15
|
||||
sync
|
||||
set +C
|
||||
echo 1 > /proc/sys/kernel/sysrq
|
||||
echo o > /proc/sysrq-trigger
|
||||
fi
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Security Trap on 'INT' and 'TERM' to provide a deterministic way to not circumvent the Nuke Routine
|
||||
# Globals:
|
||||
# DEVICES_LUKS
|
||||
# DEVICES_NUKE
|
||||
# Arguments:
|
||||
# None
|
||||
#######################################
|
||||
trap_on_term() {
|
||||
trap - INT
|
||||
stty echo
|
||||
printf "\n"
|
||||
printf "\e[0;91m✘ System caught a 'SIGINT'. System Power Off in 3 seconds. \e[0m\n" >&2
|
||||
sync
|
||||
sleep 3
|
||||
set +C
|
||||
echo 1 > /proc/sys/kernel/sysrq
|
||||
echo o > /proc/sysrq-trigger
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Print Error Message for 'non-0' Trap on 'EXIT' on Terminal.
|
||||
# Arguments:
|
||||
# $1: ${?}
|
||||
# $2: ${BASH_SOURCE[0]}
|
||||
# $3: ${LINENO}
|
||||
# $4: ${FUNCNAME[0]:-main}
|
||||
# $5: ${BASH_COMMAND}
|
||||
#######################################
|
||||
print_scr_err() {
|
||||
declare -r scr_err_errcode="$1"
|
||||
declare -r scr_err_errscrt="$2"
|
||||
declare -r scr_err_errline="$3"
|
||||
declare -r scr_err_errfunc="$4"
|
||||
declare -r scr_err_errcmmd="$5"
|
||||
printf "\n"
|
||||
printf "\e[0;91m✘ System caught an 'ERROR'. System Power Off in 15 seconds. \e[0m\n" >&2
|
||||
printf "\n"
|
||||
printf "\e[0;91m✘ Error : %s \e[0m\n" "${scr_err_errcode}" >&2
|
||||
printf "\e[0;91m✘ Line : %s \e[0m\n" "${scr_err_errline}" >&2
|
||||
printf "\e[0;91m✘ Script : %s \e[0m\n" "${scr_err_errscrt}" >&2
|
||||
printf "\e[0;91m✘ Function : %s \e[0m\n" "${scr_err_errfunc}" >&2
|
||||
printf "\e[0;91m✘ Command : %s \e[0m\n" "${scr_err_errcmmd}" >&2
|
||||
printf "\n"
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Print Error Message for '0' Trap on 'ERR' on Terminal.
|
||||
# Arguments:
|
||||
# none
|
||||
#######################################
|
||||
print_scr_scc() {
|
||||
printf "\e[0;92m✅ Script exited successfully. Proceeding with booting. \e[0m\n"
|
||||
printf "\n"
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Gather information of all LUKS Devices available on the system
|
||||
# Arguments:
|
||||
# None
|
||||
#######################################
|
||||
gather_luks_devices() {
|
||||
declare prev=() curr=() dev="" tries=0
|
||||
|
||||
while ((tries < 10)); do
|
||||
mapfile -t curr < <(blkid -t TYPE=crypto_LUKS -o device)
|
||||
|
||||
if [[ ${curr[*]} == "${prev[*]}" ]]; then
|
||||
break
|
||||
fi
|
||||
|
||||
prev=("${curr[@]}")
|
||||
tries=$((tries + 1))
|
||||
sleep 1
|
||||
done
|
||||
|
||||
### Print one device per line for mapfile compatibility
|
||||
for dev in "${curr[@]}"; do
|
||||
printf '%s\n' "${dev}"
|
||||
done
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Gather information of all NUKE Devices available on the system
|
||||
# Globals:
|
||||
# DEVICES_LUKS
|
||||
# Arguments:
|
||||
# None
|
||||
#######################################
|
||||
gather_nuke_devices() {
|
||||
### 'DEVICES_LUKS' must already be a bash array of device paths
|
||||
declare dev=""
|
||||
declare result=()
|
||||
|
||||
for dev in "${DEVICES_LUKS[@]}"; do
|
||||
### Check slot 31 for 'luks2'
|
||||
if cryptsetup luksDump "${dev}" 2> /dev/null | grep -qE '^[[:space:]]*31: luks2'; then
|
||||
result+=("${dev}")
|
||||
fi
|
||||
done
|
||||
|
||||
### Print one device per line for mapfile compatibility
|
||||
for dev in "${result[@]}"; do
|
||||
printf '%s\n' "${dev}"
|
||||
done
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Read passphrase interactively.
|
||||
# Arguments:
|
||||
# None
|
||||
#######################################
|
||||
passphrase_ask() {
|
||||
declare -g PASSPHRASE=""
|
||||
printf "\n"
|
||||
stty -echo
|
||||
printf "\e[0;95m🔐 Enter passphrase for decryption: \e[0m\n"
|
||||
read -r PASSPHRASE
|
||||
stty echo
|
||||
printf "\n"
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Test the entered passphrase against the dedicated Nuke Keyslot #31.
|
||||
# Arguments:
|
||||
# $1: DEVICE
|
||||
# $2: PASSWD
|
||||
#######################################
|
||||
passphrase_test() {
|
||||
declare -r DEVICE="$1"
|
||||
declare -r PASPHR="$2"
|
||||
printf '%s' "${PASPHR}" | cryptsetup open --batch-mode --test-passphrase --key-slot 31 "${DEVICE}" > /dev/null 2>&1
|
||||
}
|
||||
|
||||
#######################################
|
||||
# Check the integrity and authenticity of this script itself.
|
||||
# Arguments:
|
||||
# $0: Script Name
|
||||
#######################################
|
||||
verify_coresecret() {
|
||||
### Directory of this script
|
||||
# shellcheck disable=SC2155
|
||||
declare dir="$(dirname "$(readlink -f "${0}")")"
|
||||
# shellcheck disable=SC2155
|
||||
declare script="$(basename "${0}")"
|
||||
declare algo
|
||||
|
||||
for algo in sha512 sha384; do
|
||||
# shellcheck disable=SC2155
|
||||
declare hashfile="${dir}/${script}.${algo}"
|
||||
# shellcheck disable=SC2155
|
||||
declare sigfile="${hashfile}.sig"
|
||||
# shellcheck disable=SC2155
|
||||
declare cmd="${algo}sum"
|
||||
|
||||
printf "\e[0;95m🔏 Verifying signature of: [%s] \e[0m\n" "${hashfile}"
|
||||
gpgv --keyring /etc/keys/pubring.gpg "${sigfile}" "${hashfile}" || {
|
||||
printf "\e[0;91m✘ Signature verification failed for: [%s] \e[0m\n" "${hashfile}" >&2
|
||||
printf "\e[0;91m✘ System Power Off in 3 seconds. \e[0m\n" >&2
|
||||
sync
|
||||
sleep 3
|
||||
set +C
|
||||
echo 1 > /proc/sys/kernel/sysrq
|
||||
echo o > /proc/sysrq-trigger
|
||||
}
|
||||
printf "\e[0;92m🔏 Verifying signature of: [%s] successful. \e[0m\n" "${hashfile}"
|
||||
|
||||
printf "\e[0;95m🔢 Recomputing Hash: [%s] \e[0m\n" "${algo}"
|
||||
# shellcheck disable=SC2155
|
||||
declare computed=$($cmd "${dir}/${script}" | awk '{print $1}')
|
||||
# shellcheck disable=SC2155
|
||||
declare expected=$(cat "${hashfile}")
|
||||
|
||||
if [[ ${computed} != "${expected}" ]]; then
|
||||
printf "\e[0;91m✘ Hash mismatch for: [%s] \e[0m\n" "${algo}" >&2
|
||||
printf "\e[0;91m✘ System Power Off in 3 seconds. \e[0m\n" >&2
|
||||
sync
|
||||
sleep 3
|
||||
set +C
|
||||
echo 1 > /proc/sys/kernel/sysrq
|
||||
echo o > /proc/sysrq-trigger
|
||||
fi
|
||||
printf "\e[0;92m🔢 Recomputing Hash: [%s] successful. \e[0m\n" "${algo}"
|
||||
done
|
||||
|
||||
printf "\e[0;92m🔏 All signatures and hashes verified successfully. Proceeding. \e[0m\n"
|
||||
}
|
||||
|
||||
### Main Programm
|
||||
trap 'trap_on_err "$?" "${BASH_SOURCE[0]}" "${LINENO}" "${FUNCNAME[0]:-main}" "${BASH_COMMAND}"' ERR
|
||||
trap 'trap_on_term' INT TERM
|
||||
|
||||
printf "\e[0;91mCoresecret Connection established.\e[0m\n"
|
||||
printf "\e[0;91mStarting Time: %s\e[0m\n" "${CURRENTDATE}"
|
||||
printf "\n"
|
||||
|
||||
verify_coresecret
|
||||
|
||||
### Read newline-separated output into an array
|
||||
mapfile -t DEVICES_LUKS < <(gather_luks_devices)
|
||||
mapfile -t DEVICES_NUKE < <(gather_nuke_devices)
|
||||
|
||||
### Debug output: list each element with its index
|
||||
#for idx in "${!DEVICES_LUKS[@]}"; do
|
||||
# printf 'Luks[%d]: %s\n' "${idx}" "${DEVICES_LUKS[${idx}]}"
|
||||
#done
|
||||
|
||||
### Debug output: list each element with its index
|
||||
#for idx in "${!DEVICES_NUKE[@]}"; do
|
||||
# printf 'Nuke[%d]: %s\n' "${idx}" "${DEVICES_NUKE[${idx}]}"
|
||||
#done
|
||||
|
||||
### # If there are no LUKS devices at all, drop to bash
|
||||
[[ -n ${DEVICES_LUKS[*]} ]] || {
|
||||
printf "\e[0;92m✘ No LUKS Devices found. Dropping to bash ... \e[0m\n"
|
||||
prompt_string
|
||||
exec /bin/bash -i
|
||||
}
|
||||
|
||||
### If there are LUKS devices but no Nuke devices, try unlocking flow
|
||||
if [[ -n ${DEVICES_LUKS[*]} ]] && [[ -z ${DEVICES_NUKE[*]} ]]; then
|
||||
### Attempt interactive unlock with cryptroot-unlock
|
||||
if cryptroot-unlock; then
|
||||
|
||||
exit 0
|
||||
|
||||
else
|
||||
|
||||
printf "\n"
|
||||
printf "\e[0;91m✘ Unsuccessful command 'cryptroot-unlock'. \e[0m\n"
|
||||
printf "\e[0;92m✘ No LUKS operations performed. Dropping to bash ... \e[0m\n"
|
||||
printf "\e[0;92m✘ To unlock 'root' partition, and maybe others like 'swap', run 'cryptroot-unlock'. \e[0m\n"
|
||||
prompt_string
|
||||
exec /bin/bash -i
|
||||
|
||||
fi
|
||||
|
||||
elif [[ -n ${DEVICES_LUKS[*]} ]] && [[ -n ${DEVICES_NUKE[*]} ]]; then
|
||||
|
||||
declare -i attempt=1
|
||||
declare NUKED=false
|
||||
declare TEST_DEV="${DEVICES_NUKE[0]}"
|
||||
|
||||
while ((attempt <= MAX_RETRIES)); do
|
||||
|
||||
printf "\e[0;95m🔐Attempt %s/%s: \e[0m\n" "${attempt}" "${MAX_RETRIES}"
|
||||
|
||||
passphrase_ask
|
||||
declare -g PASSWD="${PASSPHRASE}"
|
||||
|
||||
if passphrase_test "${TEST_DEV}" "${PASSWD}"; then
|
||||
|
||||
for dev in "${DEVICES_NUKE[@]}"; do
|
||||
cryptsetup erase --batch-mode "${dev}" > /dev/null 2>&1
|
||||
printf "%s:\e[0;95m✘ LUKS Device Header malfunction. \e[0m\n" "${dev}"
|
||||
done
|
||||
|
||||
declare -r NUKED=true
|
||||
unset PASSWD
|
||||
break
|
||||
|
||||
else
|
||||
|
||||
declare code="$?"
|
||||
|
||||
case "${code}" in
|
||||
1) printf "\e[0;91m✘ No usable key slot is available. \e[0m\n" ;;
|
||||
2) printf "\e[0;91m✘ No key available with this passphrase. \e[0m\n" ;;
|
||||
3) printf "\e[0;93m✘ Out of memory. \e[0m\n" ;;
|
||||
*) printf "\e[0;91m✘ Unexpected Return Code. \e[0m\n" ;;
|
||||
esac
|
||||
|
||||
fi
|
||||
|
||||
attempt=$((attempt + 1))
|
||||
|
||||
done
|
||||
|
||||
if [[ ${NUKED} == true ]]; then
|
||||
stty echo
|
||||
sleep 3
|
||||
sync
|
||||
set +C
|
||||
echo 1 > /proc/sys/kernel/sysrq
|
||||
echo o > /proc/sysrq-trigger
|
||||
fi
|
||||
|
||||
if cryptroot-unlock; then
|
||||
|
||||
exit 0
|
||||
|
||||
else
|
||||
|
||||
printf "\e[0;91m✘ Unsuccessful command 'cryptroot-unlock'. \e[0m\n"
|
||||
printf "\e[0;92m✘ No LUKS operations performed. Dropping to bash ... \e[0m\n"
|
||||
printf "\e[0;92m✘ To unlock 'root' partition, and maybe others like 'swap', run 'cryptroot-unlock'. \e[0m\n"
|
||||
prompt_string
|
||||
exec /bin/bash -i
|
||||
|
||||
fi
|
||||
|
||||
fi
|
||||
# vim: number et ts=2 sw=2 sts=2 ai tw=128 ft=sh
|
||||
Reference in New Issue
Block a user