void-installer/install_void.sh

350 lines
13 KiB
Bash
Executable File

#!/bin/env bash
#############################################################################
# ██╗ ██╗ ██████╗ ██╗██████╗ ██╗███╗ ██╗███████╗████████╗ █████╗ ██╗ ██╗ ███████╗██████╗
# ██║ ██║██╔═══██╗██║██╔══██╗ ██║████╗ ██║██╔════╝╚══██╔══╝██╔══██╗██║ ██║ ██╔════╝██╔══██╗
# ██║ ██║██║ ██║██║██║ ██║ ██║██╔██╗ ██║███████╗ ██║ ███████║██║ ██║ █████╗ ██████╔╝
# ╚██╗ ██╔╝██║ ██║██║██║ ██║ ██║██║╚██╗██║╚════██║ ██║ ██╔══██║██║ ██║ ██╔══╝ ██╔══██╗
# ╚████╔╝ ╚██████╔╝██║██████╔╝ ██║██║ ╚████║███████║ ██║ ██║ ██║███████╗███████╗███████╗██║ ██║
# ╚═══╝ ╚═════╝ ╚═╝╚═════╝ ╚═╝╚═╝ ╚═══╝╚══════╝ ╚═╝ ╚═╝ ╚═╝╚══════╝╚══════╝╚══════╝╚═╝ ╚═╝
#############################################################################
# Autor:Alex Ham
# Email:kandil@disroot.org
# Description:This script install OS GNU/Linux VoidLinux on USB or HDD drives
# Dependencies:xz, curl
#############################################################################
# [-]=waiting
# [+]=successful
# [!]=warning
# [*]=info
# [?]=aksing
#############################################################################
# Colors
cl_black=$'\e[30m'
cl_red=$'\e[31m'
cl_green=$'\e[32m'
cl_yellow=$'\e[33m'
cl_blue=$'\e[34m'
cl_magenta=$'\e[35m'
cl_cyan=$'\e[36m'
cl_white=$'\e[37m'
cl_bright=$'\e[1m'
cl_normal=$'\e[0m'
#############################################################################
# ENV
luks_name="lukspc"
lvm_group_name="lvmpc"
fs_type="ext4"
sys_lang="LANG=en_US.UTF-8"
sys_locale="en_US.UTF-8 UTF-8"
sys_hostname="voidpc"
sys_pkg_list="list.pkg"
void_repo="https://repo-default.voidlinux.org/current"
user_groups="wheel,floppy,cdrom,optical,audio,video,kvm,plugdev"
grub_discards="rd.luks.allow-discards"
run_dev=$(lsblk -slnpo NAME $(df --output=source / | sed 1d) | tail -n1)
#############################################################################
# Start
clear
printf "%s######################%s\n" "${cl_blue}" "${cl_normal}"
printf "%s# Install Void Linux #%s\n" "${cl_blue}" "${cl_normal}"
printf "%s######################%s\n" "${cl_blue}" "${cl_normal}"
printf "%s================================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] Selecting disk (DEVICE:SIZE)%s\n" "${cl_green}" "${cl_normal}"
printf "%s================================%s\n" "${cl_green}" "${cl_normal}"
# Check if script runing by root
if [ "$(id -u)" != "0" ]; then
printf "[!] You are not super user!\n"
exit 1
fi
# Check dependencies
compgen -c | grep -qE "^xz$"
if [ "$?" == "0" ]; then
tar xf void.tar.xz -C /mnt
rm -f void.tar.xz >/dev/null
else
printf "Pleace install utilite xz"
exit 1
fi
# Prompt user to select disk for installation
select line in $(lsblk -dnpo NAME,SIZE | sed 's/ \+/:/g' | grep -v ${run_dev}); do
if [ -z "${line}" ]; then
printf "[!] Wrong partition\n"
exit 1
fi
PS3="[?] Select disk for installation: "
printf "[+] Selected disk: <%s>\n" ${line}
inst_dev=$(echo ${line} | cut -d':' -f1)
inst_dev_size=$(echo ${line} | cut -d':' -f2)
break
done
# Promt for script continuation
read -rp "[?] Are you shure to install on device ${inst_dev}? (y/n) " _key
if [ "${_key}" != "y" ]; then
printf "%s[!] Aborted!%s\n" "${cl_red}" "${cl_normal}"
exit 1
fi
# Check if installed device is mounted
for _dev in $(lsblk -pnlo NAME ${inst_dev}); do
if grep -q "${_dev}" /proc/mounts; then
printf "%s[!] Device <%s> is mounted%s\n" \
"${cl_red}" "${_dev}" "${cl_normal}"
exit 1
fi
done
# Unmount all filesystem in /mnt folder
if grep -q " /mnt " /proc/mounts; then
if ! umount -qR /mnt; then
printf "%s[!] Exiting%s\n" "${cl_red}" "${cl_normal}"
exit 1
fi
fi
# Check if LVM is active
_dev=$(lsblk -plno NAME,FSTYPE ${inst_dev} | grep "LVM" | awk '{print$1}')
if [ ! -z "${_dev}" ]; then
if lvscan --devices "${_dev}" | grep -q ACTIVE; then
_vg=$(pvs | grep "${_dev}" | awk '{print$2}')
vgchange -an ${_vg}
fi
fi
# Check if LUKS is open
_name=$(lsblk -lno NAME,FSTYPE ${inst_dev} | grep -A1 LUKS | sed 1d | awk '{print$1}')
if [ ! -z "${_name}" ]; then
if cryptsetup status "${_name}" | grep -q "is active"; then
cryptsetup close "${_name}"
fi
fi
# Wipe all data from disk
sfdisk --delete ${inst_dev} >/dev/null && \
printf "[+] Wipe disk %s\n" "${inst_dev}"
# Preparing device
printf "label: dos\n, , L, *\n" | sfdisk -q ${inst_dev} &&
printf "[+] Create disklabel type <DOS> and partition for LUKS\n"
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] Users and passwords%s\n" "${cl_green}" "${cl_normal}"
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
# Grab informations about users and passwords
read -rsp "[?] Password for user <root>: " root_pass
printf "\n"
read -rp "[?] Name for home user?: " user_name
read -rp "[?] Please enter your real full name? " user_full_name
read -rsp "[?] Password for home user <${user_name}>: " user_pass
printf "\n"
printf "%s========================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] Encrypting partition%s\n" "${cl_green}" "${cl_normal}"
printf "%s========================%s\n" "${cl_green}" "${cl_normal}"
# Create password to system
read -rsp "[?] Password for encrypting device: " luks_pass
printf "\n"
printf "[-] Encrypted partition, wait... "
# Create LUKS encrypted partition
inst_dev_part=$(lsblk -pnlo NAME ${inst_dev} | sed 1d)
if echo ${luks_pass} | cryptsetup -q --type luks1 luksFormat ${inst_dev_part}
then
printf "OK!\n"
else
printf "%s\n[!] ERROR!!%s\n" "${cl_red}" "${cl_normal}"
exit 1
fi
# Open encrypted partition
if echo ${luks_pass} | cryptsetup open ${inst_dev_part} ${luks_name}; then
printf "[+] Open encrypted partition to </dev/mapper/%s>\n" ${luks_name}
else
printf "%s\n[!] ERROR!!%s\n" "${cl_red}" "${cl_normal}"
exit 1
fi
printf "%s=================================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] Creating LVM and file systems%s\n" "${cl_green}" "${cl_normal}"
printf "%s=================================%s\n" "${cl_green}" "${cl_normal}"
# Creating a Physical Volume in LVM
if pvcreate /dev/mapper/"${luks_name}" >/dev/null; then
printf "[+] PV </dev/mapper/%s> successfully created\n" "${luks_name}"
else
printf "%s[!] Error creating PV </dev/mapper/%s>\n" \
"${luks_name}%s" "${cl_red}" "${cl_normal}"
exit 1
fi
# Creating a Volume Group in LVM
if vgcreate "${lvm_group_name}" /dev/mapper/"${luks_name}" >/dev/null; then
printf "[+] VG <%s> successfully created\n" "${lvm_group_name}"
else
printf "%s[!] Error creating VG <%s>\n" \
"${lvm_group_name}%s" "${cl_red}" "${cl_normal}"
exit 1
fi
# Size for partitions
printf "[+] Max size of LV partition: <%s>\n" "${inst_dev_size}"
read -rp "[?] Size{G,T,P} for LV-root (empty - all space): " lvm_root_size
if [ -n "${lvm_root_size}" ]; then
# Check if size is correct
echo "${lvm_root_size}" | grep -qE "^[0-9]+(\.[0-9])?[GTP]$"
if [ "$?" == "1" ]; then
printf "%s[!] Not correct size%s\n" "${cl_red}" "${cl_normal}"
exit 1
fi
# Creating FS for LVs [ROOT]
lvcreate --name root -L ${lvm_root_size} ${lvm_group_name} >/dev/null &&
printf "[+] Logical volume <root> created\n"
printf "[-] Creating FS for LV root, wait... "
mkfs.${fs_type} -qL root /dev/${lvm_group_name}/root && printf "OK!\n"
# Creating FS for LVs [HOME]
lvcreate --name home -l 100%FREE ${lvm_group_name} >/dev/null &&
printf "[+] Logical volume <home> created\n"
printf "[-] Creating FS for LV home, wait... "
mkfs.${fs_type} -qL home /dev/${lvm_group_name}/home && printf "OK!\n"
else
# Creating FS for LVs only root
lvcreate --name root -l 100%FREE ${lvm_group_name} >/dev/null &&
printf "[+] Logical volume <root> created\n"
printf "[-] Creating FS for LV root, wait... "
mkfs.${fs_type} -qL root /dev/${lvm_group_name}/root && printf "OK!\n"
fi
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] Mounting FileSystem%s\n" "${cl_green}" "${cl_normal}"
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
if [ -n "${lvm_root_size}" ]; then
# Mount root and home dirrectory
mount /dev/"${lvm_group_name}"/root /mnt
mkdir /mnt/home
mount /dev/"${lvm_group_name}"/home /mnt/home
else
# Mount root dirrectory
mount /dev/"${lvm_group_name}"/root /mnt
fi
# Mount xchroot
for _fs in dev proc sys; do
mkdir /mnt/${_fs}
mount --rbind "/${_fs}" "/mnt/${_fs}"
mount --make-rslave "/mnt/${_fs}"
printf "[+] Mount /%s to /mnt/%s\n" "${_fs}" "${_fs}"
done
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] System installation%s\n" "${cl_green}" "${cl_normal}"
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
# Cloning and unpacking packages
printf "[-] Downloading rootfs, wait... "
curl -s https://repo-default.voidlinux.org/live/current/void-x86_64-ROOTFS-20230628.tar.xz \
-o void.tar.xz
# Update DNS
printf "[+] Update /etc/resolv.conf"
cp /etc/resolv.conf /mnt/etc/ >/dev/null
printf "OK!\n"
printf "%s##########%s\n" "${cl_blue}" "${cl_normal}"
printf "%s# Chroot #%s\n" "${cl_blue}" "${cl_normal}"
printf "%s##########%s\n" "${cl_blue}" "${cl_normal}"
# # Date setting
# read -rp "[?] Enter the real date in the format: “YYYY-MM-DD HH:MM”? " _date
# echo "${_date}" | grep -qE \
# "^20[2-9][0-9]-[0-1][0-9]-[0-3][0-9] [0-2][0-9]:[0-5][0-9]$"
# if [ "$?" == "1" ]; then
# printf "%s[!] Not correct date!!!%s\n" "${cl_red}" "${cl_normal}"
# exit 1
# fi
# chroot /mnt date -s "${_date}"
# Installing xbps packages
printf "[-] Installing package xbps, wait... "
chroot /mnt xbps-install -Suy xbps >/dev/null
printf "OK!\n"
printf "[-] Updating system, wait... "
chroot /mnt xbps-install -uy >/dev/null
printf "OK!\n"
printf "[-] Installing base-system packages, wait... "
chroot /mnt xbps-install -y base-system lvm2 cryptsetup grub >/dev/null
printf "OK!\n"
printf "[-] Removing package base-voidstrap, wait... "
chroot /mnt xbps-remove -y base-voidstrap >/dev/null
printf "OK!\n"
# finish up the configuration
printf "[-] Configuration, wait... "
chroot /mnt chown root:root /
chroot /mnt chmod 755 /
printf "%s\n%s" "${root_pass}" "${root_pass}" \
| chroot /mnt passwd root >/dev/null
echo ${sys_hostname} > /mnt/etc/hostname
# For glibc systems
echo ${sys_lang} > /mnt/etc/locale.conf
echo ${sys_locale} >> /mnt/etc/default/libc-locales
chroot /mnt xbps-reconfigure -f glibc-locales >/dev/null
# Modify file /etc/fstab in chroot
grep "/dev/mapper/${lvm_group_name}" /proc/mounts | awk \
'$2 == "/mnt" { $2 = "/" } $2 == "/mnt/home" { $2 = "/home" } 1' \
>> /mnt/etc/fstab
# Grub configuration
_uuid=$(blkid -o value -s UUID ${inst_dev_part})
_param="rd.auto=1 rd.lvm.vg=${lvm_group_name} rd.luks.uuid=${_uuid} ${grub_discards}"
echo "GRUB_ENABLE_CRYPTODISK=y" >> /mnt/etc/default/grub
sed -i "s/\(GRUB_CMDLINE_LINUX_DEFAULT=\"\)/\1${_param} /" \
/mnt/etc/default/grub >/dev/null
# LUKS key setup
dd bs=1 count=64 if=/dev/urandom of=/mnt/root/volume.key status=none
echo ${luks_pass} | cryptsetup luksAddKey \
${inst_dev_part} /mnt/root/volume.key
chmod 000 /mnt/root/volume.key
chmod -R g-rwx,o-rwx /mnt/root/volume.key
printf "OK!\n"
# Configure for dracut
printf "%s\tUUID=%s\t/root/volume.key\tluks" "${luks_name}" "${_uuid}" >> \
/mnt/etc/crypttab
printf "install_items+=\" /root/volume.key /etc/crypttab \"" > \
/mnt/etc/dracut.conf.d/10-crypt.conf
# Complete system installation
printf "[-] Grub instalation, wait... "
chroot /mnt grub-install ${inst_dev} >/dev/null
chroot /mnt xbps-reconfigure -r /mnt -fa >/dev/null
printf "OK!\n"
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
printf "%s[*] Additional commands%s\n" "${cl_green}" "${cl_normal}"
printf "%s=======================%s\n" "${cl_green}" "${cl_normal}"
printf "%s#######################%s\n" "${cl_blue}" "${cl_normal}"
printf "%s# Finish install Void #%s\n" "${cl_blue}" "${cl_normal}"
printf "%s#######################%s\n" "${cl_blue}" "${cl_normal}"
read -rp "[?] Unmount newly created Void installation? (y/n) " _key
if [[ "${_key}" == "y" ]]; then
umount -R /mnt # Unmount root volume
vgchange -an ${lvm_name} # Deactivate volume group
cryptsetup close ${luks_name} # Close LUKS encrypted partition
fi