#!/bin/bash
# Author: Steven Shiau <steven _at_ nchc org tw>
# License: GPL
# Description: This script will create a GParted live CD/USB flash drive iso/zip

#
set -e

#
DRBL_SCRIPT_PATH="${DRBL_SCRIPT_PATH:-/usr/share/drbl}"
. $DRBL_SCRIPT_PATH/sbin/drbl-conf-functions
. /etc/drbl/drbl-ocs.conf
. $DRBL_SCRIPT_PATH/sbin/ocs-functions

# debian_mirror_url_def, debian_mirror_security_url_def, DRBL_REPOSITORY_URL_def and DRBL_GPG_KEY_URL are loaded from drbl-ocs.conf

# debian_type can be minimal (about 67 MB for Etch)/minimal-net (about 85 MB for Etch).
# Since from live-build 3.0~a55 "minimal" for debootstrap was removed. We use the option --variant of "debootstrap", i.e. "minbase" for minimal.
debian_type="minbase"
DEBIAN_DIST_DEF="wheezy"
# Do not assign any Xorg packges except xorg here. Let the Debian dependence decide that.
#Xorg_pkgs="xserver-xorg xfonts-base xserver-xorg-video-all xserver-xorg-input-mouse xserver-xorg-input-kbd xserver-xorg-input-evdev xserver-xorg-input-all-"
Xorg_pkgs="xorg"
# Some Asian fonts, like Chinese, Japan... (/NOTE/ Big size... about 5 - 10 MB)
#font_pkgs="x-ttcidfont-conf fonts-arphic-uming"
font_pkgs="fonts-arphic-uming ttf-kochi-gothic"
# $debian_pkgs_for_gparted is from drbl.conf
# Use dhcp*-client$ for dhcp3-client, dhcp-client, and isc-dhcp-client (yes, debian will select 'dhcp-client' for regex 'dhcp*-client', then select 'isc-dhcp-client' for regex 'dhcp*-client'. With "$" in the end means we do not want "isc-dhcp-client-dbg"
pkgs="console-data console-setup console-common kbd file eject user-setup grub-pc fluxbox idesk deborphan man testdisk mc less lxterminal zenity xbase-clients feh netpbm nano bogl-bterm xresprobe mdetect lxrandr sdparm hdparm discover lsscsi pciutils ifupdown dhcp*-client$ cryptsetup gpart smartmontools vim-tiny gdisk fsarchiver mdadm dmraid sudo hicolor-icon-theme netbase ssh pppoeconf ethtool whiptail lshw cpufrequtils open-iscsi tree cifs-utils nilfs-tools netsurf gptsync net-tools pcmanfm leafpad tcplay f2fs-tools partimage $debian_pkgs_for_gparted $Xorg_pkgs $font_pkgs"
categories_default="main"
cpu_flavor_default="486"
bootstrap_default="debootstrap"

# The files in dir in $ocs_live_include_dir will be included to the live-hook-dir/. Here we need some functions in ocs/live-hook so we include files in that dir.
ocs_live_include_dir="$DRBL_SCRIPT_PATH/setup/files/ocs/live-hook $DRBL_SCRIPT_PATH/setup/files/gparted/live-hook"
# The files in dir $ocs_live_script_dir will be copied to the /live-hook-dir/ in dir chroot, and $ocs_live_script_dir/$run_hook_script will be hooked and run
ocs_live_script_dir="$DRBL_SCRIPT_PATH/setup/files/gparted/live-hook"
# The script inside $ocs_live_script_dir will be run when chroot. Maybe there are many files in $ocs_live_script_dir, we will just run one here.
run_hook_script="gparted-live-hook"
# background image of syslinux/isolinux for gparted live
gparted_live_boot_bg_img="$DRBL_SCRIPT_PATH/setup/files/gparted/image/Gsplash.png"

#
vga_mode_gparted_live="normal"
# This hook is for binary_local-hooks, not for chroot hook
run_binary_hook_script="efi-binary-hook"
# The option to create a corresponding source image.
gen_source_tarball="no"
# Flag to put EFI booting image in iso
enabled_EFI=""

#
check_if_root
#
prog="$(basename $0)"
full_cmd="$prog $*"

