#!/usr/bin/env bash cat > /tmp/lfs_sudo << EOF # 3.1. Introduction # 4.3. Adding the LFS User lfs ALL = NOPASSWD: /usr/bin/chown * /mnt/lfs* # 7.3. Preparing Virtual Kernel File Systems lfs ALL = NOPASSWD: /usr/bin/mount * /mnt/lfs* lfs ALL = NOPASSWD: /usr/bin/install * /mnt/lfs* lfs ALL = NOPASSWD: /usr/sbin/chroot /mnt/lfs* EOF add_lfs_user() { echo "4.3. Adding the LFS User" echo "# groupadd lfs" echo "# useradd -s /bin/bash -g lfs -m -k /dev/null lfs" echo "# passwd lfs" echo "And add sudo rights" echo "# cp /tmp/lfs_sudo /etc/sudoers.d/lfs" echo "Now connect as lfs and execute the script" echo "$ su - lfs" echo "$ cd " echo "$ bash build.sh" } if [ "$(whoami)" != "lfs" ] then echo "Please execute this script as user lfs" grep -q lfs /etc/passwd || add_lfs_user exit 1 fi set -ueEo pipefail export LFS=/mnt/lfs # shellcheck source=/dev/null if [ ! -e /home/lfs/.lfsbuild_config ] then cat /home/lfs/.lfsbuild_config << EOSF # location of local package sources LFS_PACKAGE_DIR=/home/lfs/packages # Number of processors to use LFS_NPROC=$(nproc) # Bypass step by step validation until a breakpoint LFS_BREAKPOINT=1 # strip binaries or not LFS_STRIP_BINARIES=true # bypass network config validation by taking network config from host LFS_NETWORKSAMEASHOST=false # bypass network configuration for full offline build LFS_NETWORKOFFLINE=false # bypass linux config validation by taking linux config from host LFS_LINUXCONFIGPROVIDED=false EOSF fi # shellcheck source=/dev/null source /home/lfs/.lfsbuild_config SCRIPT_DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)" LFS_PACKAGE_DIR=${LFS_PACKAGE_DIR:-/home/lfs/packages} LFS_NPROC=${LFS_NPROC:-$(nproc)} LFS_BREAKPOINT=${LFS_BREAKPOINT:-1} LFS_STRIP_BINARIES=${LFS_STRIP_BINARIES:-false} LFS_NETWORK=${LFS_NETWORKSAMEASHOST:-false} LFS_OFFLINE=${LFS_NETWORKOFFLINE:-false} LFS_LINUXCONFIG=${LFS_LINUXCONFIGPROVIDED:-false} ask_for_exit() { echo "----- call ask_for_exit $1" echo "find ${SCRIPT_DIR}/build/ \( -name \"*.sh\" -or -name \"*.txt\" \) -print |sort |grep --context=1 \$(cat ${HLFSB})" find "${SCRIPT_DIR}/build/" \( -name "*.sh" -or -name "*.txt" \) -print |sort |grep --context=1 "$(cat "${HLFSB}")" echo "ask_for_exit : args = $* && $1 < ${LFS_BREAKPOINT} (LFS_BREAKPOINT) || $1 < $(cat "${HLFSB}") (HLFSB) || ${LFS_BREAKPOINT} (LFS_BREAKPOINT) > $(cat "${HLFSB}") (HLFSB) " if [[ $# -eq 1 ]] && [[ $1 -ge 10000 ]] && [[ $1 -lt 10000000 ]] && [[ $1 -lt ${LFS_BREAKPOINT} ]] then echo "LFS_BREAKPOINT : validation disabled" return 0 elif [[ $# -eq 1 ]] && [[ $1 -ge 10000 ]] && [[ $1 -lt 10000000 ]] && [[ $1 -lt $(cat "${HLFSB}") ]] then echo "STEP_COUNTER : already done. validation disabled" return 0 elif [[ $# -eq 1 ]] && [[ $1 -ge 10000 ]] && [[ $1 -lt 10000000 ]] && [[ ${LFS_BREAKPOINT} -gt $(cat "${HLFSB}") ]] then echo "LFS_BREAKPOINT : validation forced" return 0 else USER_ANSWER="?"; while [ "${USER_ANSWER}" != "n" ] && [ "${USER_ANSWER}" != "y" ] ; do echo -n "Continue ? [y/n]" read -r -n 1 USER_ANSWER echo ""; done if [ "$USER_ANSWER" == "n" ] then exit 0 fi fi } ask_for_execution() { USER_ANSWER="?"; while [ "${USER_ANSWER}" != "n" ] && [ "${USER_ANSWER}" != "y" ] && [ "${USER_ANSWER}" != "q" ] do echo -n "Execute ? [y/n/q]" read -r -n 1 USER_ANSWER echo ""; done if [ "$USER_ANSWER" == "y" ] then return 0 elif [ "$USER_ANSWER" == "n" ] then return 1 elif [ "$USER_ANSWER" == "q" ] then exit 0 else exit 0 fi } # 2.2 cat > /tmp/lfs_version-check.sh << "EOF" #!/bin/bash # A script to list version numbers of critical development tools # If you have tools installed in other directories, adjust PATH here AND # in ~lfs/.bashrc (section 4.4) as well. LC_ALL=C PATH=/usr/bin:/bin bail() { echo "FATAL: $1"; exit 1; } grep --version > /dev/null 2> /dev/null || bail "grep does not work" sed '' /dev/null || bail "sed does not work" sort /dev/null || bail "sort does not work" ver_check() { if ! type -p $2 &>/dev/null then echo "ERROR: Cannot find $2 ($1)"; return 1; fi v=$($2 --version 2>&1 | grep -E -o '[0-9]+\.[0-9\.]+[a-z]*' | head -n1) if printf '%s\n' $3 $v | sort --version-sort --check &>/dev/null then printf "OK: %-9s %-6s >= $3\n" "$1" "$v"; return 0; else printf "ERROR: %-9s is TOO OLD ($3 or later required)\n" "$1"; return 1; fi } ver_kernel() { kver=$(uname -r | grep -E -o '^[0-9\.]+') if printf '%s\n' $1 $kver | sort --version-sort --check &>/dev/null then printf "OK: Linux Kernel $kver >= $1\n"; return 0; else printf "ERROR: Linux Kernel ($kver) is TOO OLD ($1 or later required)\n" "$kver"; return 1; fi } version_check() { # Coreutils first because --version-sort needs Coreutils >= 7.0 ver_check Coreutils sort 8.1 || bail "Coreutils too old, stop" ver_check Bash bash 3.2 ver_check Binutils ld 2.13.1 ver_check Bison bison 2.7 ver_check Diffutils diff 2.8.1 ver_check Findutils find 4.2.31 ver_check Gawk gawk 4.0.1 ver_check GCC gcc 5.4 ver_check "GCC (C++)" g++ 5.4 ver_check Grep grep 2.5.1a ver_check Gzip gzip 1.3.12 ver_check M4 m4 1.4.10 ver_check Make make 4.0 ver_check Patch patch 2.5.4 ver_check Perl perl 5.8.8 ver_check Python python3 3.4 ver_check Sed sed 4.1.5 ver_check Tar tar 1.22 ver_check Texinfo texi2any 5.0 ver_check Xz xz 5.0.0 ver_kernel 5.4 if mount | grep -q 'devpts on /dev/pts' && [ -e /dev/ptmx ] then echo "OK: Linux Kernel supports UNIX 98 PTY"; else echo "ERROR: Linux Kernel does NOT support UNIX 98 PTY"; fi alias_check() { if $1 --version 2>&1 | grep -qi $2 then printf "OK: %-4s is $2\n" "$1"; else printf "ERROR: %-4s is NOT $2\n" "$1"; fi } echo "Aliases:" alias_check awk GNU alias_check yacc Bison alias_check sh Bash echo "Compiler check:" if printf "int main(){}" | g++ -x c++ -o /tmp/lfs_a.out - then echo "OK: g++ works"; else echo "ERROR: g++ does NOT work"; fi rm -f /tmp/lfs_a.out if [ "$(nproc)" = "" ]; then echo "ERROR: nproc is not available or it produces empty output" else echo "OK: nproc reports $(nproc) logical cores are available" fi } EOF # shellcheck source=/dev/null source /tmp/lfs_version-check.sh # 2.6. Setting the $LFS Variable and the Umask # 4.4. Setting Up the Environment cat > ~/.bashrc << EOF set +h umask 022 export LFS=/mnt/lfs export PATH=/usr/bin if [ ! -L /bin ]; then PATH=/bin:$PATH; fi export PATH=/mnt/lfs/tools/bin:$PATH:/usr/sbin export CONFIG_SITE=$LFS/usr/share/config.site export MAKEFLAGS=-j${LFS_NPROC} export ARCH=$(uname -m) export LC_ALL=POSIX export LFS_VERSION=13.0 export LFS_CODENAME=lfs # change this to whatever you want export LFS_KERNEL_VERSION=6.18.10 export LFS_TGT=$(uname -m)-lfs-linux-gnu export LFS_ZONEINFO=$(realpath --relative-to=/usr/share/zoneinfo /etc/localtime) export LFS_HOSTNAME=${LFS_HOSTNAME:-lfs} # change this to whatever you want export SOURCES=$LFS/sources export HLFSB=/home/lfs/lfs_build export SLFSB=/mnt/lfs/sources/lfs_build export RLFSB=/sources/lfs_build export STEMP=/mnt/lfs/tmp EOF # shellcheck source=/dev/null source ~/.bashrc # cat > ~/.bash_profile << "EOF" # exec env -i HOME=$HOME TERM=$TERM PS1='\u:\w\$ ' /bin/bash # EOF ## shellcheck source=/dev/null # source ~/.bash_profile cat > "${HOME}"/lfs_chroot.sh < "${SLFSB}" ask_for_exit "${step}" done return 0 } building_temporary_tools() { echo "call building_temporary_tools $1" if [[ $# -ne 1 ]] then echo "bad argument in function call" return 1 fi section=$1 for package in $(find "${SOURCES}" -name "[${section}][0-9][0-9][0-9][0-9]_*.sh" -print | sort) do scriptname=$(basename "${package}") step=${scriptname%%_*} echo "Test if $(cat "${SLFSB}") -ge ${step}" if [[ $(cat "${SLFSB}") -ge ${step} ]] then echo "${scriptname} already done" continue fi unnumbered=${scriptname##*_} packagename=${unnumbered%.*} echo "pkgname: ${packagename}" if find "${SOURCES}" -name "${packagename}*.tar.*" -print then archivepath=$(find "${SOURCES}" -name "${packagename}*.tar.*" -print) echo "archpath: ${archivepath}" archivesubpath=${archivepath##/mnt/lfs} echo "archivesubpath: ${archivesubpath}" archivename=$(basename "${archivepath}") echo "archname: ${archivename}" buildpath=/sources/"${packagename}" else echo "There is no archive with this name !!!" exit 1 fi sudofile=/tmp/lfs_${step}.sh cat > "${sudofile}" << EOSF if [ -d "${buildpath}" ] then rm -r "${buildpath}" mkdir -p "${buildpath}" else mkdir -p "${buildpath}" fi if [ ! -e "${buildpath}"/COPYING ] then tar -xf "${archivesubpath}" -C "${buildpath}" --strip-components=1 fi pushd "${buildpath}" set -ueExo pipefail eval "\$(cat ../"${scriptname}")" | tee "/tmp/lfs_${step}.log" popd rm -rf "${buildpath}" set -ueEo pipefail EOSF if ! lfs_chroot "${sudofile}" then echo "compilation error" exit 1 else echo "compilation ok" fi check_errors "${STEMP}/lfs_${step}.log" echo "${step}" > "${SLFSB}" cp -v "${STEMP}/lfs_${step}.log" "${HOME}" ask_for_exit "${step}" done } check_virtual_kernel_filesystems() { echo "call check_virtual_kernel_filesystems" if mount |grep -q "udev on /mnt/lfs/dev type devtmpfs" && \ mount |grep -q "devpts on /mnt/lfs/dev/pts type devpts" && \ mount |grep -q "proc on /mnt/lfs/proc type proc" && \ mount |grep -q "sysfs on /mnt/lfs/sys type sysfs" && \ mount |grep -q "tmpfs on /mnt/lfs/run type tmpfs" && \ mount |grep -q "tmpfs on /mnt/lfs/dev/shm type tmpfs" then echo "Ok, Filesystems are ready for chroot" return 0 else echo "7.3. Preparing Virtual Kernel File Systems" echo "Warning : Not ready for chroot !!!" return 1 fi } mount_virtual_kernel_filesystem() { echo "call mount_virtual_kernel_filesystem" echo "sudo operation : mount dev sys proc sys run /dev/shm" echo /usr/bin/mount -v --bind /dev $LFS/dev || return 1 sudo /usr/bin/mount -v --bind /dev $LFS/dev || return 1 echo /usr/bin/mount -vt devpts devpts -o gid=5,mode=0620 $LFS/dev/pts || return 1 sudo /usr/bin/mount -vt devpts devpts -o gid=5,mode=0620 $LFS/dev/pts || return 1 echo /usr/bin/mount -vt proc proc $LFS/proc || return 1 sudo /usr/bin/mount -vt proc proc $LFS/proc || return 1 echo /usr/bin/mount -vt sysfs sysfs $LFS/sys || return 1 sudo /usr/bin/mount -vt sysfs sysfs $LFS/sys || return 1 echo /usr/bin/mount -vt tmpfs tmpfs $LFS/run || return 1 sudo /usr/bin/mount -vt tmpfs tmpfs $LFS/run || return 1 echo "Content of $LFS/dev :" ls -l $LFS/dev/ echo "Content of $LFS/dev/shm :" ls -l $LFS/dev/shm if [ -h $LFS/dev/shm ] then echo /usr/bin/install -v -d -m 1777 $LFS"$(realpath /dev/shm)" || return 1 sudo /usr/bin/install -v -d -m 1777 $LFS"$(realpath /dev/shm)" || return 1 else echo /usr/bin/mount -vt tmpfs -o nosuid,nodev tmpfs $LFS/dev/shm || return 1 sudo /usr/bin/mount -vt tmpfs -o nosuid,nodev tmpfs $LFS/dev/shm || return 1 fi return 0 } lfs_chroot() { echo "call lfs_chroot $1" CHROOTFILE=$1 sed "1iif [[ ! \"\${UID\}\" -eq 0 ]] && [ ! -e ${CHROOTFILE} ] && [ -e /sources/lfs_build ]" -i "${CHROOTFILE}" sed "2ithen" -i "${CHROOTFILE}" sed "3iecho \"bad chroot\"" -i "${CHROOTFILE}" sed "4iexit 1" -i "${CHROOTFILE}" sed "5ielse" -i "${CHROOTFILE}" sed "\$afi" -i "${CHROOTFILE}" if cat "${CHROOTFILE}" | sudo /usr/sbin/chroot "$LFS" /usr/bin/env -i \ HOME=/root \ TERM="$TERM" \ PS1='(lfs chroot) \u:\w\$ ' \ PATH=/usr/bin:/usr/sbin \ MAKEFLAGS="-j1" \ TESTSUITEFLAGS="-j1" \ /bin/bash then echo "command succeed" return 0 else return 1 fi } main() { cd "$SCRIPT_DIR" if [ ! -d "$LFS/sources" ] then rm --force --verbose "${HLFSB}" echo "10000" > "${HLFSB}" fi ### CHECK LOCAL HOST ### echo "2.2 Host System Requirements" if [[ $(cat "${HLFSB}") -lt 22000 ]] then set +e version_check | tee /tmp/lfs_version_check.log echo "=== Check for errors ===" grep ERROR /tmp/lfs_version_check.log && exit 1 if [ -e /etc/bash.bashrc ] then echo "Please disable /etc/bash.bashrc for compilation" echo "# mv -v /etc/bash.bashrc /etc/bash.bashrc.NOUSE" exit 1 fi echo "22000" > "${HLFSB}" fi echo "2.7. Mounting the New Partition" if ! mount |grep -q "/mnt/lfs type ext4" then echo "2.4. Creating a New Partition" echo "2.5. Creating a File System on the Partition" echo "2.7. Mounting the New Partition" echo "You have to mount a ext4 partition under /mnt/lfs" echo "Think to create a swap partition on the target device" exit 1 fi if [ "${LFS}" != "/mnt/lfs" ] then echo "2.6. Setting the \$LFS Variable and the Umask" echo "LFS is not /mnt/lfs" exit 1 fi ask_for_exit 27000 ### DOWNLOAD PACKAGES ### echo "3.2. All Packages" if [[ $(cat "${HLFSB}") -lt 31000 ]] then if ! check_sources then echo "3.1. Introduction" echo "3.2. All Packages" echo "Some package are missing" if ! download then echo "3.1. Introduction" echo "Some package are unavailable" echo "Try manually" exit 1 fi else echo "31000" > "${HLFSB}" fi fi if [[ $(cat "${HLFSB}") -lt 32000 ]] then if ! check_sources then echo "3.1. Introduction" echo "Some package are unavailable" echo "Fix it manually" exit 1 else echo "32000" > "${HLFSB}" fi fi ask_for_exit 42000 ### PREPARE LFS DIRECTORIES ### echo "4.2. Creating a Limited Directory Layout in the LFS Filesystem" if [[ $(cat "${HLFSB}") -lt 42000 ]] && [ ! -e "${SLFSB}" ] then if [ ! -d "$LFS/tools" ] then echo "Time to create some directories on $LFS" if create_directories then echo "42000" > "${HLFSB}" else echo "4.2. Creating a Limited Directory Layout in the LFS Filesystem" echo "III. Building the LFS Cross Toolchain and Temporary Tools" echo "Failed to create directories on $LFS" echo "The user lfs has not sufficient rights" echo "If not, you can fix it manually" echo "Or the file /tmp/lfs_sudo may be copied under /etc/sudoers.d/lfs" echo "And execute the following command as root to valide syntax" echo "# visudo /etc/sudoers.d/lfs" exit 1 fi else echo "42000" > "${HLFSB}" fi fi echo "4.7. Copy sources" if [[ $(cat "${HLFSB}") -lt 47000 ]] then if ! copy_sources then echo "3.1. Introduction" echo "Copy packages to sources failed" exit 1 else echo "47000" > "${HLFSB}" fi fi ask_for_exit 48000 echo "4.8. Copy scripts" if [[ $(cat "${HLFSB}") -lt 48000 ]] then if ! copy_scripts then echo "5. Compiling a Cross-Toolchain" echo "Copy scripts to sources failed" exit 1 else if [[ ! $(du /mnt/lfs/sources/ |cut -f 1) -gt 500000 ]] then echo "check /mnt/lfs/sources content failed" exit 1 fi echo "48000" > "${HLFSB}" fi fi ######################################### ### Begin to follow steps on target ##### ######################################### if [ ! -e "${SLFSB}" ] then echo "Initialize lfs_build on /mnt/lfs" echo "48000" > "${SLFSB}" rm --force --verbose "${HLFSB}" ln --symbolic --force --verbose "${SLFSB}" "${HLFSB}" fi ask_for_exit 50000 ### CROSS TOOLCHAIN ### echo "5. Compiling a Cross-Toolchain" if [[ $(cat "${SLFSB}") -lt 52500 ]] then echo "Chapter 5. Compiling a Cross-Toolchain" if cross_toolchain 5 then echo "52500" > "${SLFSB}" else echo "Cross Toolchain Failure" exit 1 fi fi if [[ $(cat "${SLFSB}") -gt 50000 ]] && [[ $(cat "${SLFSB}") -lt 71310 ]] then case $(uname -m) in x86_64) if [ ! -e /mnt/lfs/tools/x86_64-lfs-linux-gnu/bin/ld ] || \ [ ! -e /mnt/lfs/tools/bin/x86_64-lfs-linux-gnu-gcc ] || \ [ ! -e /mnt/lfs/usr/include/asm/fcntl.h ] || \ [ ! -e /mnt/lfs/usr/sbin/ldconfig ] || \ [ ! -e /mnt/lfs/usr/lib/libstdc++.so.6.0.34 ] then echo "Some binaries are missing from cross_toolchain 5xxxx" exit 1 fi ;; i686) if [ ! -e /mnt/lfs/tools/bin/i686-lfs-linux-gnu-ld ] || \ [ ! -e /mnt/lfs/tools/bin/i686-lfs-linux-gnu-gcc ] || \ [ ! -e /mnt/lfs/usr/include/asm/fcntl.h ] || \ [ ! -e /mnt/lfs/usr/sbin/ldconfig ] || \ [ ! -e /mnt/lfs/usr/lib/libstdc++.so.6.0.34 ] then echo "Some binaries are missing from cross_toolchain 5xxxx" exit 1 fi ;; *) echo "Architecture $(uname -m) is not supported" ;; esac fi ask_for_exit 60000 ### CROSS TOOLCHAIN ### echo "6. Cross Compiling Temporary Tools" if [[ $(cat "${SLFSB}") -lt 61810 ]] then echo "Chapter 5. Compiling a Cross-Toolchain" if cross_toolchain 6 then echo "61810" > "${SLFSB}" fi fi if [[ $(cat "${SLFSB}") -gt 50000 ]] && [[ $(cat "${SLFSB}") -lt 90000 ]] then check_installed6 m4 check_installed6 ncurses check_installed6 bash check_installed6 coreutils check_installed6 diffutils check_installed6 file check_installed6 findutils check_installed6 gawk check_installed6 grep check_installed6 gzip check_installed6 make check_installed6 patch check_installed6 sed check_installed6 tar check_installed6 xz check_installed6 binutils check_installed6 gcc fi ask_for_exit 70200 ### PREPARE CHROOT ### echo "7.2. Changing Ownership" if [[ $(cat "${SLFSB}") -lt 70200 ]] then echo "Preparing for chroot step." echo "/mnt/lfs will be closed for chroot" echo "Do you validate preceding steps ?" if ask_for_exit 61810 then case $(uname -m) in x86_64) if ! sudo /usr/bin/chown -R root:root $LFS/lib64 then echo "Rights error" exit 1 fi ;; esac if sudo /usr/bin/chown -R root:root $LFS/{usr,var,etc,tools} then sudo /usr/bin/chown lfs "${SLFSB}" || exit 1 echo "70200" > "${SLFSB}" else echo "Rights error" exit 1 fi fi fi ask_for_exit 61810 echo "7.3. Preparing Virtual Kernel File Systems" if [[ $(cat "${SLFSB}") -ge 70200 ]] then if ! check_virtual_kernel_filesystems then if ! mount_virtual_kernel_filesystem then echo "7.3. Preparing Virtual Kernel File Systems" echo "Mount failure. Please fix it!" exit 1 fi if ! check_virtual_kernel_filesystems then echo "7.3. Preparing Virtual Kernel File Systems" echo "Mount failure. Please fix it!" exit 1 fi fi fi ask_for_exit 61810 ### CHROOT FIRST CONFIGURATION ### echo "7.5. Creating Directories" if [[ $(cat "${SLFSB}") -lt 70500 ]] then sudofile=/tmp/lfs_70500.sh cat > ${sudofile} << "EOSF" mkdir -pv /{boot,home,mnt,opt,srv} mkdir -pv /etc/{opt,sysconfig} mkdir -pv /lib/firmware mkdir -pv /media/{floppy,cdrom} mkdir -pv /usr/{,local/}{include,src} mkdir -pv /usr/lib/locale mkdir -pv /usr/local/{bin,lib,sbin} mkdir -pv /usr/{,local/}share/{color,dict,doc,info,locale,man} mkdir -pv /usr/{,local/}share/{misc,terminfo,zoneinfo} mkdir -pv /usr/{,local/}share/man/man{1..8} mkdir -pv /var/{cache,local,log,mail,opt,spool} mkdir -pv /var/lib/{color,misc,locate} ln -sfv /run /var/run ln -sfv /run/lock /var/lock install -dv -m 0750 /root install -dv -m 1777 /tmp /var/tmp EOSF if lfs_chroot "${sudofile}" then echo "70500" > "${SLFSB}" fi fi ask_for_exit 61810 echo "7.6. Creating Essential Files and Symlinks" if [[ $(cat "${SLFSB}") -lt 70600 ]] then sudofile=/tmp/lfs_70600.sh cat > ${sudofile} << "EOSF" ln -sv /proc/self/mounts /etc/mtab cat > /etc/hosts << EOF 127.0.0.1 localhost $(hostname) ::1 localhost EOF cat > /etc/passwd << "EOF" root:x:0:0:root:/root:/bin/bash bin:x:1:1:bin:/dev/null:/usr/bin/false daemon:x:6:6:Daemon User:/dev/null:/usr/bin/false messagebus:x:18:18:D-Bus Message Daemon User:/run/dbus:/usr/bin/false systemd-journal-gateway:x:73:73:systemd Journal Gateway:/:/usr/bin/false systemd-journal-remote:x:74:74:systemd Journal Remote:/:/usr/bin/false systemd-journal-upload:x:75:75:systemd Journal Upload:/:/usr/bin/false systemd-network:x:76:76:systemd Network Management:/:/usr/bin/false systemd-resolve:x:77:77:systemd Resolver:/:/usr/bin/false systemd-timesync:x:78:78:systemd Time Synchronization:/:/usr/bin/false systemd-coredump:x:79:79:systemd Core Dumper:/:/usr/bin/false uuidd:x:80:80:UUID Generation Daemon User:/dev/null:/usr/bin/false systemd-oom:x:81:81:systemd Out Of Memory Daemon:/:/usr/bin/false nobody:x:65534:65534:Unprivileged User:/dev/null:/usr/bin/false EOF cat > /etc/group << "EOF" root:x:0: bin:x:1:daemon sys:x:2: kmem:x:3: tape:x:4: tty:x:5: daemon:x:6: floppy:x:7: disk:x:8: lp:x:9: dialout:x:10: audio:x:11: video:x:12: utmp:x:13: clock:x:14: cdrom:x:15: adm:x:16: messagebus:x:18: systemd-journal:x:23: input:x:24: mail:x:34: kvm:x:61: systemd-journal-gateway:x:73: systemd-journal-remote:x:74: systemd-journal-upload:x:75: systemd-network:x:76: systemd-resolve:x:77: systemd-timesync:x:78: systemd-coredump:x:79: uuidd:x:80: systemd-oom:x:81: wheel:x:97: users:x:999: nogroup:x:65534: EOF echo "tester:x:101:101::/home/tester:/bin/bash" >> /etc/passwd echo "tester:x:101:" >> /etc/group install -o tester -d /home/tester touch /var/log/{btmp,lastlog,faillog,wtmp} chgrp -v utmp /var/log/lastlog chmod -v 664 /var/log/lastlog chmod -v 600 /var/log/btmp EOSF if lfs_chroot "${sudofile}" then echo "70600" > "${SLFSB}" fi fi ask_for_exit 61810 ### CHROOT COMPILATION ### echo "7.7 Building Additional Temporary Tools" if [[ $(cat "${SLFSB}") -lt 71300 ]] then if building_temporary_tools 7 then echo "71210" > "${SLFSB}" fi fi if [[ $(cat "${SLFSB}") -gt 70700 ]] && [[ $(cat "${SLFSB}") -lt 90000 ]] then check_installed7 gettext check_installed7 bison check_installed7 perl check_installed7 Python check_installed7 texinfo check_installed7 util-linux fi ask_for_exit 71210 echo "7.13. Cleaning up and Saving the Temporary System" if [[ $(cat "${SLFSB}") -lt 71310 ]] then sudofile=/tmp/lfs_71310.sh cat > ${sudofile} << "EOSF" rm -rf /usr/share/{info,man,doc}/* find /usr/{lib,libexec} -name \*.la -delete # rm -rf /tools EOSF if lfs_chroot "${sudofile}" then echo "71310" > "${SLFSB}" fi fi ask_for_exit 71310 echo "8. Installing Basic System Software" if [[ $(cat "${SLFSB}") -lt 88410 ]] then # Fix timezone for glibc with the same timezone as build computer sed "sqAmerica/New_Yorkq$(realpath --relative-to=/usr/share/zoneinfo /etc/localtime)q" -i "$SOURCES"/80510_glibc.sh if building_temporary_tools 8 then echo "88310" > "${SLFSB}" fi fi if [[ $(cat "${SLFSB}") -gt 70700 ]] && [[ $(cat "${SLFSB}") -lt 90000 ]] then check_installed8 man-pages check_installed8 iana-etc check_installed8 glibc check_installed8 zlib check_installed8 bzip2 check_installed8 xz check_installed8 lz4 check_installed8 zstd check_installed8 file check_installed8 readline check_installed8 pcre2 check_installed8 m4 check_installed8 bc check_installed8 flex check_installed8 tcl8.6.17-src check_installed8 expect check_installed8 dejagnu check_installed8 pkgconf check_installed8 gprof check_installed8 gmp check_installed8 mpfr check_installed8 mpc check_installed8 attr check_installed8 acl check_installed8 libcap check_installed8 libxcrypt check_installed8 shadow check_installed8 gcc check_installed8 ncurses check_installed8 sed check_installed8 psmisc check_installed8 gettext check_installed8 bison check_installed8 grep check_installed8 bash check_installed8 libtool check_installed8 gdbm check_installed8 gperf check_installed8 expat check_installed8 inetutils check_installed8 less check_installed8 perl check_installed8 XML-Parser check_installed8 intltool check_installed8 autoconf check_installed8 automake check_installed8 openssl check_installed8 elfutils check_installed8 libffi check_installed8 sqlite-autoconf check_installed8 Python check_installed8 flit check_installed8 packaging check_installed8 wheel check_installed8 setuptools check_installed8 ninja check_installed8 meson check_installed8 kmod check_installed8 coreutils check_installed8 diffutils check_installed8 gawk check_installed8 findutils check_installed8 groff check_installed8 grub check_installed8 gzip check_installed8 iproute2 check_installed8 kbd check_installed8 libpipeline check_installed8 make check_installed8 patch check_installed8 tar check_installed8 texinfo check_installed8 vim check_installed8 markupsafe check_installed8 jinja2 check_installed8 systemd check_installed8 dbus check_installed8 man-db check_installed8 procps check_installed8 util-linux check_installed8 e2fsprogs fi ask_for_exit 88510 echo "8.85. Stripping" if [[ $(cat "${SLFSB}") -lt 88510 ]] then sudofile=/tmp/lfs_88510.sh cat > ${sudofile} << "EOSF" save_usrlib="$(cd /usr/lib; ls ld-linux*[^g]) libc.so.6 libthread_db.so.1 libquadmath.so.0.0.0 libstdc++.so.6.0.34 libitm.so.1.0.0 libatomic.so.1.2.0" cd /usr/lib for LIB in $save_usrlib; do objcopy --only-keep-debug --compress-debug-sections=zstd $LIB $LIB.dbg cp $LIB /tmp/$LIB strip --strip-debug /tmp/$LIB objcopy --add-gnu-debuglink=$LIB.dbg /tmp/$LIB install -vm755 /tmp/$LIB /usr/lib rm /tmp/$LIB done online_usrbin="bash find strip" online_usrlib="libbfd-2.46.0.20260210.so libsframe.so.3.0.0 libhistory.so.8.3 libncursesw.so.6.6 libm.so.6 libreadline.so.8.3 libz.so.1.3.2 libzstd.so.1.5.7 $(cd /usr/lib; find libnss*.so* -type f)" for BIN in $online_usrbin; do cp /usr/bin/$BIN /tmp/$BIN strip --strip-debug /tmp/$BIN install -vm755 /tmp/$BIN /usr/bin rm /tmp/$BIN done for LIB in $online_usrlib; do cp /usr/lib/$LIB /tmp/$LIB strip --strip-debug /tmp/$LIB install -vm755 /tmp/$LIB /usr/lib rm /tmp/$LIB done for i in $(find /usr/lib -type f -name \*.so* ! -name \*dbg) \ $(find /usr/lib -type f -name \*.a) \ $(find /usr/{bin,sbin,libexec} -type f); do case "$online_usrbin $online_usrlib $save_usrlib" in *$(basename $i)* ) ;; * ) strip --strip-debug $i ;; esac done unset BIN LIB save_usrlib online_usrbin online_usrlib EOSF echo "Do you want to strip binaries ?" if ${LFS_STRIP_BINARIES} then if lfs_chroot "${sudofile}" then echo "88510" > "${SLFSB}" fi else echo "Skip stripping" echo "88510" > "${SLFSB}" fi fi ask_for_exit 88610 echo "8.86. Cleaning Up" if [[ $(cat "${SLFSB}") -lt 88610 ]] then sudofile=/tmp/lfs_88610.sh cat > ${sudofile} << "EOSF" #rm -rf /tmp/{*,.*} find /usr/lib /usr/libexec -name \*.la -delete find /usr -depth -name $(uname -m)-lfs-linux-gnu\* | xargs rm -rf userdel -r tester EOSF if lfs_chroot "${sudofile}" then echo "88610" > "${SLFSB}" fi fi ask_for_exit 90210 echo "9.2.GeneralNetworkConfiguration" if [[ $(cat "${SLFSB}") -lt 90210 ]] then if ${LFS_OFFLINE} then echo "Offline Build -- no network" echo "90210" > "${SLFSB}" elif ${LFS_NETWORK} then sudofile=/tmp/lfs_90210.sh INTERFACE=$(ip route |grep default |cut --delimiter=' ' --fields=5) GATEWAY=$(ip route |grep default |cut --delimiter=' ' --fields=3) IPADDRESS=$(ip address show dev "${INTERFACE}" |grep "${INTERFACE}$" |cut --delimiter=' ' --fields=6) if ip address show dev "${INTERFACE}" |grep "${INTERFACE}$" |grep dynamic then IPORIGIN=dynamic elif ip address show dev "${INTERFACE}" |grep "${INTERFACE}$" |grep static then IPORIGIN=static else echo "Network configuration error" fi DNSADDRESS=$(grep nameserver /etc/resolv.conf | cut --delimiter=' ' --fields=2) case "${IPORIGIN}" in dynamic) cat > ${sudofile} << EOSF echo "Set dynamic address" cat > /etc/systemd/network/10-eth-dhcp.network << "EOF" [Match] Name=${INTERFACE} [Network] DHCP=ipv4 [DHCPv4] UseDomains=true EOF echo "$(cat /etc/hostname)" > /etc/hostname echo "$(cat /etc/hosts)" > /etc/hosts EOSF ;; static) cat > ${sudofile} << EOSF echo "Set static address" cat > /etc/systemd/network/10-eth-static.network << "EOF" [Match] Name=${INTERFACE} [Network] Address=${IPADDRESS} Gateway=${GATEWAY} DNS=${DNSADDRESS} #Domains= EOF echo "$(cat /etc/hostname)" > /etc/hostname echo "$(cat /etc/hosts)" > /etc/hosts EOSF ;; *) echo "Unknown configuration. Network configuration error" exit 1 ;; esac echo "Configure network (same as host)" if lfs_chroot "${sudofile}" then echo "90210" > "${SLFSB}" else echo "Network configuration error" exit 1 fi else echo "Script is stopped for networking configuration" echo "90210" > "${SLFSB}" exit 0 fi fi ask_for_exit 90610 echo "9.6. Configuring the Linux Console" if [[ $(cat "${SLFSB}") -lt 90610 ]] then VCONSOLE=/mnt/lfs/tmp/vconsole.conf cat > ${VCONSOLE} << EOSF KEYMAP=XX FONT=XX XKBLAYOUT=XX EOSF # try with KEYMAP from vconsole host if grep --silent 'KEYMAP' /etc/vconsole.conf then keymap=$(grep --silent 'KEYMAP' /etc/vconsole.conf |cut --delimiter='=' --fields=2 |sed 's/ //g') if [[ "${keymap}" =~ ^[a-z][a-z]$ ]] then sed /KEYMAP/s/KEYMAP=XX/KEYMAP="${keymap}"/ -i ${VCONSOLE} fi fi # try with FONT from vconsole host if grep -q 'FONT' /etc/vconsole.conf then font=$(grep --silent 'FONT' /etc/vconsole.conf |cut --delimiter='=' --fields=2 |sed 's/ //g') if [[ "${font}" =~ ^[a-z0-9][a-z0-9]+$ ]] then sed /FONT/s/FONT=XX/FONT="${font}"/ -i ${VCONSOLE} fi fi # try with XKBLAYOUT from vconsole host if grep -q 'XKBLAYOUT' /etc/vconsole.conf then xkblayout=$(grep --silent 'XKBLAYOUT' /etc/vconsole.conf | cut --delimiter='=' --fields=2 |sed 's/ //g') if [[ "${xkblayout}" =~ ^[a-z0-9][a-z0-9]+$ ]] then sed /XKBLAYOUT/s/XKBLAYOUT=XX/XKBLAYOUT="${xkblayout}"/ -i ${VCONSOLE} fi fi # try with VC KEYMAP from localctl host localectl status | while IFS= read -r localectls do if echo "${localectls}" | grep --silent "VC Keymap" then keymap=$(echo "${localectls}" | cut --delimiter=':' --fields=2 |sed 's/ //g') if [[ "${keymap}" =~ ^[a-z][a-z]$ ]] then sed /KEYMAP/s/KEYMAP=XX/KEYMAP="${keymap}"/ -i ${VCONSOLE} fi fi done # try with X11 Layout from localectl host localectl status | while IFS= read -r localectls do if echo "${localectls}" | grep --silent "X11 Layout" then xkblayout=$(echo "${localectls}" | cut --delimiter=':' --fields=2 | sed 's/ //g') if [[ "${xkblayout}" =~ ^[a-z][a-z]$ ]] then sed /KEYMAP/s/KEYMAP=XX/KEYMAP="${xkblayout}"/ -i ${VCONSOLE} sed /XKBLAYOUT/s/XKBLAYOUT=XX/XKBLAYOUT="${xkblayout}"/ -i ${VCONSOLE} fi fi done # retry with VC KEYMAP from localectl host localectl status | while IFS= read -r localectls do if echo "${localectls}" | grep --silent "VC Keymap" then keymap=$(echo "${localectls}" | cut --delimiter=':' --fields=2 |sed 's/ //g') if [[ "${keymap}" =~ ^[a-z][a-z]$ ]] then sed /KEYMAP/s/KEYMAP=XX/KEYMAP="${keymap}"/ -i ${VCONSOLE} sed /XKBLAYOUT/s/XKBLAYOUT=XX/XKBLAYOUT="${keymap}"/ -i ${VCONSOLE} fi fi done # default if nothing is set (if KEYMAP=XX) sed "/KEYMAP/s/KEYMAP=XX/KEYMAP=fr/" --in-place ${VCONSOLE} sed "/FONT/s/FONT=XX/FONT=Lat2-Terminus16/" --in-place ${VCONSOLE} sed "/XKBLAYOUT/s/XKBLAYOUT=XX/XKBLAYOUT=fr/" --in-place ${VCONSOLE} # building chroot sudofile=/tmp/lfs_90610.sh cat > ${sudofile} << "EOSF" cp -v /tmp/vconsole.conf /etc/vconsole.conf EOSF if lfs_chroot "${sudofile}" then echo "90610" > "${SLFSB}" else echo "Configuration error" exit 1 fi fi ask_for_exit 90710 echo "9.7. Configuring the System Locale" if [[ $(cat "${SLFSB}") -lt 90710 ]] then LOCALECONF=/mnt/lfs/tmp/locale.conf cat > ${LOCALECONF} << EOSF LANG=XX EOSF # try with KEYMAP from vconsole host if grep --silent 'LANG' /etc/locale.conf then language=$(grep --silent 'LANG' /etc/locale.conf | cut --delimiter='=' --fields=2 |sed 's/ //g') if [[ "${language}" =~ ^["][a-z][a-zA-Z0-9_@.-]+["]$ ]] then sed /LANG/s/LANG=XX/LANG="${language}"/ --in-place "${LOCALECONF}" fi fi # default if nothing is set (if LANG=XX) sed /LANG/s/LANG=XX/LANG="fr_FR.UTF-8"/ --in-place "${LOCALECONF}" sudofile=/tmp/lfs_90710.sh cat > ${sudofile} << "EOSF" cp -v /tmp/locale.conf /etc/locale.conf cat > /etc/profile << "EOF" # Begin /etc/profile for i in $(locale); do unset ${i%=*} done if [[ "$TERM" = linux ]]; then export LANG=C.UTF-8 else source /etc/locale.conf for i in $(locale); do key=${i%=*} if [[ -v $key ]]; then export $key fi done fi # End /etc/profile EOF EOSF if lfs_chroot "${sudofile}" then echo "90710" > "${SLFSB}" else echo "Configuration error" exit 1 fi fi ask_for_exit 90810 echo "9.8. Creating the /etc/inputrc File " if [[ $(cat "${SLFSB}") -lt 90810 ]] then sudofile=/tmp/lfs_90810.sh cat > ${sudofile} << "EOSF" cat > /etc/inputrc << "EOF" # Begin /etc/inputrc # Modified by Chris Lynn # Allow the command prompt to wrap to the next line set horizontal-scroll-mode Off # Enable 8-bit input set meta-flag On set input-meta On # Turns off 8th bit stripping set convert-meta Off # Keep the 8th bit for display set output-meta On # none, visible or audible set bell-style none # All of the following map the escape sequence of the value # contained in the 1st argument to the readline specific functions "\eOd": backward-word "\eOc": forward-word # for linux console "\e[1~": beginning-of-line "\e[4~": end-of-line "\e[5~": beginning-of-history "\e[6~": end-of-history "\e[3~": delete-char "\e[2~": quoted-insert # for xterm "\eOH": beginning-of-line "\eOF": end-of-line # for Konsole "\e[H": beginning-of-line "\e[F": end-of-line # End /etc/inputrc EOF EOSF if lfs_chroot "${sudofile}" then echo "90810" > "${SLFSB}" else echo "Configuration error" exit 1 fi fi ask_for_exit 90910 echo "9.9. Creating the /etc/shells File" if [[ $(cat "${SLFSB}") -lt 90910 ]] then sudofile=/tmp/lfs_90910.sh cat > ${sudofile} << "EOSF" cat > /etc/shells << "EOF" # Begin /etc/shells /bin/sh /bin/bash # End /etc/shells EOF EOSF if lfs_chroot "${sudofile}" then echo "90910" > "${SLFSB}" else echo "Configuration error" exit 1 fi fi ask_for_exit 91010 echo "9.10. Systemd Usage and Configuration" if [[ $(cat "${SLFSB}") -lt 91010 ]] then sudofile=/tmp/lfs_91010.sh cat > ${sudofile} << "EOSF" mkdir -pv /etc/systemd/system/getty@tty1.service.d cat > /etc/systemd/system/getty@tty1.service.d/noclear.conf << EOF [Service] TTYVTDisallocate=no # ln -sfv /dev/null /etc/systemd/system/tmp.mount EOF EOSF if lfs_chroot "${sudofile}" then echo "91010" > "${SLFSB}" cat < ${FSTAB} << EOSF UUID=${blockuuid} / ext4 defaults 0 0 EOSF fi ;; *) continue ;; esac done if [ ! -e ${FSTAB} ] then echo "Can't init /etc/fstab" echo "Fix it by ourself" exit 1 fi swapuuid=$(lsblk --output UUID,MOUNTPOINTS |grep SWAP |head -1 |cut --delimiter=' ' --fields=1) if [[ "${blockuuid}" =~ ^[a-zA-Z0-9-]+$ ]] then cat >> ${FSTAB} << EOSF UUID=${swapuuid} none swap sw 0 0 EOSF echo "The first swap partition found of the host was written in /etc/fstab" echo "Fix it of you have/want another swap" else echo "Can't init swap /etc/fstab" echo "Fix it by ourself" fi sudofile=/tmp/lfs_100200.sh cat > ${sudofile} << "EOSF" cp -v /tmp/fstab /etc/fstab EOSF if lfs_chroot "${sudofile}" then echo "100200" > "${SLFSB}" echo "Please check /etc/fstab in /mnt/lfs" echo "Check root and swap" echo "Add /boot and other mount point if necessary" else echo "Configuration error" exit 1 fi fi ask_for_exit 103100 echo "10.3.1. Installation of the kernel" if [[ $(cat "${SLFSB}") -lt 103100 ]] then step=103100 scriptname=${step}_linux.sh unnumbered=${scriptname##*_} packagename=${unnumbered%.*} archivepath=$(find "${SOURCES}" -name "${packagename}*.tar.*" -print) archivesubpath=${archivepath##/mnt/lfs} archivename=$(basename "${archivepath}") package=${archivename%%.tar.xz} buildpath=/sources/"${package}" linuxversion=${package##*-} sudofile=/tmp/lfs_103100.sh cat > "${sudofile}" << EOSF if [ ! -d "${buildpath}" ] then mkdir -p "${buildpath}" fi if [ ! -e "${buildpath}"/COPYING ] then if ! tar -xf "${archivesubpath}" -C "${buildpath}" --strip-components=1 then echo "untar error" exit 1 fi fi pushd "${buildpath}" set -ueExo pipefail eval "\$(cat ../"${scriptname}")" | tee "/tmp/lfs_103100.log" popd EOSF if ! lfs_chroot "${sudofile}" then echo "compilation error" exit 1 else echo "compilation ok" fi check_errors "${STEMP}/lfs_103100.log" echo 103100 > "${SLFSB}" fi ask_for_exit 103110 echo "10.3.1. Installation of the kernel" if [[ $(cat "${SLFSB}") -lt 103110 ]] then step=103100 scriptname=${step}_linux.sh unnumbered=${scriptname##*_} packagename=${unnumbered%.*} archivepath=$(find "${SOURCES}" -name "${packagename}*.tar.*" -print) archivename=$(basename "${archivepath}") package=${archivename%%.tar.xz} buildpath=/sources/"${package}" linuxversion=${package##*-} if ${LFS_LINUXCONFIG} then if cp --verbose "${SCRIPT_DIR}/linux-config-${ARCH}.txt" /mnt/lfs/tmp/linux-config-host then sudofile=/tmp/lfs_103110.sh cat > ${sudofile} << EOSF cp --verbose /tmp/linux-config-host ${buildpath}/.config EOSF if lfs_chroot "${sudofile}" then echo "copy ok" echo "103110" > "${SLFSB}" else echo "copy error" exit 1 fi else echo "Can't find a linux configuration" echo "Fix it !" exit 1 fi fi if [ -e /mnt/lfs/sources/"${package}"/.config ] then echo "103110" > "${SLFSB}" echo "A config file for kernel compilation exist" else echo "103110" > "${SLFSB}" echo "Script is stopped for linux configuration" echo "It's time to configure kernel compilation" echo "LFS recommand to compile the kernel by youself" echo "Please execute as lfs :" echo "$ bash $HOME/lfs_chroot.sh" echo "(lfs chroot) root:/$ cd /sources/linux-6.8.10" echo "(lfs chroot) root:/$ make menuconfig" echo "you can try this at minimal :" echo "(lfs chroot) root:/$ make defconfig" exit 0 fi fi ask_for_exit 103120 echo "10.3.1. Installation of the kernel" if [[ $(cat "${SLFSB}") -lt 103120 ]] then step=103100 scriptname=${step}_linux.sh unnumbered=${scriptname##*_} packagename=${unnumbered%.*} archivepath=$(find "${SOURCES}" -name "${packagename}*.tar.*" -print) archivename=$(basename "${archivepath}") package=${archivename%%.tar.xz} buildpath=/sources/"${package}" linuxversion=${package##*-} if [ ! -e "${LFS}"/"${buildpath}"/.config ] then echo "Seems kernel was not configured" echo "Please execute as lfs :" echo "$ bash /tmp/lfs_chroot.sh" echo "(lfs chroot) root:/$ cd ${buildpath}" echo "(lfs chroot) root:/$ make menuconfig" echo "you can try too :" echo "(lfs chroot) root:/$ make defconfig" exit 1 fi sudofile=/tmp/lfs_103120.sh cat > ${sudofile} << EOSF cd "${buildpath}" make if grep "CONFIG_MODULES=y" "${buildpath}"/.config then make modules fi cp -v arch/x86/boot/bzImage /boot/vmlinuz-${linuxversion}-lfs-13.0-systemd cp -v System.map /boot/System.map-${linuxversion} cp -v .config /boot/config-${linuxversion} cp -r Documentation -T /usr/share/doc/${package} install -v -m755 -d /etc/modprobe.d cat > /etc/modprobe.d/usb.conf << "EOF" # Begin /etc/modprobe.d/usb.conf install ohci_hcd /sbin/modprobe ehci_hcd ; /sbin/modprobe -i ohci_hcd ; true install uhci_hcd /sbin/modprobe ehci_hcd ; /sbin/modprobe -i uhci_hcd ; true # End /etc/modprobe.d/usb.conf EOF EOSF if ! lfs_chroot "${sudofile}" then echo "compilation error" exit 1 else echo "compilation ok" echo "103120" > "${SLFSB}" fi fi ask_for_exit 104000 echo "10.4. Using GRUB to Set Up the Boot Process " if [[ $(cat "${SLFSB}") -lt 104000 ]] then # get "linux-6.8.10" archivepath=$(find "${SOURCES}" -name "linux-*.tar.*" -print) archivename=$(basename "${archivepath}") package=${archivename%%.tar.xz} buildpath=/sources/"${package}" linuxversion=${package##*-} # get root device uuid blockdevice=$(mount |grep '/mnt/lfs type ext4' | cut --delimiter=' ' --fields=1) #for link in /dev/disk/by-uuid/* #do # case $(readlink "${link}") in # *${blockdevice}) # echo "found ${blockdevice} with link ${link}" # blockuuid=$(basename "${link}") # if [[ ! "${blockuuid}" =~ ^[a-zA-Z0-9-]+$ ]] # then # echo "Can't init grub.conf" # echo "Fix it by ourself" # exit 1 # fi # ;; # *) # continue # ;; # esac #done # if [ ! -e "$LFS/boot/vmlinuz-${linuxversion}-lfs-13.0-systemd" ] then echo "Kernel file absent from /boot" exit 1 fi uuidfilesystem=$(lsblk -o UUID,PARTUUID,PATH,MOUNTPOINT |grep /mnt/lfs$ |cut --delimiter=' ' --fields=1) if [[ ! "${uuidfilesystem}" =~ ^[a-z0-9-]+$ ]] then echo "UUID seems bad" exit 1 fi uuidpartition=$(lsblk -o UUID,PARTUUID,PATH,MOUNTPOINT |grep /mnt/lfs$ |cut --delimiter=' ' --fields=2) if [[ ! "${uuidpartition}" =~ ^[a-z0-9-]+$ ]] then echo "PARTUUID seems bad" exit 1 fi sudofile=/tmp/lfs_104000.sh cat > ${sudofile} << EOSF mkdir --verbose /boot/grub cat > /boot/grub/grub.cfg << "EOF" # Begin /boot/grub/grub.cfg set default=0 set timeout=5 insmod part_gpt insmod ext2 search --set=root --fs-uuid=${uuidfilesystem} set gfxpayload=1024x768x32 menuentry "GNU/Linux, Linux ${linuxversion}-lfs-13.0-systemd" { linux /boot/vmlinuz-${linuxversion}-lfs-13.0-systemd root=${blockdevice} ro } EOF EOSF if lfs_chroot "${sudofile}" then echo "104000" > "${SLFSB}" else echo "grub config error" exit 1 fi fi ask_for_exit 110100 echo "11.1. The End" if [[ $(cat "${SLFSB}") -lt 110100 ]] then sudofile=/tmp/lfs_110100.sh cat > ${sudofile} << EOSF echo 13.0-systemd > /etc/lfs-release cat > /etc/lsb-release << "EOF" DISTRIB_ID="Linux From Scratch" DISTRIB_RELEASE="13.0-systemd" DISTRIB_CODENAME="" DISTRIB_DESCRIPTION="Linux From Scratch" EOF cat > /etc/os-release << "EOF" NAME="Linux From Scratch" VERSION="13.0-systemd" ID=lfs PRETTY_NAME="Linux From Scratch 13.0-systemd" VERSION_CODENAME="" HOME_URL="https://www.linuxfromscratch.org/lfs/" RELEASE_TYPE="stable" EOF EOSF if lfs_chroot "${sudofile}" then echo "You can edit /etc/lsb-release and /etc/os-release and edit your name" echo "110100" > "${SLFSB}" else echo "release file creation error" exit 1 fi fi echo "Finish successfully" echo "Adapt /boot/grub/grub.cfg to your configuration" echo "And install the bootloader if needed with the appropriate boot device" echo "(lfs chroot) root:/$ grub-install /dev/xda" } if [[ "${BASH_SOURCE[0]}" == "$0" ]]; then main "$@" fi