Radix cross Linux

The main Radix cross Linux repository contains the build scripts of packages, which have the most complete and common functionality for desktop machines

452 Commits   2 Branches   1 Tag
#!/bin/bash

program=`basename $0`
sbindir=`cd $(dirname ${BASH_SOURCE[0]}) >/dev/null 2>&1 && pwd`

# 13 = permission denied (should be root)
# 14 = there is no '.pkglist' file
# 15 = invalid target device
# 16 = target device has not specified arter --root-dev option
# 17 = source REPO directory is invalid
# 18 = custom REPO directory has not specified by --repo option
# 19 = target device too small
# 20 = /sbin/fdisk returns bad status
# 21 = cannot mount ROOT partition
# 22 = cannot mount EFI partition
# 92 = Cannot create '/tmp/...' directory
# 93 = Unexpected program abort
EXITSTATUS=0

WHERE=${sbindir}/where-we-are

#
# Getting information about DISTRO:
#
push_err() {
  message=$1
  echo -n "$program: " >&2 ; echo "${message}" >&2
}

if [ ! -r /etc/os-release ] ; then
  push_err "ERROR: /etc/os-release: There are no operating system information"
  exit 1
fi

. /etc/os-release

if [ ! -r /etc/${ID}-release ] ; then
  push_err "ERROR: /etc/${ID}-release: There are no ${ID} distribution information"
  exit 1
fi

. /etc/${ID}-release

LOG_FILE=${LOG_FILE:-/var/log/${DISTRO_NAME}-${program}.log}

DIALOG=${DIALOG:-/bin/dialog}

push_log() {
  message=$1
  echo -n "[`LANG=en LANGUAGE=en date +'%d-%b-%Y %H:%M:%S'`] $program: " >> ${LOG_FILE}
  echo    "${message}" >> ${LOG_FILE}
}

umask 022
TMP=$(mkdir -p /tmp/${DISTRO_NAME} && mktemp -d -p /tmp/${DISTRO_NAME} $program.XXXXXXXX) || { echo "Cannot create '/tmp/...' directory" ; exit 92; }
mkdir -p /tmp/${DISTRO_NAME}/mnt
MNT=/tmp/${DISTRO_NAME}/mnt
#
# Clear screen on unexpected termination:
#
trap 'clear ; \
      head -c 100 /dev/zero | tr "\0" "\n" ; \
      echo "ERROR: $program - has been terminated." ; \
      echo "" ; \
      EXITSTATUS=93 ; \
      ' INT TERM HUP QUIT
#
# This program cam mount filesystems to first level
# directories relative to $MNT or directly to $MNT:
#
trap 'for dir in `find ${MNT} -type d -mindepth 1 -maxdepth 1` ; do \
        umount $dir 2> /dev/null ; \
      done ; \
      umount ${MNT} 2> /dev/null ; \
      rm -rf /tmp/${DISTRO_NAME} ; \
      rm -f /etc/system-installer ; \
      exit ${EXITSTATUS} ;\
      ' EXIT


check_current_user()
{
  echo "Radix System Setup" > /etc/system-installer

  if [ "$EUID" != "0" ] ; then
    $DIALOG --colors --clear \
            --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
            --title " \Z0Setup:\Zn \Z1\ZbERROR\ZB\Zn " \
            --msgbox "\n\Z4${program}\Zn - \Z1program should be run by root.\Zn\n" 7 74

    push_log "ERROR: Program should be run by root"
    push_log "Aborted due to an error"
    push_err "ERROR: Program should be run by root"
    EXITSTATUS=13
    exit
  fi
}

ask_exit_setup() {
  cat > $TMP/exit-setup-help$$ << EOF

 Do you want to terminate Radix System Installation?

EOF

  $DIALOG --colors --defaultno --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Setup:\Zn \Z4\ZbExit\ZB\Zn " \
          --no-label "No" \
          --yes-label "Ok" \
          --yesno "$(cat $TMP/exit-setup-help$$)" 7 74
  ret=$?
  rm -f $TMP/exit-setup-help$$
  if [ $ret -eq 0 ] ; then
    push_log "Done"
    exit
  fi
}

fatal_error_dialog()
{
  local msg="${1}"
  cat > $TMP/fatal-message$$ << EOF

 ${msg}

EOF

  $DIALOG --colors --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Setup:\Zn \Z1\ZbERROR\ZB\Zn " \
          --msgbox "$(cat $TMP/fatal-message$$)" 7 74
}

error_dialog()
{
  local msg="${1}"
  cat > $TMP/error-message$$ << EOF

 ${msg}

EOF

  $DIALOG --colors --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Setup:\Zn \Z1\ZbERROR\ZB\Zn " \
          --no-label " Exit Setup " \
          --yes-label " Continue " \
          --yesno "$(cat $TMP/error-message$$)" 7 74
  ret=$?
  rm -f $TMP/error-message$$
  if [ $ret -ne 0 ] ; then
    exit
  fi
}

welcome_setup()
{
  cat > $TMP/welcome-setup-rc$$ << EOF
use_colors = ON
shadow_color = (BLACK,BLACK,OFF)
screen_color = (WHITE,BLACK,ON)
use_shadow = OFF
dialog_color = (WHITE,BLACK,OFF)
title_color = (WHITE,BLACK,ON)
border_color = (BLACK,BLACK,OFF)
border2_color = (BLACK,BLACK,OFF)
button_active_color = (WHITE,BLACK,ON)
button_inactive_color = (WHITE,BLACK,OFF)
button_key_active_color = (RED,BLACK,ON)
button_key_inactive_color = (WHITE,BLACK,ON)
button_label_active_color = (WHITE,BLACK,ON)
button_label_inactive_color = (WHITE,BLACK,ON)
EOF

  cat > $TMP/welcome-setup-help$$ << EOF

Version \Zb${DISTRO_FULL_VERSION}\Zn
Copyright (c) 2009-`date +%Y`, Andrey V.Kosteltsev. All rights reserved.
${DISTRO_HOME_URL}

Built for ${HARDWARE_SPEC} [\Zb${HARDWARE}\Zn]
Toolchain ${TOOLCHAIN_VERSION} [\Zb${TOOLCHAIN_NAME}\Zn]

Now you can install \Zb${DISTRO_CAPTION}-${DISTRO_VERSION}\Zn to you hard drive or internal flash.

Enjoy!

EOF

  DIALOGRC=$TMP/welcome-setup-rc$$ \
  $DIALOG --colors --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " Setup ${DISTRO_CAPTION} \Z1cross\Zn Linux " \
          --no-label " Exit Setup " \
          --yes-label " Continue " \
          --yesno "$(cat $TMP/welcome-setup-help$$)" 16 74
  ret=$?
  rm -f $TMP/welcome-setup-help$$
  if [ $ret -ne 0 ] ; then
    exit
  fi
}

usage() {
 cat << EOF

Usage: $program [options]

$program - is used to install ${DISTRO_SPEC} from the 'repo' directory.

  The 'repo' directory sould contains ${DISTRO_CAPTION} packages set with '.pkglist'
  file at least for one HARDWARE. The ordinary structure of the 'repo'
  directories should seems like following:

    /var/lib/${DISTRO_NAME}/repo
    ├── ${DISTRO_FULL_VERSION}
        ├── TOOLCHAIN
       ...  └── HARDWARE
                ├── ...
        │      ...
        └── ${TOOLCHAIN_NAME}
            └── ${HARDWARE}
                ├── app
                │   ├── bash-5.2.9-`echo ${TOOLCHAIN_NAME} | cut -f1 -d'-'`-radix-${DISTRO_VERSION}.tgz
                │   ├── ...
                │  ...
                ├── base
                │   ├── ...
                │  ...
               ...

                └── .pkglist

  where, /var/lib/${DISTRO_NAME}/repo/${DISTRO_FULL_VERSION}/${TOOLCHAIN_NAME}/${HARDWARE} - applicable
  directory for current release.

options:
   -h | --help              - Display this information;
   -r | --root-dev <DEVICE> - Target device to install [/dev/sda,
                              /dev/mmcblk0, /dev/loop0, etc.];
   --repo <DIR>             - Absolute path to the REPO source directory
                              (Default: /var/lib/${DISTRO_NAME}/repo/${DISTRO_FULL_VERSION}/${TOOLCHAIN_NAME}/${HARDWARE}).
                              The user defined absolute path to the REPO directory must match
                              the standard pattern: '/custom-dir/VERSION/TOOLCHAIN/HARDWARE';

  The /etc/${DISTRO_NAME}-rlease file contains detailed info about
  setup parameters.

EOF
}

#
# Start installation:
#
push_log "Start of ${DISTRO_CAPTION}-${DISTRO_VERSION} installation"

# Only root can execute:
check_current_user

device=
version=${DISTRO_FULL_VERSION}
toolchain=${TOOLCHAIN_NAME}
hardware=${HARDWARE}
repo=/var/lib/${DISTRO_NAME}/repo/${DISTRO_FULL_VERSION}/${TOOLCHAIN_NAME}/${HARDWARE}

custom_repo=no

current_device=
current_root=
rootfs_min_bytes=

partition_table_type=o

uefi_part_number=1
root_part_number=1
home_part_number=2
swap_part_number=3

uefi_bytes=
if [ "${hardware}" = "baikal-m1"   -o \
     "${hardware}" = "orange-pi5"  -o \
     "${hardware}" = "visionfive2" -o \
     "${hardware}" = "intel-pc64" ] ; then
  partition_table_type=g
  uefi_bytes=268435456
fi

if [ "x${uefi_bytes}" != "x" ] ; then
  root_part_number=2
  home_part_number=3
  swap_part_number=4
fi

uefi_start_sector=
uefi_end_sector=
root_bytes=
root_start_sector=
root_end_sector=
home_bytes=
home_start_sector=
home_end_sector=
swap_bytes=
swap_start_sector=
swap_end_sector=

p=


################################################################
#
# Disk Geometry functions:
#

# Disk /dev/vda: 20 GiB, 21474836480 bytes, 41943040 sectors
# Sector size (logical/physical): 512 bytes / 512 bytes

bytes=
sectors=
unit_size=
log_sector_size=
phy_sector_size=
alignment=4096
format="512N"
start_sector=
ram_bytes=
#
#   Format | logical sector size | physical sector size
#  --------+---------------------+----------------------
#     512N |         512         |          512
#  --------+---------------------+----------------------
#     512E |         512         |         4096
#  --------+---------------------+----------------------
#    4096N |        4096         |         4096
#  --------+---------------------+----------------------
#

disk_size_in_bytes() {
  disk=${1}
  echo "`LANG=en_US.UTF-8 fdisk -l ${disk}`" | while read -r line ; do
    local found=`echo "${line}" | grep "^Disk ${disk}"`
    if [ "x${found}" != "x" ] ; then
      local bytes=`echo ${found} | sed 's,.* \([0-9]*\) bytes.*,\1,'`
      echo "${bytes}"
      break
    fi
  done
}

disk_size_in_sectors() {
  disk=${1}
  echo "`LANG=en_US.UTF-8 fdisk -l ${disk}`" | while read -r line ; do
    local found=`echo "${line}" | grep "^Disk ${disk}"`
    if [ "x${found}" != "x" ] ; then
      local sectors=`echo ${found} | sed 's,.* \([0-9]*\) sectors$,\1,'`
      echo "${sectors}"
      break
    fi
  done
}

disk_unit_size() {
  disk=${1}
  echo "`LANG=en_US.UTF-8 fdisk -l ${disk}`" | while read -r line ; do
    local found=`echo "${line}" | grep "^Unit"`
    if [ "x${found}" != "x" ] ; then
      local usize=`echo ${found} | sed 's,.*= \([0-9]*\) bytes$,\1,'`
      echo "${usize}"
      break
    fi
  done
}

disk_log_sector_size() {
  disk=${1}
  echo "`LANG=en_US.UTF-8 fdisk -l ${disk}`" | while read -r line ; do
    local found=`echo "${line}" | grep '^Sector size'`
    if [ "x${found}" != "x" ] ; then
      local lsize=`echo ${found} | sed 's,.* \([0-9]*\) bytes / \([0-9]*\) bytes$,\1,'`
      echo "${lsize}"
      break
    fi
  done
}