# functions
USAGE() {
    echo "Usage:"
    echo "To create a GParted live CD iso or USB flash drive zip:"
    echo "$prog [OPTION]"
    echo "OPTION:"
    language_help_prompt_by_idx_no
    echo "-b, --branch [s|stable|t|testing|u|unstable|e|experimental]  Sepcify the DRBL branch to be used in Live CD. Default is stable."
    echo "-bt, --bootstrap BOOTSTRAP  Specify the bootsrap type as BOOTSTRAP (cdebootstrap or debootstrap). If not specified, $bootstrap_default will be used."
    echo "-c, --categories CAT   Sepcify the category, e.g. 'main', 'main non-free', default is \'$categories_default\' if not specified."
    echo "-d, --debian-dist [stable|testing|unstable|lenny|squeeze|wheezy|sid...]  Assign Debian dist, the default is $DEBIAN_DIST_DEF if not assigned."
    echo "-f, --arch-flavor ARCH  Assign the CPU architecture flavor as ARCH, e.g. 486, 686 or amd64. If it's not assigned, $cpu_flavor_default will be used."
    echo "-g, --drbl-repo-url URL  Assign the DRBL repository URL instead of default one $DRBL_REPOSITORY_URL_def."
    echo "-n, --live-kernel-pkg KERNEL_VER Assign kernel version as KERNEL_VER (KERNEL VER package must exist in repository. Ex. if KERNEL_VER is 2.6.20-1-486, then linux-image-2.6.20-1-486, squashfs-modules-2.6.20-1-486, and unionfs-modules-2.6.20-1-486 will be used."
    echo "-i, --assign-version-no NO  Assign the version no as NO instead of date."
    echo "-e, --drbl-live-branch [s|stable|t|testing|u|unstable|e|experimental]  specifies the DRBL live branch to be used in Live CD. Default is stable."
    echo "-k, --package FILE  Specifies FILE to be installed in Live CD."
    echo "-p, --packages-list FILE  specifies an external package list file (such as xfce, gnome, kde...), one package for each line"
    echo "-m, --mirror-url URL  Assign the Debian repository URL instead of default one $debian_mirror_url_def. "
    echo "-r, --rm-tmp-iso    Remove the first stage temp iso file"
    echo "-s, --mirror-security-url URL  Assign the Debian security repository URL instead of default one $debian_mirror_security_url_def."
    echo "-o, --create-source-tarball  Create a corresponding source image to the binary image.  By default such an source image will not be created since this would require to download quite a few source packages."
    echo "-t, --target-media-file  [cd|iso|usb|zip|b|both] Assign the target media file as CD (cd or iso), USB flash drive (usb or zip) or both of them (b or both). Default is both"
    echo "-u, --use-existing-tmp-iso  Use the existing first stage temp iso file"
    echo "-x, --extra-boot-param  EXTRA_PARAM  Assign extra boot parameter EXTRA_PARAM for clonezilla live kernel to read. These parameters are the same with that from live-initramfs. Ex. \"noprompt\" can be use to not prompt to eject the CD on reboot."
    echo "-v, --verbose    Run live build in verbose mode"
    echo "Ex: $0 -l en -b u -e e -n 2.6.24-etchnhalf.1"
}
#
clean_tmp_dirs_files() {
  [ -d "$stage1_iso_TMP" -a -n "$(echo $stage1_iso_TMP | grep "ocs-iso-tmp")" ] && rm -rf $stage1_iso_TMP
  [ -d "$ISOSYSLNX_TMP" -a -n "$(echo $ISOSYSLNX_TMP | grep "isolnx-tmp")" ] && rm -rf $ISOSYSLNX_TMP
  [ -d "$USB_TMP" -a -n "$(echo $USB_TMP | grep "ocs-usb-dev")" ] && rm -rf $USB_TMP
  # clean the tmp iso.
  [ "$rm_tmp_iso" = "yes" -a -f "$stage1_target_iso" ] && rm -f $stage1_target_iso
} # end of clean_tmp_dirs_files
#
create_version_tag_in_live() {
  local tag_file_in_abs_path="$1"
  local ver_tag_="$2"
  cat <<-TAG_END > $tag_file_in_abs_path
$ver_tag_
This GParted Live was created by:
$full_cmd
TAG_END
}
#
create_gparted_live_iso(){
  echo "$msg_delimiter_star_line"
  echo "Creating GParted Live iso file..."
  echo "$msg_delimiter_star_line"
  #
  # Possible kernel/initrd paths are /casper (created by casper) or /live (created by live-initramfs)
  # Find the kernel and initrd in $stage1_iso_TMP/casper or $stage1_iso_TMP/live
  # Ex: $stage1_iso_TMP/casper/vmlinuz1, /$stage1_iso_TMP/casper/initrd1.img
  # $live_sys_files_dir_list is from drbl-ocs.conf.
  # Possible kernel/initrd paths are /casper (created by casper) or /live (created by live-initramfs)
  sys_files_dir=""
  for i in $live_sys_files_dir_list; do
    krnfile="$(find $stage1_iso_TMP/$i/ -maxdepth 1 -name "vmlinuz*" -print 2>/dev/null)"
    if [ -n "$krnfile" ]; then
      krnfile="$(basename $krnfile)"
      sys_files_dir="$i"
      irdfile="$(find $stage1_iso_TMP/$i/ -maxdepth 1 -name "initrd*" -print)"
      irdfile="$(basename $irdfile)"
      break
    fi
  done
  BOOT_ITEM_DIR=$ISOSYSLNX_TMP/$sys_files_dir
  [ ! -d $BOOT_ITEM_DIR ] && mkdir $BOOT_ITEM_DIR

  if [ -z "$sys_files_dir" ]; then
    [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
    echo "No system files from template live iso are found!"
    [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
    echo "$msg_program_stop"
    exit 1
  fi
  
  if [ -z "$krnfile" -o -z "$irdfile" ]; then
     [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
     echo "Kernel and initrd files NOT found in path $stage1_iso_TMP/$sys_files_dir/!"
     echo "$msg_program_stop"
     [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
     exit 1
  fi

  if [ "$output_mode" = "cdwriter" -a type wodim &>/dev/null ]; then
    [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
    echo "Program wodim is not aviailable! You have to install it."
    [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
    echo "$msg_program_stop"
    exit 1
  fi

  # now we can insert the boot menu of isolinux
  mkdir -p $ISOSYSLNX_TMP/syslinux $ISOSYSLNX_TMP/isolinux
  # create isolinux menu
  # isolinux should be rw, so we have to copy it, and exclude the one in iso image.
  # we have to overwrite isolinux.bin since vesamenu.c32 should be same version with that.
  # For isolinux
  cp -af $isolinux_file $pxelinux_simple_vesamenu $pxelinux_simple_menu $pxelinux_memdisk_file $gparted_live_boot_bg_img $pxelinux_chain_file $ISOSYSLNX_TMP/isolinux/
  # For Syslinux 5, new .c32 are required: ldlinux.c32, libcom32.c32, libutil.c32
  for i in $sys_pxelinux_v5p_required_c32; do
    if [ -e "$pxelinux_binsrc_dir/$i" ]; then
      cp -af $pxelinux_binsrc_dir/$i $ISOSYSLNX_TMP/isolinux/
    fi
  done
  # For syslinux
  cp -af $pxelinux_simple_vesamenu $pxelinux_simple_menu $pxelinux_memdisk_file $gparted_live_boot_bg_img $pxelinux_chain_file $ISOSYSLNX_TMP/syslinux/
  # For Syslinux 5, new .c32 are required: ldlinux.c32, libcom32.c32, libutil.c32
  for i in $sys_pxelinux_v5p_required_c32; do
    if [ -e "$pxelinux_binsrc_dir/$i" ]; then
      cp -af $pxelinux_binsrc_dir/$i $ISOSYSLNX_TMP/syslinux/
    fi
  done
  # For grub2 efi
  if [ -e "$stage1_iso_TMP/EFI/boot/bootia32.efi" -a -e "$stage1_iso_TMP/EFI/boot/bootx64.efi" ]; then
    cp -af $stage1_iso_TMP/EFI $ISOSYSLNX_TMP
    cp -af $gparted_live_boot_bg_img $ISOSYSLNX_TMP/EFI/boot/
  fi

  #  etherboot_zlilo="$($query_pkglist_cmd drbl-etherboot | grep -E "eb-.*-etherboot-pci.zlilo$")"
  #  if [ -n "$etherboot_zlilo" ]; then
  #    # we have to force it name as etherboot.zdsk, since isolinux only uses the "plain" ISO 9660 filenames, i.e. it does not support Rock Ridge or Joliet filenames.
  #    # ref: http://syslinux.zytor.com/archives/2006-October/007440.html
  #    # "-" will be regards as "_" if you want to use "-" for isolinux.
  #    # In syslinux on vfat, etherboot.zlilo is too long, make it ever shorter as eb.zli
  #    cp -af $etherboot_zlilo $BOOT_ITEM_DIR/eb.zli
  #  fi
  #  # same reason, we have to use different name in isolinux
  #  [ -e "$fdos_img_src" ] && cp -af $fdos_img_src $BOOT_ITEM_DIR/freedos.img
  [ -e "$memtest86_file" ] && cp -af $memtest86_file $BOOT_ITEM_DIR/memtest

  # Put the tag
  # The VER_TAG is like drbl-live-xfce-20070315
  VER_TAG="$(echo $real_target_iso | sed -e "s/.iso$//g")"
  create_version_tag_in_live $ISOSYSLNX_TMP/GParted-Live-Version "$VER_TAG"

  # Excluding list for mkisofs
  # We will create it like this:
  # -x $stage1_iso_TMP/isolinux -x $stage1_iso_TMP/md5sum.txt -x $stage1_iso_TMP/casper/memtest 
  mkiso_exclude_list="isolinux syslinux EFI .disk md5sum.txt doc "
  for i in $live_sys_files_dir_list; do
    if [ -e "$stage1_iso_TMP/$i/memtest" ]; then
      mkiso_exclude_list="$mkiso_exclude_list $i/memtest"
      break
    fi
  done
  mkiso_exclude_opt=""
  for i in $mkiso_exclude_list; do
    mkiso_exclude_opt="$mkiso_exclude_opt -x $stage1_iso_TMP/$i"
  done

  # Find the boot param $boot_param
  get_live_boot_param $stage1_iso_TMP/isolinux
  # generate the menu
  # For isolinux
  ocs-live-boot-menu -s -d -l $lang_answer --title "GParted Live" -f $vga_mode_gparted_live -n "$version_no" -k /$sys_files_dir/$krnfile -i /$sys_files_dir/$irdfile -m $gparted_live_boot_bg_img --boot-param "$boot_param $live_extra_boot_param noswap" -r "* Boot menu for BIOS machine" isolinux $ISOSYSLNX_TMP/isolinux/
  # For syslinux
  ocs-live-boot-menu -s -d -l $lang_answer --title "GParted Live" -f $vga_mode_gparted_live -n "$version_no" -k /$sys_files_dir/$krnfile -i /$sys_files_dir/$irdfile -m $gparted_live_boot_bg_img --boot-param "$boot_param $live_extra_boot_param noswap noprompt" -r "* Boot menu for BIOS machine" syslinux $ISOSYSLNX_TMP/syslinux/
  # For grub2 efi
  if [ -e "$ISOSYSLNX_TMP/EFI/boot/bootia32.efi" -a -e "$ISOSYSLNX_TMP/EFI/boot/bootx64.efi" ]; then
    ocs-live-boot-menu -s -d -l $lang_answer --title "GParted Live" -f $vga_mode_gparted_live -n "$version_no" -k /$sys_files_dir/$krnfile -i /$sys_files_dir/$irdfile -m $gparted_live_boot_bg_img --boot-param "$boot_param $live_extra_boot_param noswap noprompt" -r "* Boot menu for EFI machine" grub2-efi $ISOSYSLNX_TMP/EFI/boot/
  fi
  
  # With syslinux-related files, we can put the iso file on USB stick and make ti bootable, too.
  echo "Preparing syslinux.exe, syslinux, makeboot.bat and makeboot.sh... "
  isolinux_ver="$(LC_ALL=C strings $ISOSYSLNX_TMP/isolinux/isolinux.bin | grep "^ISOLINUX" | awk -F" " '{print $2}')"
  put_syslinux_makeboot_for_usb_flash $ISOSYSLNX_TMP/ $isolinux_ver

  utils_files_dir_graft_point=""
  if [ -d "$ISOSYSLNX_TMP/utils" ]; then
    utils_files_dir_graft_point="/utils/=$ISOSYSLNX_TMP/utils/"
  fi

  # $sys_files_dir maybe /casper, /live or /isolinux. If it is isolinux, we can not list them twice otherwise mkisofs will go wrong.
  if [ "$sys_files_dir" != "isolinux" ]; then
    sys_files_dir_graft_point="/isolinux/=$ISOSYSLNX_TMP/isolinux/ /syslinux/=$ISOSYSLNX_TMP/syslinux/ /$sys_files_dir/=$ISOSYSLNX_TMP/$sys_files_dir/"
  else
    sys_files_dir_graft_point="/isolinux/=$ISOSYSLNX_TMP/isolinux/ /syslinux/=$ISOSYSLNX_TMP/syslinux/" 
  fi

  # Remove the existing iso
  [ -e "$target_iso" ] && rm -f $target_iso

  #
  if [ -d "$ISOSYSLNX_TMP/EFI" ]; then
    sys_files_dir_graft_point="$sys_files_dir_graft_point /EFI/=$ISOSYSLNX_TMP/EFI"
  fi
  # Build the EFI boot image. This is especially for iso file. Not for USB stick.
  efi_img_opt=""
  if [ "$enabled_EFI" = "true" ]; then
    # The following codes are referred from Fedora 
    EFI_BOOTIMG_TMP="$(mktemp -d /tmp/efi-boot.XXXXXX)"
    EFI_BOOTTREE="$stage1_iso_TMP/EFI"
    EFI_IMGTREE="$ISOSYSLNX_TMP/EFI/images"
    EFI_IMG="$EFI_IMGTREE/efiboot.img"
    mkdir -p $EFI_IMGTREE
    rm -rf $ISOSYSLNX_TMP/.disk
    rm -f $EFI_IMG
    
    BOOTDISKSIZE="$(LC_ALL=C du -kcs $EFI_BOOTTREE | tail -n1 | awk '{print $1}')"
    BOOTDISKSIZE="$(LC_ALL=C expr $BOOTDISKSIZE + 100)"
    echo "The size of the $EFI_IMG is $BOOTDISKSIZE"
    mkdosfs -n GParted-EFI -C $EFI_IMG $BOOTDISKSIZE >/dev/null
    mount -o loop,shortname=winnt,umask=0077 -t vfat $EFI_IMG $EFI_BOOTIMG_TMP
    mkdir -p $EFI_BOOTIMG_TMP/EFI/
    cp -R $EFI_BOOTTREE/* $EFI_BOOTIMG_TMP/EFI/
    umount $EFI_BOOTIMG_TMP
    if [ -d "$EFI_BOOTIMG_TMP" -a -n \
    	"$(echo $EFI_BOOTIMG_TMP | grep -e "efi-boot")" ]; then
      rm -rf $EFI_BOOTIMG_TMP
    fi
    
    # Create an info file for grub2 to autodetect the cd root
    # Ref: http://www.sysresccd.org/forums/viewtopic.php?f=5&t=4410
    mkdir $ISOSYSLNX_TMP/.disk
    echo -n "[GParted]" > $ISOSYSLNX_TMP/.disk/info
    
    efi_img_opt="-eltorito-alt-boot -efi-boot EFI/images/efiboot.img -no-emul-boot"
    # For Ubuntu uEFI secure boot signed grubx64.efi, it will search /boot/grub/grub.cfg instead of what we have (/EFI/boot/grub.cfg). Although we do not use Ubuntu as the underlaying OS, we still keep this for the future just in case.
    mkdir -p $ISOSYSLNX_TMP/boot/grub/
    cat <<-EFI_END > $ISOSYSLNX_TMP/boot/grub/grub.cfg
# This file is for compatibility to Ubuntu Linux's uEFI secure boot. 
# The real config file for grub is /EFI/boot/grub.cfg.
configfile /EFI/boot/grub.cfg
EFI_END
    efi_img_graft_opt="/.disk/=$ISOSYSLNX_TMP/.disk"
  fi

  # Create the iso file
  genisoimage \
   -A "GParted Live CD" \
   -V "GParted-live" \
   -publisher "GParted http://gparted.org" \
   -f -r -hide-rr-moved -hide-joliet-trans-tbl -J -l -allow-limited-size\
   -b isolinux/isolinux.bin -c isolinux/boot.cat \
   -no-emul-boot -boot-load-size 4 -boot-info-table \
   $efi_img_opt \
   $mkiso_exclude_opt \
   -graft-points \
   $sys_files_dir_graft_point \
   $utils_files_dir_graft_point \
   $efi_img_graft_opt \
   /GPL=$DRBL_SCRIPT_PATH/doc/GPL \
   /GParted-Live-Version=$ISOSYSLNX_TMP/GParted-Live-Version \
   $stage1_iso_TMP \
   > $real_target_iso
  RC_ISO=$?
  if [ "$RC_ISO" -eq 0 ]; then
    [ "$BOOTUP" = "color" ] && $SETCOLOR_SUCCESS
    echo "The $real_target_iso is created successfully!"
    [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  else
    [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
    echo "The $real_target_iso is NOT created!"
    [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  fi
} # end of create_gparted_live_iso
#
create_gparted_live_zip() {
  # create temp dir for usb flash drive
  echo "$msg_delimiter_star_line"
  echo "Creating GParted Live zip file..."
  echo "$msg_delimiter_star_line"
  #
  # Possible kernel/initrd paths are /casper (created by casper) or /live (created by live-initramfs)
  # Find the kernel and initrd in $stage1_iso_TMP/casper or $stage1_iso_TMP/live
  # Ex: $stage1_iso_TMP/casper/vmlinuz1, /$stage1_iso_TMP/casper/initrd1.img
  # $live_sys_files_dir_list is from drbl-ocs.conf.
  # Possible kernel/initrd paths are /casper (created by casper) or /live (created by live-initramfs)
  sys_files_dir=""
  for i in $live_sys_files_dir_list; do
    krnfile="$(find $stage1_iso_TMP/$i/ -maxdepth 1 -name "vmlinuz*" -print 2>/dev/null)"
    if [ -n "$krnfile" ]; then
      krnfile="$(basename $krnfile)"
      sys_files_dir="$i"
      irdfile="$(find $stage1_iso_TMP/$i/ -maxdepth 1 -name "initrd*" -print)"
      irdfile="$(basename $irdfile)"
      break
    fi
  done

  if [ -z "$sys_files_dir" ]; then
    [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
    echo "No system files from template live iso are found!"
    [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
    echo "$msg_program_stop"
    exit 1
  fi
  
  if [ -z "$krnfile" -o -z "$irdfile" ]; then
     [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
     echo "Kernel and initrd files NOT found in path $stage1_iso_TMP/$sys_files_dir/!"
     echo "$msg_program_stop"
     [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
     exit 1
  fi

  WD="$(pwd)"
  # Since we need more space for zip working dir, therefore if it's possible, we use the working dir instead of /tmp (which might be RAM in live CD case).
  if [ -w "$WD" ]; then
    USB_TMP="$(mktemp -d ./ocs-usb-dev.XXXXXX)"
  else
    USB_TMP="$(mktemp -d /tmp/ocs-usb-dev.XXXXXX)"
  fi
  mkdir -p $USB_TMP/$sys_files_dir
  mkdir -p $USB_TMP/syslinux/ $USB_TMP/isolinux/
  echo "Copying files to temp working directory... This might take some time..."
  rsync -av --exclude isolinux --exclude md5sum.txt --exclude doc $stage1_iso_TMP/*  $USB_TMP/
  cp -af $DRBL_SCRIPT_PATH/doc/GPL $USB_TMP/
  # For syslinux
  cp -af $pxelinux_simple_vesamenu $pxelinux_simple_menu $pxelinux_memdisk_file $gparted_live_boot_bg_img $pxelinux_chain_file $USB_TMP/syslinux/
  # For Syslinux 5, new .c32 are required: ldlinux.c32, libcom32.c32, libutil.c32
  for i in $sys_pxelinux_v5p_required_c32; do
    if [ -e "$pxelinux_binsrc_dir/$i" ]; then
      cp -af $pxelinux_binsrc_dir/$i $USB_TMP/syslinux/
    fi
  done
  # For isolinux
  cp -af $isolinux_file $pxelinux_simple_vesamenu $pxelinux_simple_menu $pxelinux_memdisk_file $pxelinux_bg_img $gparted_live_boot_bg_img $pxelinux_chain_file $USB_TMP/isolinux/
  # For Syslinux 5, new .c32 are required: ldlinux.c32, libcom32.c32, libutil.c32
  for i in $sys_pxelinux_v5p_required_c32; do
    if [ -e "$pxelinux_binsrc_dir/$i" ]; then
      cp -af $pxelinux_binsrc_dir/$i $USB_TMP/isolinux/
    fi
  done
  # For grub2 efi
  # The EFI/boot/{bootia32.efi,boox64.efi} are copied by the above rsync command from $$stage1_iso_TMP
  if [ -d "$USB_TMP/EFI/boot/" ]; then
    cp -af $gparted_live_boot_bg_img $USB_TMP/EFI/boot/
  fi

  if [ "$enabled_EFI" = "true" ]; then
    # Build the EFI boot image. This is especially for iso file. Not for USB stick. However, here we still prepare the file so that later it's easier to use genisoimage to create the EFI-enabled iso.
    # The following codes are referred from Fedora 
    EFI_BOOTIMG_TMP="$(mktemp -d /tmp/efi-boot.XXXXXX)"
    EFI_BOOTTREE="$stage1_iso_TMP/EFI"
    EFI_IMGTREE="$USB_TMP/EFI/images"
    EFI_IMG="$EFI_IMGTREE/efiboot.img"
    mkdir -p $EFI_IMGTREE
    rm -rf $USB_TMP/.disk
    rm -f $EFI_IMG
    
    BOOTDISKSIZE="$(LC_ALL=C du -kcs $EFI_BOOTTREE | tail -n1 | awk '{print $1}')"
    BOOTDISKSIZE="$(LC_ALL=C expr $BOOTDISKSIZE + 100)"
    echo "The size of the $EFI_IMG is $BOOTDISKSIZE"
    mkdosfs -n GParted-EFI -C $EFI_IMG $BOOTDISKSIZE >/dev/null
    mount -o loop,shortname=winnt,umask=0077 -t vfat $EFI_IMG $EFI_BOOTIMG_TMP
    mkdir -p $EFI_BOOTIMG_TMP/EFI/
    cp -R $EFI_BOOTTREE/* $EFI_BOOTIMG_TMP/EFI/
    umount $EFI_BOOTIMG_TMP
    if [ -d "$EFI_BOOTIMG_TMP" -a -n \
    	"$(echo $EFI_BOOTIMG_TMP | grep -e "efi-boot")" ]; then
      rm -rf $EFI_BOOTIMG_TMP
    fi
    
    # Create an info file for grub2 to autodetect the cd root
    # Ref: http://www.sysresccd.org/forums/viewtopic.php?f=5&t=4410
    mkdir $USB_TMP/.disk
    echo -n "[GParted]" > $USB_TMP/.disk/info
  
    # For Ubuntu uEFI secure boot signed grubx64.efi, it will search /boot/grub/grub.cfg instead of what we have (/EFI/boot/grub.cfg). Although we do not use Ubuntu as the underlaying OS, we still keep this for the future just in case.
    mkdir -p $USB_TMP/boot/grub/
    cat <<-EFI_END > $USB_TMP/boot/grub/grub.cfg
# This file is for compatibility to Ubuntu Linux's uEFI secure boot. 
# The real config file for grub is /EFI/boot/grub.cfg.
configfile /EFI/boot/grub.cfg
EFI_END
  fi

  # ref: http://syslinux.zytor.com/archives/2006-October/007440.html
  # "-" will be regards as "_" if you want to use "-" for isolinux.
  # In syslinux on vfat, etherboot.zlilo is too long, make it ever shorter as eb.zli
  #  etherboot_zlilo="$($query_pkglist_cmd drbl-etherboot | grep -E "eb-.*-etherboot-pci.zlilo$")"
  #  if [ -n "$etherboot_zlilo" ]; then
  #    # we have to force it name as etherboot.zdsk, since isolinux only uses the "plain" ISO 9660 filenames, i.e. it does not support Rock Ridge or Joliet filenames.
  #    # ref: http://syslinux.zytor.com/archives/2006-October/007440.html
  #    # "-" will be regards as "_" if you want to use "-" for isolinux.
  #    # In syslinux on vfat, etherboot.zlilo is too long, make it ever shorter as eb.zli
  #    cp -af $etherboot_zlilo $USB_TMP/$sys_files_dir/eb.zli
  #  fi
  #  [ -e "$fdos_img_src" ] && cp -af $fdos_img_src $USB_TMP/$sys_files_dir/freedos.img
  [ -e "$memtest86_file" ] && cp -af $memtest86_file $USB_TMP/$sys_files_dir/memtest
  cp -af $stage1_iso_TMP/$sys_files_dir/{$krnfile,$irdfile} $USB_TMP/$sys_files_dir/
  # Put the tag
  # The VER_TAG is like drbl-live-xfce-20070315
  VER_TAG="$(echo $real_target_zip | sed -e "s/.zip$//g")"
  create_version_tag_in_live $USB_TMP/GParted-Live-Version "$VER_TAG" 

  # Find the boot param $boot_param
  get_live_boot_param $stage1_iso_TMP/isolinux
  # generate the menu
  # For syslinux
  ocs-live-boot-menu -s -d -l $lang_answer --title "GParted Live" -f $vga_mode_gparted_live -n "$version_no" -k /$sys_files_dir/$krnfile -i /$sys_files_dir/$irdfile -m $gparted_live_boot_bg_img --boot-param "$boot_param $live_extra_boot_param noswap noprompt" -r "* Boot menu for BIOS machine" syslinux $USB_TMP/syslinux/
  # For isolinux
  ocs-live-boot-menu -s -d -l $lang_answer --title "GParted Live" -f $vga_mode_gparted_live -n "$version_no" -k /$sys_files_dir/$krnfile -i /$sys_files_dir/$irdfile -m $gparted_live_boot_bg_img --boot-param "$boot_param $live_extra_boot_param noswap" -r "* Boot menu for BIOS machine" isolinux $USB_TMP/isolinux/
  # For grub2 efi
  if [ -e "$USB_TMP/EFI/boot/bootia32.efi" -a -e "$USB_TMP/EFI/boot/bootx64.efi" ]; then
    ocs-live-boot-menu -s -d -l $lang_answer --title "GParted Live" -f $vga_mode_gparted_live -n "$version_no" -k /$sys_files_dir/$krnfile -i /$sys_files_dir/$irdfile -m $gparted_live_boot_bg_img --boot-param "$boot_param $live_extra_boot_param noswap noprompt" -r "* Boot menu for EFI machine" grub2-efi $USB_TMP/EFI/boot/
  fi

  echo "Preparing syslinux.exe, syslinux, makeboot.bat and makeboot.sh... "
  # Since we can not judge the version from any files in $USB_TMP/syslinux, we use $USB_TMP/isolinux/isolinux.bin.
  isolinux_ver="$(LC_ALL=C strings $USB_TMP/isolinux/isolinux.bin | grep "^ISOLINUX" | awk -F" " '{print $2}')"
  put_syslinux_makeboot_for_usb_flash $USB_TMP $isolinux_ver
  # just store it. since big files, like squash flie and opt_drbl.tgz are compressed, it's not necessary to compress it again.
  [ -e "$WD/$real_target_zip" ] && rm -f $WD/$real_target_zip
  (cd $USB_TMP; zip -0 -r $WD/$real_target_zip *)
  echo "The created release file is $real_target_zip. You can extract all the files into your pendrive, and run makeboot.bat from pendrive in M$ windows."
  [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
  echo "Warning: DO NOT RUN makeboot.bat from your local hard drive!! It is intended to be run from your USB device."
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  
} # end of create_gparted_live_zip

# default settings
pkg_list=""
pkg_list_opt=""
rm_tmp_iso="no"
use_existing_stage1_iso="no"
TARGET_MEDIA_FILE_DEF="both"
# Parse command-line options
while [ $# -gt 0 ]; do
  case "$1" in
    -l|--language)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              specified_lang="$1"
              shift
            fi
	    [ -z "$specified_lang" ] && USAGE && exit 1
            ;;
    -b|--branch)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              drbl_branch="$1"
              shift
            fi
	    [ -z "$drbl_branch" ] && USAGE && exit 1
            ;;
    -bt|--bootstrap)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              bootstrap="$1"
              shift
            fi
	    [ -z "$bootstrap" ] && USAGE && exit 1
            ;;
    -c|--categories)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              categories="$1"
              shift
            fi
	    [ -z "$categories" ] && USAGE && exit 1
            ;;
    -d|--debian-dist)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              debian_dist="$1"
              shift
            fi
	    [ -z "$debian_dist" ] && USAGE && exit 1
            ;;
    -i|--assign-version-no)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              version_no="$1"
              shift
            fi
	    [ -z "$version_no" ] && USAGE && exit 1
            ;;
    -k|--package)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              extra_pkgs="$1"
              shift
            fi
	    [ -z "$extra_pkgs" ] && USAGE && exit 1
            ;;
    -n|--live-kernel-pkg)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              live_kernel_ver="$1"
              shift
            fi
	    [ -z "$live_kernel_ver" ] && USAGE && exit 1
            ;;
    -e|--drbl-live-branch)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              drbl_live_branch="$1"
              shift
            fi
	    [ -z "$drbl_live_branch" ] && USAGE && exit 1
            ;;
    -p|--packages-list)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              pkg_list="$pkg_list $1"
              shift
            fi
	    [ -z "$pkg_list" ] && USAGE && exit 1
            ;;
    -f|--arch-flavor)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              cpu_flavor="$1"
              shift
            fi
	    [ -z "$cpu_flavor" ] && USAGE && exit 1
            ;;
    -g|--drbl-repo-url)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              DRBL_REPOSITORY_URL="$1"
              shift
            fi
	    [ -z "$DRBL_REPOSITORY_URL" ] && USAGE && exit 1
            ;;
    -m|--mirror-url)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              mirror_url="$1"
              shift
            fi
	    [ -z "$mirror_url" ] && USAGE && exit 1
            ;;
    -o|--create-source-tarball)
	    gen_source_tarball="yes"
            shift ;;
    -s|--mirror-security-url)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              mirror_security_url="$1"
              shift
            fi
	    [ -z "$mirror_security_url" ] && USAGE && exit 1
            ;;
    -t|--target-media-file)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              target_media_file="$1"
              shift
            fi
	    [ -z "$target_media_file" ] && USAGE && exit 1
            ;;
    -r|--rm-tmp-iso)
	    rm_tmp_iso="yes"
            shift ;;
    -u|--use-existing-tmp-iso)
            use_existing_stage1_iso="yes"
            shift ;;
    -v|--verbose)
	    verbose="on"
            shift ;;
    -x|--extra-boot-param)
            shift
            if [ -z "$(echo $1 |grep ^-.)" ]; then
              # skip the -xx option, in case 
              live_extra_boot_param="$1"
              shift
            fi
	    [ -z "$live_extra_boot_param" ] && USAGE && exit 1
            ;;
    -*)     echo "${0}: ${1}: invalid option" >&2
            USAGE >& 2
            exit 2 ;;
    *)      break ;;
  esac
done

#
if [ "$use_existing_stage1_iso" = "no" ]; then
  # if we use existing stage 1 iso file, then we do not have to check if make-live/lb build exists. Otherwise we need make-live to create the stage 1 iso file
  if ! type lb &>/dev/null; then
    [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
    echo "This script only works in Debian Etch or later!"
    echo "If you are running Debian Etch or later, use 'apt-get install live-build' to install the live-build (version $lh_ver_required or later), then run $0 again."
    [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
    exit 1
  fi
  create_live_required_debian_based_prompt
fi

# we need zip to create the release file when target_mode is release_file
if ! type zip &>/dev/null; then
  [ "$BOOTUP" = "color" ] && $SETCOLOR_FAILURE
  echo "Command zip not found!"
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  echo "$msg_program_stop"
  exit 1
fi

ask_and_load_lang_set $specified_lang

[ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
echo "Creating GParted Live..." 
[ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL

rm -rf debian-live/.stage/

# Apply default settings if not assigned
[ -z "$debian_dist" ] && debian_dist="$DEBIAN_DIST_DEF"
[ -z "$categories" ] && categories="$categories_default"
[ -z "$DRBL_REPOSITORY_URL" ] && DRBL_REPOSITORY_URL="$DRBL_REPOSITORY_URL_def"
[ -z "$mirror_url" ] && mirror_url="$debian_mirror_url_def"
[ -z "$mirror_security_url" ] && mirror_security_url="$debian_mirror_security_url_def"
[ -z "$cpu_flavor" ] && cpu_flavor="$cpu_flavor_default"
[ -z "$bootstrap" ] && bootstrap=$bootstrap_default

# Append the extra packages
[ -n "$extra_pkgs" ] && pkgs="$pkgs $extra_pkgs"

echo "The packages to be included in this live CD:"
echo "$msg_delimiter_star_line"
echo "$pkgs"
echo "$msg_delimiter_star_line"
if [ -n "$pkg_list" ]; then
  pkg_list_opt="$pkg_list_opt --packages-list $pkg_list"
  echo "The packages list to be included in this live CD:"
  echo "$msg_delimiter_star_line"
  echo "$pkg_list"
  echo "$msg_delimiter_star_line"
fi
#
echo "Using Debian repository from: $mirror_url"
echo "Using Debian security repository from: $mirror_security_url"
echo "Using DRBL repository from: $DRBL_REPOSITORY_URL"

#
case "$drbl_branch" in
  t|testing)
     echo "Using DRBL testing branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="testing"
     ;;
  u|unstable)
     echo "Using DRBL unstable branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="unstable"
     ;;
  e|experimental)
     echo "Using DRBL experimental branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="experimental"
     ;;
  *)
     echo "Using DRBL stable branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="stable"
     ;;
esac
case "$drbl_live_branch" in
  t|testing)
     echo "Using DRBL Live testing branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="$LIVE_REPOSITORY_SECTIONS_drbl live-testing"
     ;;
  u|unstable)
     echo "Using DRBL Live unstable branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="$LIVE_REPOSITORY_SECTIONS_drbl live-unstable"
     ;;
  e|experimental)
     echo "Using DRBL Live experimental branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="$LIVE_REPOSITORY_SECTIONS_drbl live-experimental"
     ;;
  *)
     echo "Using DRBL Live stable branch..."
     LIVE_REPOSITORY_SECTIONS_drbl="$LIVE_REPOSITORY_SECTIONS_drbl live-stable"
     ;;
esac

if [ -z "$pkg_list" ]; then
  nametag="live"
else
  # choose the first one, and strip space.
  #nametag="$(echo $pkg_list | awk -F" " '{print $1}' | sed -e "s/ //g")"
  # strip the spaces in the beginning and end, replace other space with -
  nametag="$(echo $pkg_list | sed -e "s/^ *//g" -e "s/ *$//g" -e "s/ /-/g")"
fi
  
if [ "$debian_dist" = "etch" ]; then
  # grandr and hfsprogs exist in Lenny or later dist. Remove them.
  pkgs="$(echo $pkgs | sed -e "s/grandr//g" -e "s/hfsprogs//g")"  
fi

if [ "$debian_dist" = "squeeze" -o \
     "$debian_dist" = "wheezy" -o \
     "$debian_dist" = "sid" ]; then
  # From around Oct/2009, the dummy package name "grub" is actually grub-pc, therefore we force to use grub-legacy and assume that if grub2 boot loader is used in the restored GNU/Linux, grub2 is available in the restored GNU/Linux so therefore we can use chroot to run it.
  # 2011/Dec/03 Since most of GNU/Linux distributions now use grub2, no more force to use grub-legacy, and we have backup plan by putting grub1 deb package in the live system. 
  # pkgs="$(LC_ALL=C echo $pkgs | sed -r -e "s/grub[[:space:]]+/grub-legacy /")"
  # Since with squeeze or sid, we can use uvesafb to replace vesafb, we need v86d. Check https://bugs.launchpad.net/ubuntu/+source/v86d/+bug/189621 for more details.
  pkgs="$pkgs v86d"
fi

# if version_no is not assigned, use date (Ex. 20070409)
[ -z "$version_no" ] && version_no="$(date +%Y%m%d)"
stage1_target_iso="gparted-${nametag}-stage1-${version_no}.iso"
real_target_iso="gparted-${nametag}-${version_no}.iso"
real_target_zip="gparted-${nametag}-${version_no}.zip"
target_src_tarball="gparted-live-src-${version_no}.debian.tar.gz"
target_src_tarball_list="gparted-live-src-${version_no}.debian.contents"
target_src_debian_live_tarball="gparted-live-src-${version_no}.debian-live.tar.gz"
target_src_debian_live_tarball_list="gparted-live-src-${version_no}.debian-live.contents"
[ -z "$target_media_file" ] && target_media_file="$TARGET_MEDIA_FILE_DEF"
echo "$msg_delimiter_star_line"

if [ "$verbose" = "on" ]; then
  pref="bash -x"
  export CDEBOOTSTRAP_OPTIONS="$CDEBOOTSTRAP_OPTIONS -v --debug"
fi

if [ "$use_existing_stage1_iso" = "no" ]; then
  if [ -d "debian-live" ]; then
    echo "Found dir debian-live, clean stale debian-live files..."
    chroot debian-live/chroot umount /dev/pts &>/dev/null || true
    chroot debian-live/chroot umount /proc &>/dev/null || true
    chroot debian-live/chroot umount /sys &>/dev/null || true
    (
      cd debian-live/
      lb clean
    )
  fi
  rm -rf debian-live
  mkdir debian-live
  (
  cd debian-live
  $pref lb config --archive-areas "$categories"
  $pref lb config --parent-mirror-bootstrap $mirror_url --parent-mirror-binary $mirror_url --parent-mirror-binary-updates $mirror_url --parent-mirror-chroot $mirror_url --parent-mirror-chroot-updates $mirror_url --parent-mirror-chroot-security $mirror_security_url --parent-mirror-binary-security $mirror_security_url --parent-mirror-debian-installer $mirror_url
  # Since we use Debian Sid normally, disable updates.
  $pref lb config --updates false
  $pref lb config --mirror-debian-installer $mirror_url
  $pref lb config --mirror-bootstrap $mirror_url
  $pref lb config --mirror-chroot $mirror_url --mirror-chroot-updates $mirror_url --mirror-chroot-security $mirror_security_url
  # From live-build 3.0~a58-1, no --bootstrap-flavour option.
  #$pref lb config --bootstrap-flavour $debian_type 
  $pref lb config --debootstrap-options="${DEBOOTSTRAP_OPTIONS} --variant=$debian_type"
  $pref lb config --apt apt --apt-recommends false --bootstrap $bootstrap
  # From live-build 3.0~a59-1, no --volatile option.
  #$pref lb config --volatile false
  # We want "noswap", which only exists in live-initramfs
  # Disable the firmware packages automatically inclusion
  $pref lb config --firmware-binary false --firmware-chroot false
  $pref lb config --security false
  $pref lb config --initramfs live-boot
  $pref lb config --bootappend-live username=user
  # Enable cache-indices, by doing this, "apt-get upgrade" won't be run in lb chroot_sources after hook since we might assign older package version when building.
  #$pref lb config --cache-indices true
  #$pref lb config --apt-indices none
  $pref lb config --tasksel none

  if [ "$debian_dist" = "lenny" ]; then
    # Force to use iso instead of iso-hybrid. Since the syslinux in lenny comes without isohybrid program.
    $pref lb config --binary-images iso
  else
    # Enable iso-hybrid for version >= squeeze
    # //NOTE// This is for template iso only, not for GParted live iso.
    $pref lb config --binary-images iso-hybrid
  fi

  # This decide_live_kernel_related_pkgs_from_debian function will output "kernel_related_pkgs" and "export MKSQUASHFS_OPTIONS"
  decide_live_kernel_related_pkgs_from_debian
  $pref lb config --distribution $debian_dist --parent-distribution $debian_dist
  $pref lb config --linux-packages "$kernel_related_pkgs"

  # We force to use the specific CPU kernel.
  $pref lb config --linux-flavours $cpu_flavor

  # For OS arch, we can build amd64 Debian on i386 Debian or vice versus.
  case "$cpu_flavor" in
    686*|486*) os_arch="i386";;
    amd64) os_arch="amd64";;
  esac
  $pref lb config --architectures $os_arch

  # No memtest from debian, we will use the one from drbl since it's newer.
  $pref lb config --memtest none

  $pref lb config --debian-installer false
  $pref lb config --win32-loader false

  # Disable zsync, it might fail due to download files after /etc/resolv.conf is deconfigured.
  $pref lb config --zsync false

  # Create a source tarball or not.
  if [ "$gen_source_tarball" = "yes" ]; then
    $pref lb config --source true
    $pref lb config --source-images tar
    # Since most of the debian packages are compressed, we just use gzip, not the default one xz.
    $pref lb config --compression gzip
  else
    $pref lb config --source false
  fi

  # Put files to be included in the chroot hook
  mkdir -p config/includes.chroot/live-hook-dir
  for i in $ocs_live_include_dir; do
    cp -pr $i/* config/includes.chroot/live-hook-dir/
  done
  cp -a /etc/drbl/{drbl.conf,drbl-ocs.conf} config/includes.chroot/live-hook-dir
  cp -ar $DRBL_SCRIPT_PATH/setup/files/gparted config/includes.chroot/live-hook-dir/

  # Put packages list in config/package-lists/. //NOTE// Do not use file name like gparted-packages.list. Make it like gparted-packages.list.binary (for lb_binary) or gparted-packages.list.chroot (for lb_chroot). Otherwise lb_binary_package-lists will generate deb repository (/pool). 
  # Ref: http://lists.debian.org/debian-live/2012/07/msg00119.html
  echo "$pkgs" > config/package-lists/gparted-packages.list.chroot

  # Put hook file to be run
  cp $ocs_live_script_dir/${run_hook_script} config/hooks/${run_hook_script}.chroot

  # Put hook file to be run in the binary_local-hooks
  cp $ocs_live_script_dir/$run_binary_hook_script config/hooks/${run_binary_hook_script}.binary
  
  # prepare drbl source list
  cat << AddDRBLRepository > config/archives/drbl-repository.list.chroot
deb $DRBL_REPOSITORY_URL drbl $LIVE_REPOSITORY_SECTIONS_drbl
deb-src $DRBL_REPOSITORY_URL drbl $LIVE_REPOSITORY_SECTIONS_drbl
AddDRBLRepository
  
  # Prepare drbl key
  LC_ALL=C wget -O config/archives/drbl-gpg.key $DRBL_GPG_KEY_URL

  # Disable apt languages and translations when creating DRBL live. This could reduce apt repository issue.
  disable_apt_lang_translation chroot/etc/apt/apt.conf.d/99lang
  
  # Build it.
  $pref lb build
  )
  mv -f debian-live/binary*.iso $stage1_target_iso
  if [ "$gen_source_tarball" = "yes" ]; then
    mv -f debian-live/source.debian.tar.gz $target_src_tarball
    mv -f debian-live/source.debian.contents $target_src_tarball_list
    mv -f debian-live/source.debian-live.tar.gz $target_src_debian_live_tarball
    mv -f debian-live/source.debian-live.contents $target_src_debian_live_tarball_list
  fi
else
  echo "Use existing temp iso file: $stage1_target_iso"
fi
  # clean the dir debian-live if $stage1_target_iso is already created
  if [ -f "$stage1_target_iso" -a -d "debian-live" ]; then
    echo "Removing working dir debian-live in background..."
    # If live cd is not created, we have to force umount these before rm files.
    umount -l debian-live/chroot/dev/pts &>/dev/null || true
    umount -l debian-live/chroot/proc &>/dev/null || true
    umount -l debian-live/chroot/sys &>/dev/null || true
    rm -rf debian-live &
  fi
# 
[ ! -e "$stage1_target_iso" ] && echo "$stage1_target_iso does NOT exist!" && exit 1

# mount the stage 1 iso file
stage1_iso_TMP="$(mktemp -d /tmp/ocs-iso-tmp.XXXXXX)"
trap "[ -d "$stage1_iso_TMP" ] && umount $stage1_iso_TMP &>/dev/null && clean_tmp_dirs_files" HUP INT QUIT TERM EXIT
ISOSYSLNX_TMP="$(mktemp -d /tmp/isolnx-tmp.XXXXXX)"
mount -o loop $stage1_target_iso $stage1_iso_TMP

# Check if EFI boot could be supported.
if [ ! -e "$stage1_iso_TMP/EFI/boot/bootx64.efi" ]; then
  # We only check bootx64.efi since bootx86.efi is optional.
  [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
  echo "Warning! /EFI/boot/bootx64.efi was not found in stage1 GParted live!"
  echo "The generated $target_iso will not support EFI boot!"
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  sleep 5
  enabled_EFI="false"
elif [ -n "$(LC_ALL=C genisoimage --help 2>&1 | grep -E -- "-efi-boot")" ]; then
  # Check if genisoimage support -efi-boot option
  enabled_EFI="true"
else
  [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
  echo "Warning! Setting EFI boot image name is not supported in genisoimage!"
  [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
  sleep 5
  enabled_EFI="false"
fi
  
#
case "$target_media_file" in
  cd|CD|iso|ISO)
     create_gparted_live_iso ;;
  usb|zip)
     create_gparted_live_zip ;;
  b|both|BOTH)
     create_gparted_live_iso
     create_gparted_live_zip
     ;;
esac

# unmount all iso file
umount $stage1_iso_TMP &>/dev/null

# Isohybrid the generated iso file.
# //NOTE// This is for GParted live iso. It's different from that for template iso.

if [ -e "$real_target_iso" ]; then
  if type isohybrid &>/dev/null; then
    echo -n "Isohybriding $real_target_iso... "
    isohybrid $real_target_iso
    echo "done!"
  fi
fi

case "$target_media_file" in
  cd|CD|iso|ISO)
     [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
     echo "$msg_burn_drbl_live_img_iso: $real_target_iso"
     [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
     ;;
  usb|zip)
     [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
     echo "$msg_burn_drbl_live_img_zip: $real_target_zip"
     [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
     ;;
  b|both|BOTH)
     [ "$BOOTUP" = "color" ] && $SETCOLOR_WARNING
     echo "$msg_burn_drbl_live_img_iso: $real_target_iso"
     echo "$msg_burn_drbl_live_img_zip: $real_target_zip"
     [ "$BOOTUP" = "color" ] && $SETCOLOR_NORMAL
     ;;
esac

# ///NOTE/// This should be the last command otherwise the rest of commands might be skipped due to trap.
# Clean the tmp working directory
echo "Cleaning tmp dirs..."
clean_tmp_dirs_files

