1#!/bin/sh 2#- 3# Copyright (c) 2011 Nathan Whitehorn 4# Copyright (c) 2013-2018 Devin Teske 5# All rights reserved. 6# 7# Redistribution and use in source and binary forms, with or without 8# modification, are permitted provided that the following conditions 9# are met: 10# 1. Redistributions of source code must retain the above copyright 11# notice, this list of conditions and the following disclaimer. 12# 2. Redistributions in binary form must reproduce the above copyright 13# notice, this list of conditions and the following disclaimer in the 14# documentation and/or other materials provided with the distribution. 15# 16# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 17# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 18# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 19# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 20# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 21# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 22# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 23# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 24# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 25# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 26# SUCH DAMAGE. 27# 28# $FreeBSD$ 29# 30############################################################ INCLUDES 31 32BSDCFG_SHARE="/usr/share/bsdconfig" 33. $BSDCFG_SHARE/common.subr || exit 1 34f_include $BSDCFG_SHARE/dialog.subr 35 36############################################################ GLOBALS 37 38# 39# Strings that should be moved to an i18n file and loaded with f_include_lang() 40# 41hline_arrows_tab_enter="Press arrows, TAB or ENTER" 42hline_arrows_tab_space_enter="Press arrows, TAB, SPACE or ENTER" 43msg_abort="Abort" 44msg_an_installation_step_has_been_aborted="An installation step has been aborted. Would you like\nto restart the installation or exit the installer?" 45msg_auto_ufs="Auto (UFS)" 46msg_auto_ufs_desc="Guided UFS Disk Setup" 47msg_auto_ufs_help="Menu options help choose which disk to setup using UFS and standard partitions" 48msg_auto_zfs="Auto (ZFS)" 49msg_auto_zfs_desc="Guided Root-on-ZFS" 50msg_auto_zfs_help="To use ZFS with less than 8GB RAM, see https://wiki.freebsd.org/ZFSTuningGuide" 51msg_exit="Exit" 52msg_freebsd_installer="$OSNAME Installer" 53msg_gpt_active_fix="Your hardware is known to have issues booting in CSM/Legacy/BIOS mode from GPT partitions that are not set active. Would you like the installer to apply this workaround for you?" 54msg_lenovo_fix="Your model of Lenovo is known to have a BIOS bug that prevents it booting from GPT partitions without UEFI. Would you like the installer to apply a workaround for you?" 55msg_manual="Manual" 56msg_manual_desc="Manual Disk Setup (experts)" 57msg_manual_help="Create customized partitions from menu options" 58msg_no="NO" 59msg_restart="Restart" 60msg_shell="Shell" 61msg_shell_desc="Open a shell and partition by hand" 62msg_shell_help="Create customized partitions using command-line utilities" 63msg_yes="YES" 64 65############################################################ FUNCTIONS 66 67# error [$msg] 68# 69# Display generic error message when a script fails. An optional message 70# argument can preceed the generic message. User is given the choice of 71# restarting the installer or exiting. 72# 73error() 74{ 75 local title="$msg_abort" 76 local btitle="$msg_freebsd_installer" 77 local prompt="${1:+$1\n\n}$msg_an_installation_step_has_been_aborted" 78 local hline="$hline_arrows_tab_space_enter" 79 80 [ -f "$PATH_FSTAB" ] && bsdinstall umount 81 82 local height width 83 f_dialog_buttonbox_size height width \ 84 "$title" "$btitle" "$prompt" "$hline" 85 86 if $DIALOG \ 87 --title "$title" \ 88 --backtitle "$btitle" \ 89 --hline "$hline" \ 90 --no-label "$msg_exit" \ 91 --yes-label "$msg_restart" \ 92 --yesno "$prompt" $height $width 93 then 94 exec $0 95 # NOTREACHED 96 fi 97 exit 1 98} 99 100# dialog_workaround 101# 102# Ask the user if they wish to apply a workaround 103# 104dialog_workaround() 105{ 106 local passed_msg="$1" 107 local title="$DIALOG_TITLE" 108 local btitle="$DIALOG_BACKTITLE" 109 local prompt # Calculated below 110 local hline="$hline_arrows_tab_enter" 111 112 local height=8 width=50 prefix=" " 113 local plen=${#prefix} list= line= 114 local max_width=$(( $width - 3 - $plen )) 115 116 local yes no defaultno extra_args format 117 if [ "$USE_XDIALOG" ]; then 118 yes=ok no=cancel defaultno=default-no 119 extra_args="--wrap --left" 120 format="$passed_msg" 121 else 122 yes=yes no=no defaultno=defaultno 123 extra_args="--cr-wrap" 124 format="$passed_msg" 125 fi 126 127 # Add height for Xdialog(1) 128 [ "$USE_XDIALOG" ] && height=$(( $height + $height / 5 + 3 )) 129 130 prompt=$( printf "$format" ) 131 f_dprintf "%s: Workaround prompt" "$0" 132 $DIALOG \ 133 --title "$title" \ 134 --backtitle "$btitle" \ 135 --hline "$hline" \ 136 --$yes-label "$msg_yes" \ 137 --$no-label "$msg_no" \ 138 $extra_args \ 139 --yesno "$prompt" $height $width 140} 141 142############################################################ MAIN 143 144f_dprintf "Began Installation at %s" "$( date )" 145 146rm -rf $BSDINSTALL_TMPETC 147mkdir $BSDINSTALL_TMPETC 148 149trap true SIGINT # This section is optional 150[ -z "$BSDINSTALL_SKIP_KEYMAP" ] && bsdinstall keymap 151 152trap error SIGINT # Catch cntrl-C here 153if [ -z "$BSDINSTALL_SKIP_HOSTNAME" ]; then bsdinstall hostname || error "Set hostname failed"; fi 154 155export DISTRIBUTIONS="${DISTRIBUTIONS:-base.txz kernel.txz}" 156if [ -f $BSDINSTALL_DISTDIR/MANIFEST ]; then 157 DISTMENU=`awk -F'\t' '!/^(kernel\.txz|base\.txz)/{print $1,$5,$6}' $BSDINSTALL_DISTDIR/MANIFEST` 158 DISTMENU="$(echo ${DISTMENU} | sed -E 's/\.txz//g')" 159 160 if [ -n "$DISTMENU" ]; then 161 exec 3>&1 162 EXTRA_DISTS=$( eval dialog \ 163 --backtitle \"$OSNAME Installer\" \ 164 --title \"Distribution Select\" --nocancel --separate-output \ 165 --checklist \"Choose optional system components to install:\" \ 166 0 0 0 $DISTMENU \ 167 2>&1 1>&3 ) 168 for dist in $EXTRA_DISTS; do 169 export DISTRIBUTIONS="$DISTRIBUTIONS $dist.txz" 170 done 171 fi 172fi 173 174FETCH_DISTRIBUTIONS="" 175for dist in $DISTRIBUTIONS; do 176 if [ ! -f $BSDINSTALL_DISTDIR/$dist ]; then 177 FETCH_DISTRIBUTIONS="$FETCH_DISTRIBUTIONS $dist" 178 fi 179done 180 181if [ -n "$FETCH_DISTRIBUTIONS" -a -n "$BSDINSTALL_CONFIGCURRENT" ]; then 182 dialog --backtitle "$OSNAME Installer" --title "Network Installation" --msgbox "Some installation files were not found on the boot volume. The next few screens will allow you to configure networking so that they can be downloaded from the Internet." 0 0 183 bsdinstall netconfig || error 184 NETCONFIG_DONE=yes 185fi 186 187rm -f $PATH_FSTAB 188touch $PATH_FSTAB 189 190# 191# Try to detect known broken platforms and apply their workarounds 192# 193 194if f_interactive; then 195 sys_maker=$( kenv -q smbios.system.maker ) 196 f_dprintf "smbios.system.maker=[%s]" "$sys_maker" 197 sys_model=$( kenv -q smbios.system.product ) 198 f_dprintf "smbios.system.product=[%s]" "$sys_model" 199 sys_version=$( kenv -q smbios.system.version ) 200 f_dprintf "smbios.system.version=[%s]" "$sys_version" 201 sys_mb_maker=$( kenv -q smbios.planar.maker ) 202 f_dprintf "smbios.planar.maker=[%s]" "$sys_mb_maker" 203 sys_mb_product=$( kenv -q smbios.planar.product ) 204 f_dprintf "smbios.planar.product=[%s]" "$sys_mb_product" 205 206 # 207 # Laptop Models 208 # 209 case "$sys_maker" in 210 "LENOVO") 211 case "$sys_version" in 212 "ThinkPad X220"|"ThinkPad T420"|"ThinkPad T520"|"ThinkPad W520"|"ThinkPad X1") 213 dialog_workaround "$msg_lenovo_fix" 214 retval=$? 215 f_dprintf "lenovofix_prompt=[%s]" "$retval" 216 if [ $retval -eq $DIALOG_OK ]; then 217 export ZFSBOOT_PARTITION_SCHEME="GPT + Lenovo Fix" 218 export WORKAROUND_LENOVO=1 219 fi 220 ;; 221 esac 222 ;; 223 "Dell Inc.") 224 case "$sys_model" in 225 "Latitude E6330"|"Latitude E7440"|"Latitude E7240"|"Precision Tower 5810") 226 dialog_workaround "$msg_gpt_active_fix" 227 retval=$? 228 f_dprintf "gpt_active_fix_prompt=[%s]" "$retval" 229 if [ $retval -eq $DIALOG_OK ]; then 230 export ZFSBOOT_PARTITION_SCHEME="GPT + Active" 231 export WORKAROUND_GPTACTIVE=1 232 fi 233 ;; 234 esac 235 ;; 236 "Hewlett-Packard") 237 case "$sys_model" in 238 "HP ProBook 4330s") 239 dialog_workaround "$msg_gpt_active_fix" 240 retval=$? 241 f_dprintf "gpt_active_fix_prompt=[%s]" "$retval" 242 if [ $retval -eq $DIALOG_OK ]; then 243 export ZFSBOOT_PARTITION_SCHEME="GPT + Active" 244 export WORKAROUND_GPTACTIVE=1 245 fi 246 ;; 247 esac 248 ;; 249 esac 250 # 251 # Motherboard Models 252 # 253 case "$sys_mb_maker" in 254 "Intel Corporation") 255 case "$sys_mb_product" in 256 "DP965LT"|"D510MO") 257 dialog_workaround "$msg_gpt_active_fix" 258 retval=$? 259 f_dprintf "gpt_active_fix_prompt=[%s]" "$retval" 260 if [ $retval -eq $DIALOG_OK ]; then 261 export ZFSBOOT_PARTITION_SCHEME="GPT + Active" 262 export WORKAROUND_GPTACTIVE=1 263 fi 264 ;; 265 esac 266 ;; 267 "Acer") 268 case "$sys_mb_product" in 269 "Veriton M6630G") 270 dialog_workaround "$msg_gpt_active_fix" 271 retval=$? 272 f_dprintf "gpt_active_fix_prompt=[%s]" "$retval" 273 if [ $retval -eq $DIALOG_OK ]; then 274 export ZFSBOOT_PARTITION_SCHEME="GPT + Active" 275 export WORKAROUND_GPTACTIVE=1 276 fi 277 ;; 278 esac 279 ;; 280 esac 281fi 282 283PMODES=" 284 '$msg_auto_ufs' '$msg_auto_ufs_desc' '$msg_auto_ufs_help' 285 '$msg_manual' '$msg_manual_desc' '$msg_manual_help' 286 '$msg_shell' '$msg_shell_desc' '$msg_shell_help' 287" # END-QUOTE 288 289CURARCH=$( uname -m ) 290case $CURARCH in 291 amd64|arm64|i386|riscv) # Booting ZFS Supported 292 PMODES=" 293 '$msg_auto_zfs' '$msg_auto_zfs_desc' '$msg_auto_zfs_help' 294 $PMODES 295 " # END-QUOTE 296 ;; 297 *) # Booting ZFS Unsupported 298 ;; 299esac 300 301exec 3>&1 302PARTMODE=`echo $PMODES | xargs dialog --backtitle "$OSNAME Installer" \ 303 --title "Partitioning" \ 304 --item-help \ 305 --menu "How would you like to partition your disk?" \ 306 0 0 0 2>&1 1>&3` || exit 1 307exec 3>&- 308 309case "$PARTMODE" in 310"$msg_auto_zfs") # ZFS 311 bsdinstall zfsboot || error "ZFS setup failed" 312 bsdinstall mount || error "Failed to mount filesystem" 313 ;; 314"$msg_auto_ufs") # Guided UFS 315 bsdinstall autopart || error "Partitioning error" 316 bsdinstall mount || error "Failed to mount filesystem" 317 ;; 318"$msg_shell") # Shell 319 clear 320 echo "Use this shell to set up partitions for the new system. When finished, mount the system at $BSDINSTALL_CHROOT and place an fstab file for the new system at $PATH_FSTAB. Then type 'exit'. You can also enter the partition editor at any time by entering 'bsdinstall partedit'." 321 sh 2>&1 322 ;; 323"$msg_manual") # Manual 324 if f_isset debugFile; then 325 # Give partedit the path to our logfile so it can append 326 BSDINSTALL_LOG="${debugFile#+}" bsdinstall partedit || error "Partitioning error" 327 else 328 bsdinstall partedit || error "Partitioning error" 329 fi 330 bsdinstall mount || error "Failed to mount filesystem" 331 ;; 332*) 333 error "Unknown partitioning mode" 334 ;; 335esac 336 337if [ -n "$FETCH_DISTRIBUTIONS" ]; then 338 exec 3>&1 339 export BSDINSTALL_DISTDIR=$(`dirname $0`/fetchmissingdists 2>&1 1>&3) 340 FETCH_RESULT=$? 341 exec 3>&- 342 343 [ $FETCH_RESULT -ne 0 ] && error "Could not fetch remote distributions" 344fi 345bsdinstall checksum || error "Distribution checksum failed" 346bsdinstall distextract || error "Distribution extract failed" 347 348# Set up boot loader 349bsdinstall bootconfig || error "Failed to configure bootloader" 350 351bsdinstall rootpass || error "Could not set root password" 352 353trap true SIGINT # This section is optional 354if [ "$NETCONFIG_DONE" != yes ]; then 355 bsdinstall netconfig # Don't check for errors -- the user may cancel 356fi 357[ -z "$BSDINSTALL_SKIP_TIME" ] && bsdinstall time 358[ -z "$BSDINSTALL_SKIP_SERVICES" ] && bsdinstall services 359[ -z "$BSDINSTALL_SKIP_HARDENING" ] && bsdinstall hardening 360 361[ -z "$BSDINSTALL_SKIP_USERS" ] && dialog --backtitle "$OSNAME Installer" \ 362 --title "Add User Accounts" --yesno \ 363 "Would you like to add users to the installed system now?" 0 0 && \ 364 bsdinstall adduser 365 366finalconfig() { 367 exec 3>&1 368 REVISIT=$(dialog --backtitle "$OSNAME Installer" \ 369 --title "Final Configuration" --no-cancel --menu \ 370 "Setup of your $OSNAME system is nearly complete. You can now modify your configuration choices. After this screen, you will have an opportunity to make more complex changes using a shell." 0 0 0 \ 371 "Exit" "Apply configuration and exit installer" \ 372 "Add User" "Add a user to the system" \ 373 "Root Password" "Change root password" \ 374 "Hostname" "Set system hostname" \ 375 "Network" "Networking configuration" \ 376 "Services" "Set daemons to run on startup" \ 377 "System Hardening" "Set security options" \ 378 "Time Zone" "Set system timezone" \ 379 "Handbook" "Install $OSNAME Handbook (requires network)" 2>&1 1>&3) 380 exec 3>&- 381 382 case "$REVISIT" in 383 "Add User") 384 bsdinstall adduser 385 finalconfig 386 ;; 387 "Root Password") 388 bsdinstall rootpass 389 finalconfig 390 ;; 391 "Hostname") 392 bsdinstall hostname 393 finalconfig 394 ;; 395 "Network") 396 bsdinstall netconfig 397 finalconfig 398 ;; 399 "Services") 400 bsdinstall services 401 finalconfig 402 ;; 403 "System Hardening") 404 bsdinstall hardening 405 finalconfig 406 ;; 407 "Time Zone") 408 bsdinstall time 409 finalconfig 410 ;; 411 "Handbook") 412 bsdinstall docsinstall 413 finalconfig 414 ;; 415 esac 416} 417 418# Allow user to change his mind 419[ -z "$BSDINSTALL_SKIP_FINALCONFIG" ] && finalconfig 420 421trap error SIGINT # SIGINT is bad again 422bsdinstall config || error "Failed to save config" 423 424if [ ! -z "$BSDINSTALL_FETCHDEST" ]; then 425 rm -rf "$BSDINSTALL_FETCHDEST" 426fi 427 428if [ -z "$BSDINSTALL_SKIP_MANUAL" ]; then 429 dialog --backtitle "$OSNAME Installer" --title "Manual Configuration" \ 430 --default-button no --yesno \ 431 "The installation is now finished. Before exiting the installer, would you like to open a shell in the new system to make any final manual modifications?" 0 0 432 if [ $? -eq 0 ]; then 433 clear 434 echo This shell is operating in a chroot in the new system. \ 435 When finished making configuration changes, type \"exit\". 436 chroot "$BSDINSTALL_CHROOT" /bin/sh 2>&1 437 fi 438fi 439 440bsdinstall entropy 441bsdinstall umount 442 443f_dprintf "Installation Completed at %s" "$( date )" 444 445################################################################################ 446# END 447################################################################################ 448