disk_phy_sector_size() {
  disk=${1}
  echo "`LANG=en_US.UTF-8 fdisk -l ${disk}`" | while read -r line ; do
    local found=`echo "${line}" | grep '^Sector size'`
    if [ "x${found}" != "x" ] ; then
      local psize=`echo ${found} | sed 's,.* \([0-9]*\) bytes / \([0-9]*\) bytes$,\2,'`
      echo "${psize}"
      break
    fi
  done
}

memory_size() {
  echo "`LANG=en_US.UTF-8 free -b -w`" | while read -r line ; do
    local found=`echo "${line}" | grep '^Mem'`
    if [ "x${found}" != "x" ] ; then
      local msize=`echo ${found} | tr -s ' ' | cut -f2 -d' '`
      echo "${msize}"
      break
    fi
  done
}

disk_geometry() {
  disk=${1}

  bytes=`disk_size_in_bytes ${disk}`
  sectors=`disk_size_in_sectors ${disk}`
  unit_size=`disk_unit_size ${disk}`
  log_sector_size=`disk_log_sector_size ${disk}`
  phy_sector_size=`disk_phy_sector_size ${disk}`

  ram_bytes=`memory_size`

  if [ $unit_size -eq $alignment ] ; then
    # Copy of GPT at end of disk:
    let "sectors = sectors - 5"
  else
    # Copy of GPT at end of disk:
    let "sectors = sectors - 33"
  fi

  if [ $phy_sector_size -eq $alignment ] ; then
    if [ $log_sector_size -lt $phy_sector_size ] ; then
      format="512E"
      start_sector=2048
    else
      format="4096N"
      start_sector=256
    fi
  else
    format="512N"
    start_sector=2048
  fi
}
#
# End of Disk Geometry functions.
#
################################################################

################################################################
#
# Disk Format functions:
#
clean_disk()
{
  local disk=${1}
  fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
${partition_table_type}
w
EOF

  partprobe ${disk}
}

create_EFI_partition()
{
  local disk=${1}

  local name="EFI System"
  local guid="c12a7328-f81f-11d2-ba4b-00a0c93ec93b"
  local type="ef"

  uefi_start_sector=${start_sector}

  let 'uefi_bytes = uefi_bytes / alignment * alignment'

  let 'uefi_end_sector = uefi_start_sector + ( uefi_bytes / unit_size - 1 )'
  let 'root_start_sector = uefi_end_sector + 1'

  if [ "${partition_table_type}" = "g" ] ; then
    fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
$uefi_part_number
$uefi_start_sector
$uefi_end_sector
t
$guid
x
n
$name
r
w
EOF
  else
    fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
p
$uefi_part_number
$uefi_start_sector
$uefi_end_sector
t
$type
w
EOF
  fi

  partprobe ${disk}

  mkfs.fat -F 32 -n UEFI ${disk}${p}1  2>/dev/null 1>/dev/null
}

create_ROOT_partition()
{
  local disk=${1}

  local name="Linux filesystem"
  local guid="0fc63daf-8483-4772-8e79-3d69d8477de4"
  local type="83"

  local half=
  local third=
  local GiB=1073741824
  local MiB=1048576

  if [ "${bytes}" -gt "${GiB}" ] ; then
    half=`echo  "scale=0; ( $bytes / $GiB / 2 - 1 ) * $GiB" | bc`
    third=`echo "scale=0; ( $bytes / $GiB / 3 + 1 ) * $GiB" | bc`
  else
    half=`echo  "scale=0; ( $bytes / $MiB / 2 - 1 ) * $MiB" | bc`
    third=`echo "scale=0; ( $bytes / $MiB / 3 + 1 ) * $MiB" | bc`
  fi

  let 'half  =  half / alignment * alignment'
  let 'third = third / alignment * alignment'

  if [ "x${uefi_bytes}" = "x" ] ; then
    root_start_sector=${start_sector}
    if [ "${hardware}" = "leez-p710" ] ; then
      root_start_sector=32768
    fi
  fi

  if [ "${third}" -gt "${rootfs_min_bytes}" ] ; then
    let 'root_end_sector = root_start_sector + ( third / unit_size - 1 )'
    let 'home_start_sector = root_end_sector + 1'
  elif [ "${half}" -gt "${rootfs_min_bytes}" ] ; then
    let 'root_end_sector = root_start_sector + ( half / unit_size - 1 )'
    let 'home_start_sector = root_end_sector + 1'
  elif [ "${bytes}" -gt "${rootfs_min_bytes}" ] ; then
    let 'root_end_sector = root_start_sector + ( rootfs_min_bytes / unit_size - 1 )'
    let 'home_start_sector = root_end_sector + 1'
  else
    fatal_error_dialog "Target device too small. Exit ${program}."
    push_log "ERROR: Target device too small"
    push_log "Aborted due to an error"
    push_err "ERROR: Target device too small"
    EXITSTATUS=19
    exit
  fi

  root_bytes=`echo "(${root_end_sector} - ${root_start_sector} + 1) * ${log_sector_size}" | bc`

  if [ "${root_part_number}" -eq "1" ] ; then
    if [ "${partition_table_type}" = "g" ] ; then
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
$root_part_number
$root_start_sector
$root_end_sector
t
$guid
x
n
$name
r
w
EOF
    else
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
p
$root_part_number
$root_start_sector
$root_end_sector
t
$type
w
EOF
    fi
  else
    if [ "${partition_table_type}" = "g" ] ; then
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
$root_part_number
$root_start_sector
$root_end_sector
t
$root_part_number
$guid
x
n
$root_part_number
$name
r
w
EOF
    else
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
p
$root_part_number
$root_start_sector
$root_end_sector
t
$root_part_number
$type
w
EOF
    fi
  fi

  partprobe ${disk}
}

create_HOME_partition()
{
  local disk=${1}

  local name="Linux filesystem"
  local guid="0fc63daf-8483-4772-8e79-3d69d8477de4"
  local type="83"

  local left=
  local octa=
  local swap=
  local GiB=1073741824
  local MiB=1048576

  let 'left = ( sectors - root_end_sector ) * unit_size'

  if [ "x${home_start_sector}" != "x" -a "${left}" -gt "$GiB" ] ; then

    let 'swap =  ram_bytes * 2 / alignment * alignment'

    if [ "${bytes}" -gt "${GiB}" ] ; then
      octa=`echo  "scale=0; $bytes / $GiB / 8 * $GiB" | bc`
    else
      octa=`echo  "scale=0; $bytes / $MiB / 8 * $MiB" | bc`
    fi

    let 'octa =  octa / alignment * alignment'

    if [ "${octa}" -gt "${swap}" ] ; then
      let 'left = ( left - swap ) / alignment * alignment'
      swap_bytes=${swap}
    elif [ "${octa}" -gt "${ram_bytes}" ] ; then
      let 'left = ( left - ram_bytes ) / alignment * alignment'
      swap_bytes=${ram_bytes}
    else
      swap_bytes=0
      swap_start_sector=0
    fi

    if [ "${swap_bytes}" -gt "0" ] ; then
      let 'home_end_sector = home_start_sector + ( left / unit_size - 1 )'
      let 'swap_start_sector = home_end_sector + 1'
    else
      let 'home_end_sector = sectors - 1'
    fi

    let 'home_bytes = ( home_end_sector - home_start_sector + 1 ) * unit_size'

    if [ "${partition_table_type}" = "g" ] ; then
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
$home_part_number
$home_start_sector
$home_end_sector
t
$home_part_number
$guid
x
n
$home_part_number
$name
r
w
EOF
    else
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
p
$home_part_number
$home_start_sector
$home_end_sector
t
$home_part_number
$type
w
EOF
    fi
  else
    home_bytes=0
    home_start_sector=0
    swap_bytes=0
    swap_start_sector=0
  fi

  partprobe ${disk}
}

create_SWAP_partition()
{
  local disk=${1}

  local name="Linux swap"
  local guid="0657fd6d-a4ab-43c4-84e5-0933c84b4f4f"
  local type="82"

  if [ "${swap_bytes}" -gt "0" ] ; then
    if [ "${partition_table_type}" = "g" ] ; then
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
$swap_part_number


t
$swap_part_number
$guid
x
n
$swap_part_number
$name
r
w
EOF
    else
      fdisk --wipe=always --wipe-partition=always ${disk} 1>/dev/null 2>/dev/null <<EOF
n
p
$swap_part_number


t
$swap_part_number
$type
w
EOF
    fi
  fi

  partprobe ${disk}
}

umount_target_partitions()
{
  local disk=${1}
  for dev in `mount | grep "^${disk}" | tr -s ' ' | cut -f1 -d' '` ; do
    umount ${dev} 2>/dev/null 1>/dev/null
  done
}

format_disk()
{
  local dev=${1}

  umount_target_partitions "${dev}"

  clean_disk "${dev}"
  if [ "x${uefi_bytes}" != "x" ] ; then
    create_EFI_partition "${dev}"
  fi

  create_ROOT_partition "${dev}"
  create_HOME_partition "${dev}"
  create_SWAP_partition "${dev}"
}

format_by_fdisk()
{
  local disk=${1}
  local fdiskprg=`which fdisk 2> /dev/null`

  umount_target_partitions "${disk}"

  clean_disk "${disk}"
  if [ "x${uefi_bytes}" != "x" ] ; then
    create_EFI_partition "${disk}"
  fi

  clear
  ${fdiskprg} ${disk}
  ret=$?
  if [ ${ret} -ne 0 ] ; then
    fatal_error_dialog "${fdiskprg} returns bad status. Exit ${program}."
    push_log "ERROR: ${fdiskprg} returns bad status"
    push_log "Aborted due to an error"
    push_err "ERROR: ${fdiskprg} returns bad status"
    EXITSTATUS=20
    exit
  fi

  partprobe ${disk}
}

ask_formatting()
{
  local disk=${1}

  local height=16
  local items=3

  local fdiskprg=`which fdisk 2> /dev/null`

  cat > $TMP/menu-format$$ << EOF
--colors --clear $nocancel \\
--backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \\
--title " \Z0Format the\Zn \Z4${disk}\Zn \Z0target device\Zn " \\
--menu "\\n\\
EOF

  cat >> $TMP/menu-format$$ << EOF
 The target disk should has at least one \Z1Linux\Zn partition for root\\n\\
 file system. Also you may want to have \Z1/home\Zn and \Z1swap\Zn partitions.\\n\\
EOF

  if [ "x${uefi_bytes}" != "x" ] ; then
    let 'height += 3'
    cat >> $TMP/menu-format$$ << EOF
\\n\\
 The target disk also should has \Z1EFI\Zn partition for boot the system.\\n\\
 The drive must be formated using \Z1G\ZnUID \Z1P\Znartition \Z1T\Znable (\Z1GPT\Zn).\\n\\
EOF
  fi

  cat >> $TMP/menu-format$$ << EOF
\\n\\
 \Z1NOTE\Zn: All data on the target \Z4${disk}\Zn device will be destroyed.\\
EOF

  cat >> $TMP/menu-format$$ << EOF
\\n\\n\\
 Please select method of formatting:\\
" ${height} 74 ${items} \\
EOF

  if [ "x${fdiskprg}" != "x" -a -x "${fdiskprg}" ] ; then
    cat >> $TMP/menu-format$$ << EOF
"Fdisk" "Use '\Zb${fdiskprg}\ZB' for formatting" \\
EOF
  fi

  cat >> $TMP/menu-format$$ << EOF
"Default" "Use default procedure for formatting" \\
EOF

  cat >> $TMP/menu-format$$ << EOF
"Exit" "Terminate the Radix cross Linux installation" \\
EOF

  $DIALOG --default-item "Default" --file $TMP/menu-format$$ 2> $TMP/format$$
  ret=$?
  if [ ${ret} -eq 1 -o ${ret} -eq 255 ]; then
    rm -f $TMP/format$$
    rm -f $TMP/menu-format$$
    return $ret
  fi
  result=`cat $TMP/format$$`
  rm -f $TMP/format$$
  rm -f $TMP/menu-format$$
  if [ "${result}" = "Exit" ]; then
    push_log "Done"
    exit
  elif [ "${result}" = "Fdisk" ]; then
    format_by_fdisk "${disk}"
  else
    format_disk "${disk}"
  fi
}

