1#!/bin/sh 2#- 3# Copyright (c) 2015-2017 The FreeBSD Foundation 4# 5# Portions of this software were developed by Glen Barber 6# under sponsorship from the FreeBSD Foundation. 7# 8# Redistribution and use in source and binary forms, with or without 9# modification, are permitted provided that the following conditions 10# are met: 11# 1. Redistributions of source code must retain the above copyright 12# notice, this list of conditions and the following disclaimer. 13# 2. Redistributions in binary form must reproduce the above copyright 14# notice, this list of conditions and the following disclaimer in the 15# documentation and/or other materials provided with the distribution. 16# 17# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 18# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 21# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27# SUCH DAMAGE. 28# 29# Common subroutines used to build arm, arm64, or RISC-V SD card images. 30# 31# $FreeBSD$ 32# 33 34cleanup() { 35 if [ -c "${DESTDIR}/dev/null" ]; then 36 umount_loop ${DESTDIR}/dev 2>/dev/null 37 fi 38 umount_loop ${DESTDIR} 39 if [ ! -z "${mddev}" ]; then 40 mdconfig -d -u ${mddev} 41 fi 42 43 return 0 44} 45 46umount_loop() { 47 DIR=$1 48 i=0 49 sync 50 while ! umount ${DIR}; do 51 i=$(( $i + 1 )) 52 if [ $i -ge 10 ]; then 53 # This should never happen. But, it has happened. 54 echo "Cannot umount(8) ${DIR}" 55 echo "Something has gone horribly wrong." 56 return 1 57 fi 58 sleep 1 59 done 60 61 return 0 62} 63 64arm_create_disk() { 65 if [ $(sysctl -n kern.geom.part.mbr.enforce_chs) != 0 ]; then 66 return 1 67 fi 68 69 # Create the target raw file and temporary work directory. 70 chroot ${CHROOTDIR} gpart create -s ${PART_SCHEME} ${mddev} 71 if [ "${PART_SCHEME}" = "GPT" ]; then 72 chroot ${CHROOTDIR} gpart add -t efi -l efi -a 512k -s ${FAT_SIZE} ${mddev} 73 chroot ${CHROOTDIR} newfs_msdos -L efi -F ${FAT_TYPE} /dev/${mddev}p1 74 chroot ${CHROOTDIR} gpart add -t freebsd-ufs -l rootfs -a 64k ${mddev} 75 chroot ${CHROOTDIR} newfs -U -L rootfs /dev/${mddev}p2 76 fi 77 if [ "${PART_SCHEME}" = "MBR" ]; then 78 chroot ${CHROOTDIR} gpart add -t '!12' -a 512k -s ${FAT_SIZE} ${mddev} 79 chroot ${CHROOTDIR} gpart set -a active -i 1 ${mddev} 80 chroot ${CHROOTDIR} newfs_msdos -L efi -F ${FAT_TYPE} /dev/${mddev}s1 81 chroot ${CHROOTDIR} gpart add -t freebsd ${mddev} 82 chroot ${CHROOTDIR} gpart create -s bsd ${mddev}s2 83 chroot ${CHROOTDIR} gpart add -t freebsd-ufs -a 64k -b 64k ${mddev}s2 84 chroot ${CHROOTDIR} newfs -U -L rootfs /dev/${mddev}s2a 85 fi 86 87 return 0 88} 89 90arm_create_user() { 91 # Create a default user account 'freebsd' with the password 'freebsd', 92 # and set the default password for the 'root' user to 'root'. 93 chroot ${CHROOTDIR} /usr/sbin/pw -R ${DESTDIR} \ 94 groupadd freebsd -g 1001 95 chroot ${CHROOTDIR} mkdir -p ${DESTDIR}/home/freebsd 96 chroot ${CHROOTDIR} /usr/sbin/pw -R ${DESTDIR} \ 97 useradd freebsd \ 98 -m -M 0755 -w yes -n freebsd -u 1001 -g 1001 -G 0 \ 99 -c 'FreeBSD User' -d '/home/freebsd' -s '/bin/csh' 100 chroot ${CHROOTDIR} /usr/sbin/pw -R ${DESTDIR} \ 101 usermod root -w yes 102 103 return 0 104} 105 106arm_setup_usb_otg() { 107 # Set up virtual serial port over USB OTG / device mode. 108 echo >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 109 echo '# Required for USB OTG virtual serial port.' \ 110 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 111 echo 'notify 100 {' \ 112 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 113 echo ' match "system" "DEVFS";' \ 114 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 115 echo ' match "subsystem" "CDEV";' \ 116 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 117 echo ' match "type" "CREATE";' \ 118 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 119 echo ' match "cdev" "ttyU[0-9]+";' \ 120 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 121 echo ' action "/sbin/init q";' \ 122 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 123 echo '};' \ 124 >> ${CHROOTDIR}/${DESTDIR}/etc/devd.conf 125 126 echo '# USB OTG virtual serial port' \ 127 >> ${CHROOTDIR}/${DESTDIR}/etc/ttys 128 echo 'ttyU0 "/usr/libexec/getty 3wire" vt100 onifconsole secure' \ 129 >> ${CHROOTDIR}/${DESTDIR}/etc/ttys 130 echo 'ttyU1 "/usr/libexec/getty 3wire" vt100 onifconsole secure' \ 131 >> ${CHROOTDIR}/${DESTDIR}/etc/ttys 132 133 echo '# Configure USB OTG; see usb_template(4).' \ 134 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 135 echo 'hw.usb.template=3' \ 136 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 137 echo 'umodem_load="YES"' \ 138 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 139} 140 141arm64_setup_multicons() { 142 if [ "${EMBEDDED_TARGET_ARCH}" != "aarch64" ]; then 143 return 144 fi 145 146 echo '# Multiple console (serial+efi gop) enabled.' \ 147 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 148 echo 'boot_multicons="YES"' \ 149 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 150 echo 'boot_serial="YES"' \ 151 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 152} 153 154arm_setup_fdt_overlays() { 155 if [ -z "${FDT_OVERLAYS}" ]; then 156 return 157 fi 158 159 echo '# DTB OVERLAYS' \ 160 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 161 echo "fdt_overlays=\"${FDT_OVERLAYS}\"" \ 162 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 163} 164 165arm_setup_minimal_loader() { 166 echo '# Disable the beastie menu and color' \ 167 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 168 echo 'beastie_disable="YES"' \ 169 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 170 echo 'loader_color="NO"' \ 171 >> ${CHROOTDIR}/${DESTDIR}/boot/loader.conf 172} 173 174arm_install_base() { 175 if [ "${PART_SCHEME}" = "GPT" ]; then 176 chroot ${CHROOTDIR} mount /dev/${mddev}p2 ${DESTDIR} 177 fi 178 if [ "${PART_SCHEME}" = "MBR" ]; then 179 chroot ${CHROOTDIR} mount /dev/${mddev}s2a ${DESTDIR} 180 fi 181 _OSVERSION=$(chroot ${CHROOTDIR} /usr/bin/uname -U) 182 REVISION=$(chroot ${CHROOTDIR} make -C /usr/src/release -V REVISION) 183 BRANCH=$(chroot ${CHROOTDIR} make -C /usr/src/release -V BRANCH) 184 export UNAME_r=${REVISION}-${BRANCH} 185 eval chroot ${CHROOTDIR} make -C ${WORLDDIR} \ 186 TARGET=${EMBEDDED_TARGET} \ 187 TARGET_ARCH=${EMBEDDED_TARGET_ARCH} \ 188 DESTDIR=${DESTDIR} KERNCONF=${KERNEL} \ 189 ${CONF_FILES} installworld installkernel distribution 190 chroot ${CHROOTDIR} mkdir -p ${DESTDIR}/boot/efi 191 # Compatibility symlink to /boot/msdos for 13.1 and earlier 192 chroot ${CHROOTDIR} ln -s efi ${DESTDIR}/boot/msdos 193 194 arm_create_user 195 arm_setup_usb_otg 196 arm64_setup_multicons 197 arm_setup_fdt_overlays 198 arm_setup_minimal_loader 199 arm_do_quirk 200 201 echo '# Custom /etc/fstab for FreeBSD embedded images' \ 202 > ${CHROOTDIR}/${DESTDIR}/etc/fstab 203 if [ "${PART_SCHEME}" = "GPT" ]; then 204 echo "/dev/ufs/rootfs / ufs rw 1 1" \ 205 >> ${CHROOTDIR}/${DESTDIR}/etc/fstab 206 echo "/dev/msdosfs/EFI /boot/efi msdosfs rw,noatime 0 0" \ 207 >> ${CHROOTDIR}/${DESTDIR}/etc/fstab 208 fi 209 if [ "${PART_SCHEME}" = "MBR" ]; then 210 echo "/dev/ufs/rootfs / ufs rw 1 1" \ 211 >> ${CHROOTDIR}/${DESTDIR}/etc/fstab 212 echo "/dev/msdosfs/EFI /boot/efi msdosfs rw,noatime 0 0" \ 213 >> ${CHROOTDIR}/${DESTDIR}/etc/fstab 214 fi 215 echo "tmpfs /tmp tmpfs rw,mode=1777 0 0" \ 216 >> ${CHROOTDIR}/${DESTDIR}/etc/fstab 217 218 local hostname 219 hostname="$(echo ${KERNEL} | tr '[:upper:]' '[:lower:]')" 220 echo "hostname=\"${hostname}\"" > ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 221 echo 'ifconfig_DEFAULT="DHCP inet6 accept_rtadv"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 222 echo 'sshd_enable="YES"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 223 echo 'sendmail_enable="NONE"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 224 echo 'sendmail_submit_enable="NO"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 225 echo 'sendmail_outbound_enable="NO"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 226 echo 'sendmail_msp_queue_enable="NO"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 227 echo 'growfs_enable="YES"' >> ${CHROOTDIR}/${DESTDIR}/etc/rc.conf 228 229 sync 230 umount_loop ${CHROOTDIR}/${DESTDIR} 231 232 return 0 233} 234 235arm_install_boot() { 236 FATMOUNT="${DESTDIR%${KERNEL}}/fat" 237 UFSMOUNT="${DESTDIR%${KERNEL}}/ufs" 238 chroot ${CHROOTDIR} mkdir -p "${FATMOUNT}" "${UFSMOUNT}" 239 if [ "${PART_SCHEME}" = "GPT" ]; then 240 dospart="/dev/${mddev}p1" 241 ufspart="/dev/${mddev}p2" 242 fi 243 if [ "${PART_SCHEME}" = "MBR" ]; then 244 dospart="/dev/${mddev}s1" 245 ufspart="/dev/${mddev}s2a" 246 fi 247 248 chroot ${CHROOTDIR} mount_msdosfs ${dospart} ${FATMOUNT} 249 chroot ${CHROOTDIR} mount ${ufspart} ${UFSMOUNT} 250 251 BOOTFILES="$(chroot ${CHROOTDIR} \ 252 env TARGET=${EMBEDDED_TARGET} TARGET_ARCH=${EMBEDDED_TARGET_ARCH} \ 253 WITH_UNIFIED_OBJDIR=yes \ 254 make -C ${WORLDDIR}/stand -V .OBJDIR)" 255 BOOTFILES="$(chroot ${CHROOTDIR} realpath ${BOOTFILES})" 256 257 chroot ${CHROOTDIR} mkdir -p ${FATMOUNT}/EFI/BOOT 258 chroot ${CHROOTDIR} cp -p ${BOOTFILES}/efi/loader_lua/loader_lua.efi \ 259 ${FATMOUNT}/EFI/BOOT/$(efi_boot_name ${EMBEDDED_TARGET}) 260 261 chroot ${CHROOTDIR} cp -R ${UFSMOUNT}/boot/dtb ${FATMOUNT} 262 263 chroot ${CHROOTDIR} touch ${UFSMOUNT}/firstboot 264 sync 265 umount_loop ${CHROOTDIR}/${FATMOUNT} 266 umount_loop ${CHROOTDIR}/${UFSMOUNT} 267 chroot ${CHROOTDIR} rmdir ${FATMOUNT} 268 chroot ${CHROOTDIR} rmdir ${UFSMOUNT} 269} 270 271arm_install_uboot() { 272 # Override in the ${EMBEDDED_TARGET}/${BOARDNAME}.conf file. 273 274 return 0 275} 276 277arm_do_quirk() { 278 # Override in the ${EMBEDDED_TARGET}/${BOARDNAME}.conf file. 279} 280