#
# End of Disk Format functions.
#
################################################################

################################################################
#
# Check Custom REPO functions:
#
welcome_custom_setup()
{
  cat > $TMP/welcome-setup-rc$$ << EOF
use_colors = ON
shadow_color = (BLACK,BLACK,OFF)
screen_color = (WHITE,BLACK,ON)
use_shadow = OFF
dialog_color = (WHITE,BLACK,OFF)
title_color = (WHITE,BLACK,ON)
border_color = (BLACK,BLACK,OFF)
border2_color = (BLACK,BLACK,OFF)
button_active_color = (WHITE,BLACK,ON)
button_inactive_color = (WHITE,BLACK,OFF)
button_key_active_color = (RED,BLACK,ON)
button_key_inactive_color = (WHITE,BLACK,ON)
button_label_active_color = (WHITE,BLACK,ON)
button_label_inactive_color = (WHITE,BLACK,ON)
EOF

  cat > $TMP/welcome-setup-help$$ << EOF

Version \Zb${version}\Zn
Copyright (c) 2009-`date +%Y`, Andrey V.Kosteltsev. All rights reserved.
${DISTRO_HOME_URL}

Built for: \Zb${hardware}\Zn
Toolchain: \Zb${toolchain}\Zn

Now you can install \Zb${DISTRO_CAPTION}-${version}\Zn from:

  ${repo}/

directory to you hard drive or internal flash.

Enjoy!

EOF

  DIALOGRC=$TMP/welcome-setup-rc$$ \
  $DIALOG --colors --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " Setup ${DISTRO_CAPTION} \Z1cross\Zn Linux " \
          --no-label " Exit Setup " \
          --yes-label " Continue " \
          --yesno "$(cat $TMP/welcome-setup-help$$)" 19 74
  ret=$?
  rm -f $TMP/welcome-setup-help$$
  if [ $ret -ne 0 ] ; then
    exit
  fi
}

ask_custom_repo()
{
  cat > $TMP/select-custom-repo$$ << EOF

 The selected custom REPO is invalid.
 Do you want to select Custom REPO to install from?

EOF

  $DIALOG --colors --defaultno --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Setup:\Zn \Z4\ZbSelect Custom Repository\ZB\Zn " \
          --no-label "Exit Setup" \
          --yes-label " Select " \
          --yesno "$(cat $TMP/select-custom-repo$$)" 9 74
  ret=$?
  rm -f $TMP/select-custom-repo$$
  if [ $ret -ne 0 ] ; then
    push_log "Done"
    exit
  fi
}

select_custom_repo()
{
  cat > $TMP/dselect-help$$ << EOF

  Use the space-bar to copy the current selection into the text-entry
  window. Press '/' and then Up Arrow to go to selected directoy.

EOF

  result=`$DIALOG --stdout  --colors \
                  --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
                  --title " \Z0\ZbSelect the\ZB\Zn \Z0\ZbCustom \Z1REPO\Zn \Z0\ZbDirectory (\ZB\Zn\Z4press F1 for help\Zn\Z0\Zb):\ZB\Zn " \
                  --hfile $TMP/dselect-help$$ \
                  --no-shadow \
                  --dselect ${repo} 7 74`
  ret=$?
  if [ $ret -eq 0 ]; then
    custom_repo="`echo ${result} | sed 's,/$,,'`"
  else
    custom_repo=no
    # continue with default REPO
  fi
}

check_custom_repo()
{
  rp="${1}"

  rp="`echo ${rp} | sed 's,/$,,'`"

  if ! `echo "${rp}" | grep -q "^/"` ; then
    ask_custom_repo
    select_custom_repo
    if [ "x${custom_repo}" != "xno" ] ; then
      check_custom_repo "${custom_repo}"
    else
      return
    fi
  fi

  if [ ! -d "${rp}" ] ; then
    ask_custom_repo
    select_custom_repo
    if [ "x${custom_repo}" != "xno" ] ; then
      check_custom_repo "${custom_repo}"
    else
      return
    fi
  fi

  local depth=`echo "${rp}" | grep -o '/' - | wc -l`
  if [ "${depth}" -lt "3" ] ; then
    ask_custom_repo
    select_custom_repo
    if [ "x${custom_repo}" != "xno" ] ; then
      check_custom_repo "${custom_repo}"
    else
      return
    fi
  fi

  local  d=`dirname  "${rp}"`
  local hw=`basename "${rp}"`
  local th=`basename "${d}"`
         d=`dirname  "${d}"`
  local  v=`basename "${d}"`

  if ! `echo ${v} | grep -q '^[0-9]*\.[0-9]*\.[0-9]*'` ; then
    ask_custom_repo
    select_custom_repo
    if [ "x${custom_repo}" != "xno" ] ; then
      check_custom_repo "${custom_repo}"
    else
      return
    fi
  fi

  if [ ! -r "${rp}/${hw}.pkglist" ] ; then
    ask_custom_repo
    select_custom_repo
    if [ "x${custom_repo}" != "xno" ] ; then
      check_custom_repo "${custom_repo}"
    else
      return
    fi
  elif [ ! -L "${rp}/.pkglist" ] ; then
    ( cd "${rp}" ; ln -sf ${hw}.pkglist .pkglist )
  fi

  version=$v
  toolchain=$th
  hardware=$hw
  repo=${rp}

  custom_repo=yes
}

#
# End of Check Custom REPO functions.
#
################################################################

################################################################
#
# Check Source REPO functions:
#
check_repo()
{
  local rp="${1}"

  if [ ! -d "${rp}" ] ; then
    return 1
  fi

  if [ ! -r "${rp}/${HARDWARE}.pkglist" ] ; then
    return 1
  elif [ ! -L "${rp}/.pkglist" ] ; then
    ( cd "${rp}" ; ln -sf ${HARDWARE}.pkglist .pkglist )
  fi

  return 0
}
#
# End of Check Source REPO functions.
#
################################################################

################################################################
#
# Check Target device functions:
#
major_number()
{
  local part=${1}
  local name=`basename ${part}`

  local major=`ls -l /dev | grep -v ^l | grep ${name} | tr -s ' ' | sed 's/,//g' | cut -f5 -d' ' | sort -u | tr '\n' ',' | sed 's/,$//'`
  echo "${major}"
}

#
# returns the prefix 'p' of partition number if applicable
#
part_prefix()
{
  local dev=${1}
  if `echo ${dev: -1} | grep -q '[0-1]'` ; then
    p=p
  fi
}

check_current_device()
{
  current_device=`${WHERE} -n -o disk`
  current_root=`${WHERE} -n -o root`
  pline=`LANG=en_US.UTF-8 fdisk -l --bytes ${current_device} | grep "^${current_root}" | tr -s ' '`
  active=`echo "${pline}" | cut -f2 -d' '`
  if [ "${partition_table_type}" = "o" ] ; then
    if [ "${active}" = "*" ] ; then
      rootfs_min_bytes=`echo "${pline}" | cut -f6 -d' '`
    fi
  else
    rootfs_min_bytes=`echo "${pline}" | cut -f5 -d' '`
  fi
}

ask_target_device()
{
  cat > $TMP/select-target-device$$ << EOF

 Target device is not selected or invalid.
 Do you want to select Target Device to install?

EOF

  $DIALOG --colors --defaultno --clear \
          --backtitle "\Z7${DISTRO_CAPTION}\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Setup:\Zn \Z4\ZbSelect Target Device\ZB\Zn " \
          --no-label "Exit Setup" \
          --yes-label " Select " \
          --yesno "$(cat $TMP/select-target-device$$)" 9 74
  ret=$?
  rm -f $TMP/select-target-device$$
  if [ $ret -ne 0 ] ; then
    push_log "Done"
    exit
  fi
}

select_target_device()
{
  cat > $TMP/device-help$$ << EOF
--colors --clear \\
--backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \\
--title " \Z0\ZbSelect the destination\ZB\Zn " \\
--menu "\\n\\
 If the desired device is not displayed in the following list,\\n\\
 please insert the disk and repeat installation.\\n\\
\\n\\
 Please select the target device:\\
" 14 74 3 \\
EOF

  for dev in `lsblk -ldn -o name` ; do
    #
    # Skip 'ram.*', 'zram.*', 'mtd.*', 'mmcblk[0-9]*boot.*':
    #
    if `echo ${dev} | grep -q 'ram.*\|zram.*\|mtd.*\|mmcblk[0-9]*boot.*'` ; then
      continue
    fi
    #
    # Exclude current device:
    #
    local sfound=`echo "${current_device}" | grep "/dev/${dev}"`
    if [ "x${sfound}" = "x" ] ; then
      echo "\"/dev/$dev\" \" \" \\" >> $TMP/device-help$$
    fi
  done

  ${DIALOG} --file $TMP/device-help$$ 2> $TMP/devmame$$
  ret=$?
  if [ $ret -eq 1 -o $ret -eq 255 ]; then
    rm -f $TMP/devmame$$
    rm -f $TMP/device-help$$
    # continue: see check_target_device()
  fi
  result=`cat $TMP/devmame$$`
  rm -f $TMP/devmame$$
  rm -f $TMP/device-help$$

  device=$result
}

check_target_device()
{
  while [ "x${device}" = "x" -o "x${device}" = "x${current_device}" ] ; do
    ask_target_device
    select_target_device
  done

  if [ -b "${device}" ] ; then
    local base=`basename ${device}`
    local mjrs=`major_number ${device}`
    local line="`lsblk -I ${mjrs} -l -o name,type | grep \"${base} \" | tr -s ' ' | head -n 1`"
    if [ "$line" != "" ] ; then
      local name=`echo "${line}" | tr -s ' ' | cut -f1 -d' '`
      local type=`echo "${line}" | tr -s ' ' | cut -f2 -d' '`
      if [ "${base}" = "${name}" -a "${type}" != "disk" -a "${type}" != "loop" ] ; then
        push_log "ERROR: The DEVICE (${device}) is not a physical disk"
        device=
        check_target_device
      fi
    else
      push_log "ERROR: The DEVICE ($device) not found"
      device=
      check_target_device
    fi
  else
    push_log "ERROR: The DEVICE ($device) not a block device"
    device=
    check_target_device
  fi

  part_prefix ${device}
  disk_geometry ${device}
}
#
# End of Check Target device functions.
#
################################################################

################################################################
#
# Partitions functions.
#
make_ext2() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1ext2\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.ext2 -q -F -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.ext2 -q -F ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_ext3() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1ext3\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.ext3 -q -F -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.ext3 -q -F ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_ext4() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1ext4\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.ext4 -q -F -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.ext4 -q -F ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_vfat() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1vfat\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.fat -F 32 -n "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.fat -F 32 ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_btrfs() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1btrfs\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.btrfs -d single -m single -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.btrfs -d single -m single ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_jfs() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1jfs\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.jfs -q -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.jfs -q ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_xfs() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1xfs\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkfs.xfs -q -f -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkfs.xfs -q -f ${pname} 1>/dev/null 2>/dev/null
  fi
}

make_swap() {
  local  pname=${1}
  local plabel=${2}

  local psize=`get_partition_size ${pname}`
  let "psize = psize / 1024"

  $DIALOG --colors \
          --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
          --title " \Z0Formatting\Zn \Z4\Zb$pname\ZB\Zn " \
          --infobox "\n Formatting \Z1${pname}\ZB\Zn\n\n\
 Size in 1K blocks: \Z4${psize}\Zn\n\
   Filesystem type: \Z1swap\Zn\n" 8 74
  if `mount | grep -q "^${pname} " 1>/dev/null 2>/dev/null` ; then
    umount ${pname} 2>/dev/null
  fi
  if [ "x${plabel}" != "x" ] ; then
    mkswap -v1 -L "${plabel}" ${pname} 1>/dev/null 2>/dev/null
  else
    mkswap -v1 ${pname} 1>/dev/null 2>/dev/null
  fi
}

partlist=$TMP/plist.$$
partitems=$TMP/pitems.$$

gen_parts_list()
{
  local disk=${1}
  local devname=`echo ${disk} | sed -e 's,^/dev/,,'`

  if [ "${partition_table_type}" = "g" ] ; then
    uefi_id="EFI System"
    linux_id="Linux filesystem"
    swap_id="Linux swap"
  else
    uefi_id="ef"
    linux_id="83"
    swap_id="82"
  fi

  truncate -s0 $partlist

  local first_uefi= ; local first_root= ; local first_home=

  local plist=`LANG=en_US.UTF-8 lsblk -lb -o name,size,type,fstype,mountpoint | grep ${devname} | tr -s ' '`
  echo -e "${plist}" | while read -r line ; do
    words=`echo "${line}" | wc -w`

    pname= ; psize= ; ptype= ; fstype= ; mpoint= ; partuuid= ; uuid=

    pname=`echo "${line}" | cut -f1 -d ' '`
    if [ ${words} -ge 2 ] ; then
      psize=`echo "${line}" | cut -f2 -d ' '`
    fi
    if [ ${words} -ge 3 ] ; then
      ptype=`echo "${line}" | cut -f3 -d ' '`
      if [ "${ptype}" != "part" ] ; then
        continue
      fi
    fi
    if [ ${words} -ge 4 ] ; then
      fstype=`echo "${line}" | cut -f4 -d ' '`
    fi
    if [ ${words} -ge 5 ] ; then
      mpoint=`echo "${line}" | cut -f5 -d ' '`
    fi

    #
    # recomended values:
    #
    used=
    # skip active partition sign [asterisk '*']
    local pline=`LANG=en_US.UTF-8 fdisk -l /dev/${devname} | grep "^/dev/${pname}" | tr -s ' '`
    active=`echo "${pline}" | cut -f2 -d' '`
    if [ "${partition_table_type}" = "g" ] ; then
      partid=`echo "${pline}" | cut -f6,7 -d' '`
    else
      if [ "${active}" = "*" ] ; then
        partid=`echo "${pline}" | cut -f7 -d' '`
      else
        partid=`echo "${pline}" | cut -f6 -d' '`
      fi
    fi

    if [ "${partid}" = "${swap_id}" ] ; then
      mpoint="swap"
      fstype="swap"
    fi
    if [ "x${first_uefi}" = "x" ] ; then
      if [ "${partid}" = "${uefi_id}" ] ; then
        first_boot="/dev/${pname}"
        mpoint="/boot/efi"
        fstype="vfat"
        used="use"
      fi
    fi
    if [ "x${first_root}" = "x" ] ; then
      if [ "${partid}" = "${linux_id}" ] ; then
        first_root="/dev/${pname}"
        mpoint="/"
        fstype="ext4"
      fi
    fi
    if [ "x${first_root}" != "x" -a "x${first_home}" = "x" ] ; then
      if [ "${partid}" = "${linux_id}" ] ; then
         if [ "${first_root}" != "/dev/${pname}" ] ; then
           first_home="/dev/${pname}"
           mpoint="/home"
           fstype="ext4"
        fi
      fi
    fi

    echo "/dev/${pname}:${psize}:${fstype}:${mpoint}:${used}:${partuuid}:${uuid}" | tr -s ' ' >> ${partlist}
  done
}

gen_parts_menu_items()
{
  local disk=${1}
  local devname=`echo ${disk} | sed -e 's,^/dev/,,'`

  local first_uefi= ; local first_root= ; local first_home=

  truncate -s0 $partitems

  cat "$partlist" | while read -r line ; do
    pname= ; psize= ; ptype= ; fstype= ; mpoint=

    pname=`echo "$line" | cut -f1 -d':'`

    #
    # get partition type (skipping active partition sign [asterisk '*']):
    #
    pline=`LANG=en_US.UTF-8 fdisk -l ${disk} | grep "^${pname}" | tr -s ' '`
    active=`echo "${pline}" | cut -f2 -d' '`
    if [ "${partition_table_type}" = "g" ] ; then
      ptype=`echo "${pline}" | cut -f6,7 -d' '`
    else
      if [ "${active}" = "*" ] ; then
        ptype=`echo "${pline}" | cut -f7 -d' '`
      else
        ptype=`echo "${pline}" | cut -f6 -d' '`
      fi
    fi

    if [ "${partition_table_type}" = "g" ] ; then
      if [ "${ptype}" = "EFI System" ] ; then
        ptype="ef"
      fi
      if [ "${ptype}" = "Linux filesystem" ] ; then
        ptype="83"
      fi
      if [ "${ptype}" = "Linux swap" ] ; then
        ptype="82"
      fi
    fi

    ptype=`printf ' %02s ' "${ptype}"`

    psize=`echo "${line}" | cut -f2 -d':'`
    let "psize = psize / 1048576"
    psize=`printf '%6d' $psize`

    fstype=`echo "${line}" | cut -f3 -d':'`
    fstype=`printf '%-8s' "${fstype}"`

    mpoint=`echo "${line}" | cut -f4 -d':'`

    used=`echo "${line}" | cut -f5 -d':'`
    if [ "${used}" == "use" ] ; then
      fstype="\\Z4${fstype}\\Zn"
      mpoint="\\Z4${mpoint}\\Zn"
    fi
    echo "\"${pname}\" \"${psize}M ${ptype} ${fstype} ${mpoint}\" \\" | sed -e 's,\s\+$,,g' >> ${partitems}
  done
}

get_partition_size()
{
  local dev=${1}
  local psize=`cat ${partlist} | grep "^${dev}" | cut -f2 -d':'`
  echo -n "${psize}"
}

get_recomended_fstype()
{
  local dev=${1}
  local fstype=`cat ${partlist} | grep "^${dev}" | cut -f3 -d':'`
  echo -n "${fstype}"
}

set_recomended_fstype() {
  local dev=${1}
  local fstype=${2}
  local   name=`echo ${dev} | sed -e 's,/dev/,,'`
  local  psize=`cat ${partlist} | grep "^${dev}" | cut -f2 -d':'`
  local mpoint=`cat ${partlist} | grep "^${dev}" | cut -f4 -d':'`
  local  puuid=`cat ${partlist} | grep "^${dev}" | cut -f6 -d':'`
  local   uuid=`cat ${partlist} | grep "^${dev}" | cut -f7 -d':'`
  sed -i "/${name}/c\/dev/${name}:${psize}:${fstype}:${mpoint}:use:${puuid}:${uuid}" ${partlist}
}

get_recomended_mpoint()
{
  local dev=${1}
  local mpoint=`cat ${partlist} | grep "^${dev}" | cut -f4 -d':'`
  echo -n "${mpoint}"
}

set_recomended_mpoint()
{
  local dev=${1}
  local mpoint=${2}
  local   name=`echo ${dev} | sed -e 's,/dev/,,'`
  local  psize=`cat ${partlist} | grep "^${dev}" | cut -f2 -d':'`
  local fstype=`cat ${partlist} | grep "^${dev}" | cut -f3 -d':'`
  local  puuid=`cat ${partlist} | grep "^${dev}" | cut -f6 -d':'`
  local   uuid=`cat ${partlist} | grep "^${dev}" | cut -f7 -d':'`
  sed -i "/${name}/c\/dev/${name}:${psize}:${fstype}:${mpoint}:use:${puuid}:${uuid}" ${partlist}
}

get_rootfs_devname()
{
  cat "${partlist}" | while read -r line ; do
    pname= ; fstype= ; mpoint=

     pname=`echo "${line}" | cut -f1 -d':'`
    fstype=`echo "${line}" | cut -f3 -d':'`
    mpoint=`echo "${line}" | cut -f4 -d':'`

    if [ "${mpoint}" = "/" ] ; then
      echo -n "${pname}"
      break
    fi
  done
}

get_uefi_devname()
{
  cat "${partlist}" | while read -r line ; do
    pname= ; fstype= ; mpoint=

     pname=`echo "${line}" | cut -f1 -d':'`
    fstype=`echo "${line}" | cut -f3 -d':'`
    mpoint=`echo "${line}" | cut -f4 -d':'`

    if [ "${mpoint}" = "/boot/efi" ] ; then
      echo -n "${pname}"
      break
    fi
  done
}

get_part_uuid()
{
  local dev=${1}
  local puuid=`cat ${partlist} | grep "^${dev}" | cut -f6 -d':'`
  echo -n "${puuid}"
}

set_part_uuid()
{
  local dev=${1}
  local  puuid=${2}
  local   name=`echo ${dev} | sed -e 's,/dev/,,'`
  local  psize=`cat ${partlist} | grep "^${dev}" | cut -f2 -d':'`
  local fstype=`cat ${partlist} | grep "^${dev}" | cut -f3 -d':'`
  local mpoint=`cat ${partlist} | grep "^${dev}" | cut -f4 -d':'`
  local   used=`cat ${partlist} | grep "^${dev}" | cut -f5 -d':'`
  local   uuid=`cat ${partlist} | grep "^${dev}" | cut -f7 -d':'`
  sed -i "/${name}/c\/dev/${name}:${psize}:${fstype}:${mpoint}:${used}:${puuid}:${uuid}" ${partlist}
}

get_uuid()
{
  local dev=${1}
  local uuid=`cat ${partlist} | grep "^${dev}" | cut -f7 -d':'`
  echo -n "${uuid}"
}

set_uuid()
{
  local dev=${1}
  local   uuid=${2}
  local   name=`echo ${dev} | sed -e 's,/dev/,,'`
  local  psize=`cat ${partlist} | grep "^${dev}" | cut -f2 -d':'`
  local fstype=`cat ${partlist} | grep "^${dev}" | cut -f3 -d':'`
  local mpoint=`cat ${partlist} | grep "^${dev}" | cut -f4 -d':'`
  local   used=`cat ${partlist} | grep "^${dev}" | cut -f5 -d':'`
  local  puuid=`cat ${partlist} | grep "^${dev}" | cut -f6 -d':'`
  sed -i "/${name}/c\/dev/${name}:${psize}:${fstype}:${mpoint}:${used}:${puuid}:${uuid}" ${partlist}
}

create_file_system()
{
  local  pname=${1}
  local fstype=${2}
  local plabel=

  mpoint=`get_recomended_mpoint ${pname}`
  if [ "${mpoint}" = "/" ] ; then
    plabel="root"
  fi
  if [ "${mpoint}" == "/home" ] ; then
    plabel="home"
  fi

  cat > $TMP/partlabel-help$$ << EOF

 Please specify the volume label for file system
 on the \Z1${pname}\Zn partition.

 Set the volume label or leave following field blank:
EOF

  result=`$DIALOG --stdout  --colors \
                  --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
                  --title " \Z0Select Volume Label\Zn " \
                  --inputbox "$(cat $TMP/partlabel-help$$)" 12 74 "${plabel}"`
  ret=$?
  rm -f $TMP/partlabel-help$$
  if [ ${ret} -eq 0 ]; then
    plabel="${result}"
  fi

  case "${fstype}" in
    ext2 )
      make_ext2 "${pname}" "${plabel}"
      ;;
    ext3 )
      make_ext3 "${pname}" "${plabel}"
      ;;
    ext4 )
      make_ext4 "${pname}" "${plabel}"
      ;;
    vfat )
      make_vfat "${pname}" "${plabel}"
      ;;
    btrfs )
      make_btrfs "${pname}" "${plabel}"
      ;;
    * )
      ;;
  esac

  set_recomended_fstype "${pname}" "${fstype}"
}

set_mount_point()
{
  local pname=${1}
  local mpoint=${2}

  cat > $TMP/mountpoint-help$$ << EOF

 Please specify the mount directory of the \Z1${pname}\Zn partition.

 Set the mount directory:
EOF

  result=`$DIALOG --stdout  --colors \
                  --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
                  --title " \Z0Select Mount Point for\Zn \Z4${pname}\Zn " \
                  --inputbox "$(cat $TMP/mountpoint-help$$)" 11 74 "${mpoint}"`
  ret=$?
  rm -f $TMP/mountpoint-help$$
  if [ ${ret} -eq 0 ]; then
    mpoint="${result}"
  fi
  set_recomended_mpoint "${pname}" "${mpoint}"
}

format_partition()
{
  local pname=${1}

  local fstype=`get_recomended_fstype ${pname}`
  local mpoint=`get_recomended_mpoint ${pname}`

  if [ "${fstype}" == "swap" ] ; then
    cat > $TMP/mountpoint-help$$ << EOF

 Radix Setup will now prepare your system's \Z1swap\Zn space.

 Would you like to format \Z1${pname}\Zn using \Z4mkswap\Zn ?
EOF

    result=`$DIALOG --stdout  --colors \
                    --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
                    --title " \Z0Format Swap Partition\Zn \Z4${pname}\Zn " \
                    --yes-label " OK " \
                    --yesno "$(cat $TMP/mountpoint-help$$)" 9 74`
    ret=$?
    rm -f $TMP/mountpoint-help$$
    if [ ${ret} -eq 0 ]; then
      make_swap ${pname} swap
    else
      return
    fi
    set_recomended_fstype "${pname}" "swap"
    set_recomended_mpoint "${pname}" "swap"
    return
  else
    unset EXT2 EXT3 EXT4 REISERFS BTRFS VFAT JFS XFS
    if grep -wq ext2 /proc/filesystems 1>/dev/null 2>/dev/null ; then
      EXT2="Ext2 is the traditional Linux file system and is fast and stable."
    fi
    if grep -wq ext3 /proc/filesystems 1>/dev/null 2>/dev/null ; then
      EXT3="Ext3 is the journaling version of the Ext2 filesystem."
    fi
    if grep -wq ext4 /proc/filesystems 1>/dev/null 2>/dev/null ; then
      EXT4="Ext4 is the successor to the ext3 filesystem."
    fi
    if grep -wq btrfs /proc/filesystems 1>/dev/null 2>/dev/null ; then
      BTRFS="Btrfs is a B-tree copy-on-write filesystem."
    fi
    if grep -wq vfat /proc/filesystems 1>/dev/null 2>/dev/null ; then
      VFAT="VFAT is a updated version of the FAT filesystem for Windows. VFAT's updates are mainly support for longer file names."
    fi
    if grep -wq jfs /proc/filesystems 1>/dev/null 2>/dev/null ; then
      JFS="JFS is IBM's Journaled Filesystem, currently used in IBM enterprise servers."
    fi
    if grep -wq xfs /proc/filesystems 1>/dev/null 2>/dev/null ; then
      XFS="XFS is SGI's journaling filesystem that originated on IRIX."
    fi

    cat > $TMP/filesystem-help$$ << EOF
--colors --default-item "${fstype}" \\
--backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \\
--title " \Z0Select File System for\Zn \Z4${pname}\Zn " \\
--menu "\\n\\
 Please select the type of filesystem to use for the specified device\\n\\
 or hit <\Z1\ZbC\ZB\Zn\Zbancel\ZB> to leave existed filesystem. \\
\\n\\n\\
 Here are descriptions of the available filesystems:\\
" 15 74 4 \\
EOF

    if [ "x${EXT2}" != "x" ]; then
      echo "\"ext2\" \"Standard Linux Ext2 Filesystem\" \\" >> $TMP/filesystem-help$$
    fi
    if [ "x${EXT3}" != "x" ]; then
      echo "\"ext3\" \"Ext3 Journaling Filesystem\" \\" >> $TMP/filesystem-help$$
    fi
    if [ "x${EXT4}" != "x" ]; then
      echo "\"ext4\" \"Ext4 Journaling Filesystem\" \\" >> $TMP/filesystem-help$$
    fi
    if [ "x${VFAT}" != "x" ]; then
      echo "\"vfat\" \"VFAT updated version of the FAT filesystem\" \\" >> $TMP/filesystem-help$$
    fi
    if [ "x${BTRFS}" != "x" ]; then
      echo "\"btrfs\" \"Btrfs Copy-on-Write B-tree Filesystem\" \\" >> $TMP/filesystem-help$$
    fi

    $DIALOG --file $TMP/filesystem-help$$ 2> $TMP/filesystem$$
    ret=$?
    result=`cat $TMP/filesystem$$`
    rm -f $TMP/filesystem$$
    rm -f $TMP/filesystem-help$$
    if [ ${ret} -eq 0 ]; then
      fstype=${result}

      # Create File System:
      create_file_system "${pname}" "${fstype}"

      # Set Mount Point:
      set_mount_point "${pname}" "${mpoint}"
    else
      # Leave existed file system:
      set_recomended_fstype "${pname}" "${fstype}"
      # Set Mount Point:
      set_mount_point "${pname}" "${mpoint}"
    fi
  fi
}

prepare_partitions()
{
  local disk=${1}

  if [ "x${disk}" = "x" ] ; then
    return 255
  fi

  local items=4
  local height=21

  gen_parts_list "${disk}"

  while [ 0 ] ; do
    cat > $TMP/menu-format$$ << EOF
--colors --clear --cancel-label "Continue" \\
--backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \\
--title " \Z0Create File Systems and Select\Zn \Z0Mountpoints\Zn " \\
--menu "\\n\\
EOF

    cat >> $TMP/menu-format$$ << EOF
 The target disk has fillowing partitions. Each menu item show the\\n\\
 device name, size in MiB, and type of existing partition. Last two\\n\\
 columns may shows recomended filesystem and mount point for the\\n\\
 target system. Now you can create filesystem on each existing\\n\\
 partitions (if needed) and choose or confirm mount point.\\n\\n\\
 Already changed values will be shown in \Z4\ZbBlue\ZB\Zn (0x0000FF) color.\\
EOF

    cat >> $TMP/menu-format$$ << EOF
\\n\\n\\
 Please select each of partitions listed below,\\n\\
 or if you're done, hit <Continue>:\\
" $height 73 $items \\
EOF

    gen_parts_menu_items "${disk}"

    cat "${partitems}" >> $TMP/menu-format$$

    $DIALOG --file $TMP/menu-format$$ 2> $TMP/format$$
    ret=$?
    if [ ${ret} -eq 1 -o ${ret} -eq 255 ]; then
      rm -f $TMP/format$$
      rm -f $TMP/menu-format$$
      # continue the installation
      return ${ret}
    fi
    local pname=`cat $TMP/format$$`
    rm -f $TMP/format$$
    rm -f $TMP/menu-format$$

    format_partition "${pname}"
  done
}

partitions_loop()
{
  local disk=${1}

  while [ 0 ] ; do
    prepare_partitions "${disk}"
    ret=$?
    if [ ${ret} -eq 255 ]; then
      # User can interrupt format partitions cycle by press Esc button
      # on keyboard. In this case we have to exit setup because we not
      # sure that user done all needs.  If user say Esc again, then we
      # will return him back to the cycle until user press <Continue>.
      ask_exit_setup
      continue
    fi
    if [ ${ret} -eq 1 ]; then
      break
    fi
  done
}

check_partitions()
{
  local disk=${1}

  local has_uefi=
  local has_linux=
  local retvalue=0

  if [ "${partition_table_type}" = "g" ] ; then
    if [ "x${uefi_bytes}" != "x" ] ; then
      has_uefi=`LANG=en_US.UTF-8 fdisk -l ${disk} | tr -s ' ' | grep "^${disk}.* EFI System"`
      if [ "x${has_uefi}" = "x" ] ; then
        retvalue=1
      fi
    fi
    has_linux=`LANG=en_US.UTF-8 fdisk -l ${disk} | tr -s ' '  | grep "^${disk}.* Linux filesystem"`
    if [ "x${has_linux}" = "x" ] ; then
      retvalue=2
    fi
  else
    if [ "x${uefi_bytes}" != "x" ] ; then
      has_uefi=`LANG=en_US.UTF-8 fdisk -l ${disk} | tr -s ' '  | grep "^${disk}.* ef .*"`
      if [ "x${has_uefi}" = "x" ] ; then
        retvalue=1
      fi
    fi
    has_linux=`LANG=en_US.UTF-8 fdisk -l ${disk} | tr -s ' '  | grep "^${disk}.* 83 .*"`
    if [ "x${has_linux}" = "x" ] ; then
      retvalue=2
    fi
  fi

  if [ "${retvalue}" -eq "1" ] ; then
    error_dialog "Target device must have \Z1EFI\Zn partition."
    ask_formatting "${disk}"
  fi
  if [ "${retvalue}" -eq "2" ] ; then
    error_dialog "Target device must have at least one \Z1Linux\Zn partition."
    ask_formatting "${disk}"
  fi
}

check_filesystems()
{
  cat "${partlist}" | while read -r line ; do
    pname= ; fstype= ; mpoint=

     pname=`echo "${line}" | cut -f1 -d':'`
    fstype=`echo "${line}" | cut -f3 -d':'`
    mpoint=`echo "${line}" | cut -f4 -d':'`
      used=`echo "${line}" | cut -f5 -d':'`

    if [ "${used}" = "use" ] ; then
      if [ "${mpoint}" = "/" ] ; then
        name=`echo ${pname} | sed -e 's,/dev/,,'`
        PARTUUID=`LANG=en_US.UTF-8 lsblk -ln -o name,partuuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
            UUID=`LANG=en_US.UTF-8 lsblk -ln -o name,uuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
        set_part_uuid "${pname}" "${PARTUUID}"
             set_uuid "${pname}" "${UUID}"
      elif [ "${mpoint}" = "/home" ] ; then
        name=`echo ${pname} | sed -e 's,/dev/,,'`
        PARTUUID=`LANG=en_US.UTF-8 lsblk -ln -o name,partuuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
            UUID=`LANG=en_US.UTF-8 lsblk -ln -o name,uuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
        set_part_uuid "${pname}" "${PARTUUID}"
             set_uuid "${pname}" "${UUID}"
      elif [ "${fstype}" = "vfat" -a "${mpoint}" = "/boot/efi" ] ; then
        name=`echo ${pname} | sed -e 's,/dev/,,'`
        PARTUUID=`LANG=en_US.UTF-8 lsblk -ln -o name,partuuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
            UUID=`LANG=en_US.UTF-8 lsblk -ln -o name,uuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
        set_part_uuid "${pname}" "${PARTUUID}"
             set_uuid "${pname}" "${UUID}"
      elif [ "${fstype}" = "swap" ] ; then
        name=`echo ${pname} | sed -e 's,/dev/,,'`
        PARTUUID=`LANG=en_US.UTF-8 lsblk -ln -o name,partuuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
            UUID=`LANG=en_US.UTF-8 lsblk -ln -o name,uuid | grep "^${name}" | tr -s ' ' | cut -f2 -d' '`
        set_part_uuid "${pname}" "${PARTUUID}"
             set_uuid "${pname}" "${UUID}"
      fi
    fi
  done
}
#
# End of Partitions functions.
#
################################################################

####################################################################
#
# prepare /etc/fstab - create temporary /etc/fstab according to
#                      the table of formated partitions.
#
fstab=$TMP/fstab.$$

prepare_dev_etc_fstab() {
  cat > $fstab << EOF
#
# /etc/fstab
#
# --------------+----------------+-----------+------------------------------------+------+------
#        device | mount point    | FS type   | options                            | dump | pass
# --------------+----------------+-----------+------------------------------------+------+------

EOF

  cat "${partlist}" | while read -r line ; do
    pname= ; fstype= ; mpoint= ; dump= ; pass=

     pname=`echo "${line}" | cut -f1 -d':'`
    fstype=`echo "${line}" | cut -f3 -d':'`
    mpoint=`echo "${line}" | cut -f4 -d':'`
      used=`echo "${line}" | cut -f5 -d':'`

    if [ "${used}" = "use" ] ; then
      if [ "${mpoint}" = "/" ] ; then
        dump=1 ; pass=1
      elif [ "${mpoint}" = "/home" ] ; then
        dump=1 ; pass=2
      elif [ "${fstype}" = "vfat" -a "${mpoint}" = "/boot/efi" ] ; then
        dump=1 ; pass=0
      elif [ "${mpoint}" = "swap" ] ; then
        dump=0 ; pass=0
      else
        dump=1 ; pass=2
      fi
      printf "%-16s %-16s %-11s %-36s %-6s %s\n" "${pname}" "${mpoint}" "${fstype}" "defaults" "${dump}" "${pass}" >> ${fstab}
    fi
  done
  echo "" >> ${fstab}
  printf "%-16s %-16s %-11s %-36s %-6s %s\n" "devpts" "/dev/pts" "devpts" "gid=5,mode=620"      "0" "0" >> ${fstab}
  printf "%-16s %-16s %-11s %-36s %-6s %s\n" "proc"   "/proc"    "proc"   "defaults"            "0" "0" >> ${fstab}
  printf "%-16s %-16s %-11s %-36s %-6s %s\n" "tmpfs"  "/dev/shm" "tmpfs"  "nosuid,nodev,noexec" "0" "0" >> ${fstab}

  cat >> ${fstab} << EOF

# --------------+----------------+-----------+------------------------------------+------+------
EOF
}

prepare_uuid_etc_fstab() {
  cat > $fstab << EOF
#
# /etc/fstab
#
# ----------------------------------------+----------------+-----------+------------------------------------+------+------
#                  device                 | mount point    | FS type   | options                            | dump | pass
# ----------------------------------------+----------------+-----------+------------------------------------+------+------

EOF

  cat "${partlist}" | while read -r line ; do
    pname= ; fstype= ; mpoint= ; dump= ; pass=

     pname=`echo "${line}" | cut -f1 -d':'`
    fstype=`echo "${line}" | cut -f3 -d':'`
    mpoint=`echo "${line}" | cut -f4 -d':'`
      used=`echo "${line}" | cut -f5 -d':'`
      uuid=`echo "${line}" | cut -f7 -d':'`

    if [ "${used}" = "use" ] ; then
      if [ "${mpoint}" = "/" ] ; then
        dump=1 ; pass=1
      elif [ "${mpoint}" = "/home" ] ; then
        dump=1 ; pass=2
      elif [ "${fstype}" = "vfat" -a "${mpoint}" = "/boot/efi" ] ; then
        dump=1 ; pass=0
      elif [ "${mpoint}" = "swap" ] ; then
        dump=0 ; pass=0
      else
        dump=1 ; pass=2
      fi
      printf "%-42s %-16s %-11s %-36s %-6s %s\n" "UUID=${uuid}" "${mpoint}" "${fstype}" "defaults" "${dump}" "${pass}" >> ${fstab}
    fi
  done
  echo "" >> ${fstab}
  printf "%-42s %-16s %-11s %-36s %-6s %s\n" "devpts" "/dev/pts" "devpts" "gid=5,mode=620"      "0" "0" >> ${fstab}
  printf "%-42s %-16s %-11s %-36s %-6s %s\n" "proc"   "/proc"    "proc"   "defaults"            "0" "0" >> ${fstab}
  printf "%-42s %-16s %-11s %-36s %-6s %s\n" "tmpfs"  "/dev/shm" "tmpfs"  "nosuid,nodev,noexec" "0" "0" >> ${fstab}

  cat >> ${fstab} << EOF

# ----------------------------------------+----------------+-----------+------------------------------------+------+------
EOF
}

prepare_partuuid_etc_fstab() {
  if [ "${partition_table_type}" = "g" ] ; then
    local dlen=46
    cat > $fstab << EOF
#
# /etc/fstab
#
# --------------------------------------------+----------------+-----------+------------------------------------+------+------
#                    device                   | mount point    | FS type   | options                            | dump | pass
# --------------------------------------------+----------------+-----------+------------------------------------+------+------

EOF
  else
    local dlen=21
    cat > $fstab << EOF
#
# /etc/fstab
#
# -------------------+----------------+-----------+------------------------------------+------+------
#             device | mount point    | FS type   | options                            | dump | pass
# -------------------+----------------+-----------+------------------------------------+------+------

EOF
  fi

  cat "${partlist}" | while read -r line ; do
    pname= ; fstype= ; mpoint= ; dump= ; pass=

     pname=`echo "${line}" | cut -f1 -d':'`
    fstype=`echo "${line}" | cut -f3 -d':'`
    mpoint=`echo "${line}" | cut -f4 -d':'`
      used=`echo "${line}" | cut -f5 -d':'`
     puuid=`echo "${line}" | cut -f6 -d':'`

    if [ "${used}" = "use" ] ; then
      if [ "${mpoint}" = "/" ] ; then
        dump=1 ; pass=1
      elif [ "${mpoint}" = "/home" ] ; then
        dump=1 ; pass=2
      elif [ "${fstype}" = "vfat" -a "${mpoint}" = "/boot/efi" ] ; then
        dump=1 ; pass=0
      elif [ "${mpoint}" = "swap" ] ; then
        dump=0 ; pass=0
      else
        dump=1 ; pass=2
      fi
      printf "%-${dlen}s %-16s %-11s %-36s %-6s %s\n" "PARTUUID=${puuid}" "${mpoint}" "${fstype}" "defaults" "${dump}" "${pass}" >> ${fstab}
    fi
  done
  echo "" >> ${fstab}
  printf "%-${dlen}s %-16s %-11s %-36s %-6s %s\n" "devpts" "/dev/pts" "devpts" "gid=5,mode=620"      "0" "0" >> ${fstab}
  printf "%-${dlen}s %-16s %-11s %-36s %-6s %s\n" "proc"   "/proc"    "proc"   "defaults"            "0" "0" >> ${fstab}
  printf "%-${dlen}s %-16s %-11s %-36s %-6s %s\n" "tmpfs"  "/dev/shm" "tmpfs"  "nosuid,nodev,noexec" "0" "0" >> ${fstab}

  if [ "${partition_table_type}" = "g" ] ; then
    cat >> ${fstab} << EOF

# --------------------------------------------+----------------+-----------+------------------------------------+------+------
EOF
  else
    cat >> ${fstab} << EOF

# -------------------+----------------+-----------+------------------------------------+------+------
EOF
  fi
}
#
# End of prepare /etc/fstab functions.
#
####################################################################

####################################################################
#
# prepare /boot/grub/grub.cfg - create temporary
#                               /boot/grub/grub.cfg according to
#                               the table of formated partitions.
#
grub_cfg=$TMP/grub.cfg.$$
grub_load_cfg=$TMP/grub.load.cfg.$$
grub_core_img=$TMP/grub.core.img.$$

prepare_grub_config()
{
  local root_uuid=`cat "${partlist}" | grep ':/:' | cut -f7 -d':'`
  local root_partuuid=`cat "${partlist}" | grep ':/:' | cut -f6 -d':'`

  cat > ${grub_cfg} << EOF

set menu_color_normal=black/light-gray
set menu_color_highlight=white/light-gray
set background_color=black

set timeout=5

EOF

  if [ "${hardware}" = "baikal-m1"  -o \
       "${hardware}" = "orange-pi5" -o \
       "${hardware}" = "visionfive2" ] ; then
    cat >> ${grub_cfg} << EOF
font '/boot/grub/fonts/dejavusansmono.pf2'
EOF
  fi

  cat >> ${grub_cfg} << EOF
loadfont dejavusansmono

menuentry 'Radix cross Linux' {
  set root_uuid=${root_uuid}
  set part_uuid=${root_partuuid}

  insmod gzio
  insmod xzio
EOF

  if [ "${hardware}" = "intel-pc32" ] ; then
    cat >> ${grub_cfg} << EOF
  insmod part_msdos
EOF
  fi

  cat >> ${grub_cfg} << EOF
  insmod part_gpt
  insmod ext2

  search --set=root --fs-uuid \$root_uuid
EOF

  if [ "${hardware}" = "ebox-3350dx2" -o \
       "${hardware}" = "intel-pc32"   -o \
       "${hardware}" = "intel-pc64" ] ; then
    cat >> ${grub_cfg} << EOF
  linux (\$root)/boot/vmlinuz root=PARTUUID=\$part_uuid ro rootwait console=tty0
EOF
  fi

  if [ "${hardware}" = "baikal-m1" ] ; then
    cat >> ${grub_cfg} << EOF
  devicetree (\$root)/boot/bm1000-mbm20.dtb
  linux (\$root)/boot/Image root=PARTUUID=\$part_uuid ro rootwait console=tty1 earlyprintk=uart8250-32bit,0x20230000,115200
EOF
  fi

  if [ "${hardware}" = "orange-pi5" ] ; then
    cat >> ${grub_cfg} << EOF
  devicetree (\$root)/boot/rockchip/rk3588s-orangepi-5.dtb
  linux (\$root)/boot/Image root=PARTUUID=\$part_uuid ro rootwait console=ttyS2,1500000n8 console=tty1
EOF
  fi

  if [ "${hardware}" = "visionfive2" ] ; then
    cat >> ${grub_cfg} << EOF
  devicetree (\$root)/boot/starfive/jh7110-visionfive-v2.dtb
  linux (\$root)/boot/Image root=PARTUUID=\$part_uuid ro rootwait console=ttyS0,115200n8 earlycon=sbi console=tty1
EOF
  fi

  cat >> ${grub_cfg} << EOF
}
EOF
}

prepare_grub_load_config()
{
  local root_uuid=`cat "${partlist}" | grep ':/:' | cut -f7 -d':'`

  cat > ${grub_load_cfg} << EOF

set color_normal=black/black

set pager=1
search.fs_uuid ${root_uuid} root
set prefix=(\$root)/boot/grub

set color_normal=light-gray/black
clear
EOF
}
#
# End of prepare /boot/grub/grub.cfg functions.
#
####################################################################

####################################################################
#
# Install packages:
#
errlist=$TMP/errlist.$$

ROOT=
ROOT_MPOINT=

install_packages()
{
  ROOT=`get_rootfs_devname`
  ROOT_MPOINT=$MNT/root

  if [ "x${ROOT}" = "x" ] ; then
    fatal_error_dialog "Cannot mount ROOT partition. Exit ${program}."
    push_log "ERROR: Cannot mount ROOT partition"
    push_log "Aborted due to an error"
    push_err "ERROR: Cannot mount ROOT partition"
    EXITSTATUS=21
    exit
  fi

  if `mount | grep -q ${ROOT}` ; then
    umount ${ROOT}
  fi
  mkdir -p ${ROOT_MPOINT}
  if [ "x`mount | grep ${ROOT_MPOINT}`" != "x" ] ; then
    umount ${ROOT_MPOINT}
  fi
  mount ${ROOT} ${ROOT_MPOINT}

  TMP=/tmp install-pkglist --errlist --info-dialog --priority all --root=${ROOT_MPOINT}/ ${repo} 2>${errlist}

  mkdir -p ${ROOT_MPOINT}/etc
  cat ${fstab} > ${ROOT_MPOINT}/etc/fstab

  if [ "${hardware}" = "baikal-m1"    -o \
       "${hardware}" = "orange-pi5"   -o \
       "${hardware}" = "visionfive2"  -o \
       "${hardware}" = "ebox-3350dx2" -o \
       "${hardware}" = "intel-pc32"   -o \
       "${hardware}" = "intel-pc64" ] ; then
    mkdir -p ${ROOT_MPOINT}/boot/grub
    cat ${grub_cfg} > ${ROOT_MPOINT}/boot/grub/grub.cfg
  fi
}
#
# End of install packages.
#
####################################################################

####################################################################
#
# Set EFI boot entry:
#
set_efiboot_entry() {
  local uefi=${1}
  local loader="${2}"

  local devlen=${#device}
  local partlen=

  let 'partlen = devlen + 1'
  if [ "${#p}" -gt "0" ] ; then
    let 'plen++'
  fi

  local uefi_device=
  local uefi_partition=

  modprobe efivarfs 1> /dev/null 2> /dev/null

  if [ ! -d '/sys/firmware/efi/efivars' ] ; then return ; fi
  if [ -z "${uefi}" -o -z "${loader}" ] ; then return ; fi

  uefi_device=$(echo "${uefi}" | cut -b 1-${devlen})
  uefi_partition=$(echo "${uefi}" | cut -b ${partlen}- | sed 's/[^0-9]*//g')

  #
  # Remove the previous boot entry if set:
  #
  efibootmgr -v | rev | cut -f2- | rev | grep Boot0 | grep "${DISTRO_CAPTION}" | while read line ; do
    if ! $(echo ${line} | cut -f2- -d' ' | grep -q "${DISTRO_CAPTION}") ; then
      continue
    fi
    efibootmgr -q -B -b $(echo ${line} | cut -b5-8)
    sleep 1
  done

  #
  # Set boot entry:
  #
  efibootmgr -q -c -d ${uefi_device} -p ${uefi_partition} -l "${loader}" -L "${DISTRO_CAPTION}-${DISTRO_FULL_VERSION}"
}
#
# End of set EFI boot entry.
#
####################################################################

####################################################################
#
# Install GRUB:
#
UEFI=
UEFI_MPOINT=

install_baikal_m1_grub()
{
  UEFI=`get_uefi_devname`
  UEFI_MPOINT=$MNT/UEFI

  if [ "x${UEFI}" = "x" ] ; then
    fatal_error_dialog "Cannot mount EFI partition. Exit ${program}."
    push_log "ERROR: Cannot mount EFI partition"
    push_log "Aborted due to an error"
    push_err "ERROR: Cannot mount EFI partition"
    EXITSTATUS=22
    exit
  fi

  if `mount | grep -q ${UEFI}` ; then
    umount ${UEFI}
  fi
  mkdir -p ${UEFI_MPOINT}
  if [ "x`mount | grep ${UEFI_MPOINT}`" != "x" ] ; then
    umount ${UEFI_MPOINT}
  fi
  mount ${UEFI} ${UEFI_MPOINT}

  local grub_modules="all_video archelp bfs bitmap bitmap_scale blocklist boot btrfs"
  grub_modules="${grub_modules} cat chain configfile cpio date datehook datetime disk diskfilter"
  grub_modules="${grub_modules} echo efi_gop efifwsetup efinet elf eval exfat ext2 extcmd f2fs fat"
  grub_modules="${grub_modules} fdt file font fshelp gettext gfxmenu gfxterm gfxterm_background"
  grub_modules="${grub_modules} gfxterm_menu gptsync gzio halt hashsum help hexdump iso9660 jpeg"
  grub_modules="${grub_modules} json keystatus linux loadenv loopback ls lsefi lzopio mdraid1x"
  grub_modules="${grub_modules} memdisk minicmd msdospart net newc normal part_gpt part_msdos"
  grub_modules="${grub_modules} png probe procfs read reboot regexp reiserfs search search_fs_file"
  grub_modules="${grub_modules} search_fs_uuid search_label serial squash4 tar terminal terminfo"
  grub_modules="${grub_modules} test tftp time tr trig true udf ufs1 ufs2 video video_colors"
  grub_modules="${grub_modules} video_fb videoinfo xzio zstd"

  /usr/sbin/grub-install --skip-fs-probe \
                         --fonts=dejavusansmono \
                         --boot-directory=${ROOT_MPOINT}/boot \
                         --directory=/usr/lib/grub/arm64-efi \
                         --target=arm64-efi --no-efi \
                         --no-bootsector --no-nvram  2>/dev/null 1>/dev/null

  mkdir -p ${ROOT_MPOINT}/boot/efi
  mkdir -p ${ROOT_MPOINT}/boot/grub/arm64-efi
  cat ${grub_load_cfg} > ${ROOT_MPOINT}/boot/grub/arm64-efi/load.cfg

  mkdir -p ${UEFI_MPOINT}/efi/boot
  /usr/bin/grub-mkimage --format=arm64-efi \
                        --directory=/usr/lib/grub/arm64-efi \
                        --compression=xz \
                        --prefix=/efi/boot \
                        --config="${grub_load_cfg}" \
                        --output=${UEFI_MPOINT}/efi/boot/bootaa64.efi \
                        ${grub_modules}  2>/dev/null 1>/dev/null
}

install_orange_pi5_grub()
{
  UEFI=`get_uefi_devname`
  UEFI_MPOINT=$MNT/UEFI

  if [ "x${UEFI}" = "x" ] ; then
    fatal_error_dialog "Cannot mount EFI partition. Exit ${program}."
    push_log "ERROR: Cannot mount EFI partition"
    push_log "Aborted due to an error"
    push_err "ERROR: Cannot mount EFI partition"
    EXITSTATUS=22
    exit
  fi

  if `mount | grep -q ${UEFI}` ; then
    umount ${UEFI}
  fi
  mkdir -p ${UEFI_MPOINT}
  if [ "x`mount | grep ${UEFI_MPOINT}`" != "x" ] ; then
    umount ${UEFI_MPOINT}
  fi
  mount ${UEFI} ${UEFI_MPOINT}

  local grub_modules="all_video archelp bfs bitmap bitmap_scale blocklist boot btrfs"
  grub_modules="${grub_modules} cat chain configfile cpio date datehook datetime disk diskfilter"
  grub_modules="${grub_modules} echo efi_gop efifwsetup efinet elf eval exfat ext2 extcmd f2fs fat"
  grub_modules="${grub_modules} fdt file font fshelp gettext gfxmenu gfxterm gfxterm_background"
  grub_modules="${grub_modules} gfxterm_menu gptsync gzio halt hashsum help hexdump iso9660 jpeg"
  grub_modules="${grub_modules} json keystatus linux loadenv loopback ls lsefi lzopio mdraid1x"
  grub_modules="${grub_modules} memdisk minicmd msdospart net newc normal part_gpt part_msdos"
  grub_modules="${grub_modules} png probe procfs read reboot regexp reiserfs search search_fs_file"
  grub_modules="${grub_modules} search_fs_uuid search_label serial squash4 tar terminal terminfo"
  grub_modules="${grub_modules} test tftp time tr trig true udf ufs1 ufs2 video video_colors"
  grub_modules="${grub_modules} video_fb videoinfo xzio zstd"

  /usr/sbin/grub-install --skip-fs-probe \
                         --fonts=dejavusansmono \
                         --boot-directory=${ROOT_MPOINT}/boot \
                         --directory=/usr/lib/grub/arm64-efi \
                         --target=arm64-efi --no-efi \
                         --no-bootsector --no-nvram  2>/dev/null 1>/dev/null

  mkdir -p ${ROOT_MPOINT}/boot/efi
  mkdir -p ${ROOT_MPOINT}/boot/grub/arm64-efi
  cat ${grub_load_cfg} > ${ROOT_MPOINT}/boot/grub/arm64-efi/load.cfg

  mkdir -p ${UEFI_MPOINT}/efi/boot
  /usr/bin/grub-mkimage --format=arm64-efi \
                        --directory=/usr/lib/grub/arm64-efi \
                        --compression=xz \
                        --prefix=/efi/boot \
                        --config="${grub_load_cfg}" \
                        --output=${UEFI_MPOINT}/efi/boot/bootaa64.efi \
                        ${grub_modules}  2>/dev/null 1>/dev/null
}

install_orange_pi5_edk2() {
  FLASHCP=`PATH=/sbin:/usr/sbin:$PATH which flashcp`
  if [ -c /dev/mtd0 -a "`basename ${FLASHCP}`" = "flashcp" -a -f "/boot/edk2/spi-flash.image" ] ; then
    ${FLASHCP} /boot/edk2/spi-flash.image /dev/mtd0
  fi
}

install_starfive_vf2_grub()
{
  UEFI=`get_uefi_devname`
  UEFI_MPOINT=$MNT/UEFI

  if [ "x${UEFI}" = "x" ] ; then
    fatal_error_dialog "Cannot mount EFI partition. Exit ${program}."
    push_log "ERROR: Cannot mount EFI partition"
    push_log "Aborted due to an error"
    push_err "ERROR: Cannot mount EFI partition"
    EXITSTATUS=22
    exit
  fi

  if `mount | grep -q ${UEFI}` ; then
    umount ${UEFI}
  fi
  mkdir -p ${UEFI_MPOINT}
  if [ "x`mount | grep ${UEFI_MPOINT}`" != "x" ] ; then
    umount ${UEFI_MPOINT}
  fi
  mount ${UEFI} ${UEFI_MPOINT}

  local grub_modules="all_video archelp bfs bitmap bitmap_scale blocklist boot btrfs"
  grub_modules="${grub_modules} cat chain configfile cpio date datehook datetime disk diskfilter"
  grub_modules="${grub_modules} echo efi_gop efifwsetup efinet elf eval exfat ext2 extcmd f2fs fat"
  grub_modules="${grub_modules} fdt file font fshelp gettext gfxmenu gfxterm gfxterm_background"
  grub_modules="${grub_modules} gfxterm_menu gptsync gzio halt hashsum help hexdump iso9660 jpeg"
  grub_modules="${grub_modules} json keystatus linux loadenv loopback ls lsefi lzopio mdraid1x"
  grub_modules="${grub_modules} memdisk minicmd msdospart net newc normal part_gpt part_msdos"
  grub_modules="${grub_modules} png probe procfs read reboot regexp reiserfs search search_fs_file"
  grub_modules="${grub_modules} search_fs_uuid search_label serial squash4 tar terminal terminfo"
  grub_modules="${grub_modules} test tftp time tr trig true udf ufs1 ufs2 video video_colors"
  grub_modules="${grub_modules} video_fb videoinfo xzio zstd"

  /usr/sbin/grub-install --skip-fs-probe \
                         --fonts=dejavusansmono \
                         --boot-directory=${ROOT_MPOINT}/boot \
                         --directory=/usr/lib/grub/riscv64-efi \
                         --target=riscv64-efi --no-efi \
                         --no-bootsector --no-nvram  2>/dev/null 1>/dev/null

  mkdir -p ${ROOT_MPOINT}/boot/efi
  mkdir -p ${ROOT_MPOINT}/boot/grub/riscv64-efi
  cat ${grub_load_cfg} > ${ROOT_MPOINT}/boot/grub/riscv64-efi/load.cfg

  mkdir -p ${UEFI_MPOINT}/efi/boot
  /usr/bin/grub-mkimage --format=riscv64-efi \
                        --directory=/usr/lib/grub/riscv64-efi \
                        --compression=xz \
                        --prefix=/efi/boot \
                        --config="${grub_load_cfg}" \
                        --output=${UEFI_MPOINT}/efi/boot/bootriscv64.efi \
                        ${grub_modules}  2>/dev/null 1>/dev/null
}

install_intel_pc64_grub()
{
  UEFI=`get_uefi_devname`
  UEFI_MPOINT=$MNT/UEFI

  if [ "x${UEFI}" = "x" ] ; then
    fatal_error_dialog "Cannot mount EFI partition. Exit ${program}."
    push_log "ERROR: Cannot mount EFI partition"
    push_log "Aborted due to an error"
    push_err "ERROR: Cannot mount EFI partition"
    EXITSTATUS=22
    exit
  fi

  if `mount | grep -q ${UEFI}` ; then
    umount ${UEFI}
  fi
  mkdir -p ${UEFI_MPOINT}
  if [ "x`mount | grep ${UEFI_MPOINT}`" != "x" ] ; then
    umount ${UEFI_MPOINT}
  fi
  mount ${UEFI} ${UEFI_MPOINT}

  local grub_modules="part_gpt part_msdos fat f2fs ext2 hfs hfsplus iso9660 udf ufs1 ufs2 chain linux"
  grub_modules="${grub_modules} boot appleldr configfile normal regexp minicmd reboot halt search search_fs_file"
  grub_modules="${grub_modules} search_fs_uuid search_label gfxterm gfxmenu efi_gop efi_uga all_video loadbios"
  grub_modules="${grub_modules} gzio echo true probe loadenv bitmap_scale font cat help ls png jpeg tga test"
  grub_modules="${grub_modules} at_keyboard usb_keyboard zstd"

  /usr/sbin/grub-install --skip-fs-probe \
                         --fonts=dejavusansmono \
                         --boot-directory=${ROOT_MPOINT}/boot \
                         --directory=/usr/lib/grub/x86_64-efi \
                         --target=x86_64-efi --no-efi \
                         --no-bootsector --no-nvram  2>/dev/null 1>/dev/null

  mkdir -p ${ROOT_MPOINT}/boot/efi
  mkdir -p ${ROOT_MPOINT}/boot/grub/x86_64-efi
  cat ${grub_load_cfg} > ${ROOT_MPOINT}/boot/grub/x86_64-efi/load.cfg

  mkdir -p ${UEFI_MPOINT}/efi/boot
  /usr/bin/grub-mkimage --format=x86_64-efi \
                        --directory=/usr/lib/grub/x86_64-efi \
                        --compression=xz \
                        --prefix=/efi/boot \
                        --config="${grub_load_cfg}" \
                        --output=${UEFI_MPOINT}/efi/boot/bootx64.efi \
                        ${grub_modules}  2>/dev/null 1>/dev/null

  set_efiboot_entry "${UEFI}" "\\efi\\boot\\bootx64.efi"
}

install_intel_pc32_grub()
{
  local disk=${1}

  local grub_modules="part_gpt part_msdos fat f2fs ext2 hfs hfsplus iso9660 udf ufs1 ufs2 chain linux"
  grub_modules="${grub_modules} boot biosdisk configfile normal regexp minicmd reboot halt search search_fs_file"
  grub_modules="${grub_modules} search_fs_uuid search_label gfxterm gfxmenu all_video gzio echo true probe loadenv"
  grub_modules="${grub_modules} bitmap_scale font cat help ls png jpeg tga test at_keyboard usb_keyboard zstd"

  /usr/sbin/grub-install --skip-fs-probe \
                         --fonts=dejavusansmono \
                         --boot-directory=${ROOT_MPOINT}/boot \
                         --directory=/usr/lib/grub/i386-pc \
                         --target=i386-pc \
                         --modules="${grub_modules}" \
                         --disk-module=biosdisk \
                         ${disk}  2>/dev/null 1>/dev/null

  mkdir -p ${ROOT_MPOINT}/boot/grub/i386-pc
  cat ${grub_load_cfg} > ${ROOT_MPOINT}/boot/grub/i386-pc/load.cfg

  /usr/bin/grub-mkimage --format=i386-pc \
                        --directory=/usr/lib/grub/i386-pc \
                        --prefix=/boot/grub \
                        --config="${grub_load_cfg}" \
                        --output=${grub_core_img} \
                        ${grub_modules}  2>/dev/null 1>/dev/null

  dd if=${grub_core_img} of=${disk} obs=512 seek=1 conv=notrunc  2>/dev/null 1>/dev/null
}

install_ebox_3350dx2_grub()
{
  local disk=${1}

  local grub_modules="part_gpt part_msdos fat f2fs ext2 hfs hfsplus iso9660 udf ufs1 ufs2 chain linux"
  grub_modules="${grub_modules} boot biosdisk configfile normal regexp minicmd reboot halt search search_fs_file"
  grub_modules="${grub_modules} search_fs_uuid search_label gfxterm gfxmenu all_video gzio echo true probe loadenv"
  grub_modules="${grub_modules} bitmap_scale font cat help ls png jpeg tga test at_keyboard usb_keyboard zstd"

  /usr/sbin/grub-install --skip-fs-probe \
                         --fonts=dejavusansmono \
                         --boot-directory=${ROOT_MPOINT}/boot \
                         --directory=/usr/lib/grub/i386-pc \
                         --target=i386-pc \
                         --modules="${grub_modules}" \
                         --disk-module=biosdisk \
                         ${disk}  2>/dev/null 1>/dev/null

  mkdir -p ${ROOT_MPOINT}/boot/grub/i386-pc
  cat ${grub_load_cfg} > ${ROOT_MPOINT}/boot/grub/i386-pc/load.cfg

  /usr/bin/grub-mkimage --format=i386-pc \
                        --directory=/usr/lib/grub/i386-pc \
                        --prefix=/boot/grub \
                        --config="${grub_load_cfg}" \
                        --output=${grub_core_img} \
                        ${grub_modules}  2>/dev/null 1>/dev/null

  dd if=${grub_core_img} of=${disk} obs=512 seek=1 conv=notrunc  2>/dev/null 1>/dev/null
}
#
# End of install GRUB:
#
####################################################################

####################################################################
#
# Install U-Boot:
#
install_leez_p710_uboot()
{
  local disk=${1}

  dd if=${ROOT_MPOINT}/boot/u-boot/idbloader.img of=${disk} bs=512 seek=64     2>/dev/null 2>/dev/null
  dd if=${ROOT_MPOINT}/boot/u-boot/u-boot.itb    of=${disk} bs=512 seek=16384  2>/dev/null 2>/dev/null

  ln -sfr ${ROOT_MPOINT}/boot/boot.emmc.scr ${ROOT_MPOINT}/boot/boot.scr
}
#
# End of install U-Boot.
#
####################################################################

####################################################################
#
# Select Desktop Environment:
#
select_desktop_environment()
{
  local height=10
  local items=0

  cat > $TMP/select-desktop-envitonment$$ << EOF
--colors --clear $nocancel \\
--backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \\
--title " \Z0Select Desktop Environment\Zn " \\
--menu "\\n\\
EOF


  cat >> $TMP/select-desktop-envitonment$$ << EOF
\\n\\
 Please select your preferred Desktop Environment:\\
" ${height} 74 ${items} \\
EOF

  #
  # Currently we have only 'OpenBox' and 'Mate' Environments:
  #
  for session in `ls ${ROOT_MPOINT}/etc/X11/xinit/xinitrc.*-session` ; do
    case ${session} in
      *openbox*)
        let 'items += 1'
        let 'height += 1'
        cat >> $TMP/select-desktop-envitonment$$ << EOF
"OpenBox" "- Lightweight window manager for X Window" \\
EOF
       ;;
      *mate*)
        let 'items += 1'
        let 'height += 1'
        cat >> $TMP/select-desktop-envitonment$$ << EOF
"MATE" "- MATE Desktop Environment (based on GNOME 2)" \\
EOF
       ;;
    esac
  done

  $DIALOG --default-item "OpenBox" --file $TMP/select-desktop-envitonment$$ 2> $TMP/desktop$$
  ret=$?
  if [ ${ret} -eq 255 ]; then
    rm -f $TMP/desktopt$$
    rm -f $TMP/select-desktop-envitonment$$
    result="OpenBox"
  else
    result=`cat $TMP/desktop$$`
  fi
  rm -f $TMP/desktop$$
  rm -f $TMP/select-desktop-envitonment$$
  if [ "${result}" = "MATE" ]; then
    ln -srf ${ROOT_MPOINT}/etc/X11/xinit/xinitrc.mate-session ${ROOT_MPOINT}/etc/X11/xinit/xinitrc
  else
    ln -srf ${ROOT_MPOINT}/etc/X11/xinit/xinitrc.openbox-session ${ROOT_MPOINT}/etc/X11/xinit/xinitrc
  fi
}
#
# End of Select Desktop Environment.
#
####################################################################


#
# Parse Options:
#
while [ 0 ]; do
  if [ "$1" = "-h" -o "$1" = "--help" ] ; then
    usage
    exit
  elif [ "$1" = "-r" -o "$1" = "--root-dev" ]; then
    if [ "$2" = "" ]; then
      usage
      push_log "ERROR: Target DEVICE has not specified by --root-dev option"
      push_log "Aborted due to an error"
      push_err "ERROR: Target DEVICE has not specified by --root-dev option"
      EXITSTATUS=16
      exit
    fi
    device="`echo $2 | sed 's,/$,,'`"
    shift 2
  elif [ "$1" = "--repo" ]; then
    if [ "$2" = "" ]; then
      usage
      push_log "ERROR: Custom REPO directory has not specified by --repo option"
      push_err "ERROR: Custom REPO directory has not specified by --repo option"
      EXITSTATUS=18
      exit
    fi
    custom_repo="$2"
    if ! `echo ${custom_repo: -1} | grep -q '/'` ; then
      custom_repo="${custom_repo}/"
    fi
    shift 2
  else
    break
  fi
done

if [ "x${custom_repo}" != "xno" ] ; then
  check_custom_repo "${custom_repo}"
else
  check_repo "${repo}"
  ret=$?
  if [ $ret -ne 0 ] ; then
    fatal_error_dialog "Source REPO directory is invalid. Exit ${program}."
    push_log "ERROR: Source REPO directory is invalid"
    push_log "Aborted due to an error"
    push_err "ERROR: Source REPO directory is invalid"
    EXITSTATUS=17
    exit
  fi
fi

#
# Show DISTRO spec:
# ----------------
#
if [ "x${custom_repo}" != "xyes" ] ; then
  welcome_setup
else
  welcome_custom_setup
fi

check_current_device
check_target_device

#
# Ask for format target device:
# ----------------------------
#
ask_formatting "${device}"
blockdev -q --rereadpt "${device}"

#
# File Systems:
# ------------
#
check_partitions "${device}"
partitions_loop "${device}"
$DIALOG --colors \
        --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
        --title " \Z0Install Packages\Zn " \
        --infobox "\n Please wait for packages installation.\n\n" 5 74
check_filesystems

#
# /etc/fstab:
# ----------
#
if [ "${hardware}" = "baikal-m1"   -o \
     "${hardware}" = "orange-pi5"  -o \
     "${hardware}" = "visionfive2" -o \
     "${hardware}" = "intel-pc64" ] ; then
  prepare_partuuid_etc_fstab
else
  prepare_uuid_etc_fstab
  #prepare_dev_etc_fstab
fi

#
# /boot/grub/grub.cfg:
# -------------------
#
if [ "${hardware}" = "baikal-m1"    -o \
     "${hardware}" = "orange-pi5"   -o \
     "${hardware}" = "visionfive2"  -o \
     "${hardware}" = "ebox-3350dx2" -o \
     "${hardware}" = "intel-pc32"   -o \
     "${hardware}" = "intel-pc64" ] ; then
  prepare_grub_config
  prepare_grub_load_config
fi

#
# Install all packages:
# --------------------
#
install_packages

#
# Install GRUB:
# ------------
#
if [ "${hardware}" = "baikal-m1" ] ; then
  install_baikal_m1_grub
fi
if [ "${hardware}" = "orange-pi5" ] ; then
  install_orange_pi5_grub
fi
if [ "${hardware}" = "visionfive2" ] ; then
  install_starfive_vf2_grub
fi
if [ "${hardware}" = "intel-pc64" ] ; then
  install_intel_pc64_grub
fi
if [ "${hardware}" = "intel-pc32" ] ; then
  install_intel_pc32_grub "${device}"
fi
if [ "${hardware}" = "ebox-3350dx2" ] ; then
  install_ebox_3350dx2_grub "${device}"
fi

#
# Install U-Boot:
# --------------
#
if [ "${hardware}" = "leez-p710" ] ; then
  install_leez_p710_uboot "${device}"
fi

#
# Install EDK2:
# ------------
#
if [ "${hardware}" = "orange-pi5" ] ; then
  install_orange_pi5_edk2
fi

#
# post-install settings:
#
if [ -x ${ROOT_MPOINT}/usr/sbin/timeconfig ] ; then
  ${ROOT_MPOINT}/usr/sbin/timeconfig --root ${ROOT_MPOINT}
fi

#
# Select Desktop Environment:
#
enabled=$(echo "`ls /etc/X11/xinit/xinitrc.*-session`" | wc -l)
if [ ${enabled} -gt 1 ] ; then
  select_desktop_environment
fi

$DIALOG --colors --clear \
        --backtitle "\Z7Radix\Zn \Z1cross\Zn\Z7 Linux\Zn" \
        --title " \Z0System Installation is Complete\Zn " \
        --msgbox "\nSetup is complete. Please set \Z1root\Zn password at first login.\n" 7 74

exit