#!/bin/sh set -e . /usr/share/debconf/confmodule log () { logger -t nobootloader "$@" } error () { log "error: $@" } findfs () { case "$(udpkg --print-os)" in hurd) fsysopts "/target$1" | sed 's:^.* \([^ ]*\):\1:' ;; *) mount | grep "on /target${1%/} " | tail -n1 | cut -d' ' -f1 ;; esac } die () { local template="$1" shift error "$@" db_input critical "$template" || [ $? -eq 30 ] db_go || true exit 1 } mountvirtfs () { fstype="$1" path="$2" if grep -q "[[:space:]]$fstype\$" /proc/filesystems && \ ! grep -q "^[^ ]\+ \+$path " /proc/mounts; then mkdir -p "$path" || \ die nobootloader/mounterr "Error creating $path" mount -t "$fstype" "$fstype" "$path" || \ die nobootloader/mounterr "Error mounting $path" trap "umount $path" HUP INT QUIT KILL PIPE TERM EXIT fi } rootfs_devfs=$(findfs /) bootfs_devfs=$(findfs /boot) # partconf workaround (mounts /target as /target/) if [ "$rootfs_devfs" = "" ]; then rootfs_devfs=$(findfs //) fi if [ "$bootfs_devfs" = "" ]; then bootfs_devfs=$rootfs_devfs boot="boot/" else boot="" fi rootfs=$(mapdevfs $rootfs_devfs) bootfs=$(mapdevfs $bootfs_devfs) case "$(archdetect)" in powerpc/chrp_pegasos) kernel=$(ls /target/boot/vmlinuz-* | sed -e 's%/target/boot/%%') if [ -z "$kernel" ]; then kernelpath=$(ls /target/boot/vmlinux-* | sed -e 's%/target%%') version="${kernelpath#*vmlinux-}" if [ "$version" ]; then if apt-install mkvmlinuz; then # mkvmlinuz, initramfs-tools need proc, sys, dev in /target mountvirtfs proc /target/proc mountvirtfs sysfs /target/sys mountvirtfs devtmpfs /target/dev chroot /target /usr/sbin/update-initramfs -u -k "$version" chroot /target /usr/sbin/mkvmlinuz "$version" "$kernelpath" fi fi kernel=$(ls /target/boot/vmlinuz-* | sed -e 's%/target/boot/%%') fi partition_offset=1 if [ -e /proc/device-tree/openprom/firmware-version ]; then firmware_version="$(cat /proc/device-tree/openprom/firmware-version)" fv1="${firmware_version%%.*}" rest="${firmware_version#*.}" fv2="${rest%%.*}" rest="${rest#*.}" fv3="${rest%%.*}" if [ "$fv1" -eq 1 ]; then if [ "$fv2" -eq 3 ] && [ "$fv3" -ge 99 ]; then partition_offset=0 elif [ "$fv2" -ge 4 ]; then partition_offset=0 fi elif [ "$fv1" -ge 2 ]; then partition_offset=0 fi fi bootfs_disk_syspath= if [ -d /sys/block ]; then if type udevadm >/dev/null 2>&1; then bootfs_disk_syspath="$(dirname "$(udevadm info -q path -n "$bootfs_devfs")")" elif type udevinfo >/dev/null 2>&1; then bootfs_disk_syspath="$(dirname "$(udevinfo -q path -n "$bootfs_devfs")")" fi fi if [ "$bootfs_disk_syspath" ]; then # TODO: device symlinks are allegedly slated to go # away, but it's not entirely clear what their # replacement will be yet ... bootfs_disk="$(basename "$(readlink "/sys$bootfs_disk_syspath/device")")" kind="$(basename "$(readlink "/sys$bootfs_disk_syspath/device/bus")")" case $kind in ide) host="$(basename "$(dirname "$(readlink "/sys$bootfs_disk_syspath/device")")" | sed 's/[^0-9]*//')" # TODO: devfs set bus to hwif->channel, which # doesn't appear to be exposed. Since we only # support the first controller anyway, I'm hoping # that the host (hwif->index) will be good enough. bus="$(echo "$bootfs_disk" | cut -d. -f1)" target="$(echo "$bootfs_disk" | cut -d. -f2)" lun= ;; scsi) host="$(echo "$bootfs_disk" | cut -d: -f1)" bus="$(echo "$bootfs_disk" | cut -d: -f2)" target="$(echo "$bootfs_disk" | cut -d: -f3)" lun="$(echo "$bootfs_disk" | cut -d: -f4)" ;; esac part="$(($(echo "$bootfs_devfs" | sed 's/^.*[^0-9]//') - $partition_offset))" else kind=$(echo $bootfs_devfs | sed -e 's%/dev/%%' -e 's%/host.*$%%') host=$(echo $bootfs_devfs | sed -e 's%^.*host%%' -e 's%/bus.*$%%') bus=$(echo $bootfs_devfs | sed -e 's%^.*bus%%' -e 's%/target.*$%%') target=$(echo $bootfs_devfs | sed -e 's%^.*target%%' -e 's%/lun.*$%%') lun=$(echo $bootfs_devfs | sed -e 's%^.*lun%%' -e 's%/part.*$%%') part="$(($(echo "$bootfs_devfs" | sed -e 's%^.*part%%') - $partition_offset))" fi # We don't know how to map non ide or scsi disks # and we have trouble when there is more than one such controller. case "$kind","$host" in ide,0) path="/pci/ide/disk@$bus,$target" ;; scsi,0) path="/pci/scsi/disk@$bus,$target,$lun" ;; *) path="hd" ;; esac # map theidevice to the OF aliases from /proc/device-tree/aliases. if [ -d /proc/device-tree/aliases ]; then for alias in $(ls /proc/device-tree/aliases/*); do device=$(grep disk $alias | sed -e 's%@[^/]*/%/%g') if [ "$path" = "$device" ]; then path="${alias#/proc/device-tree/aliases/}" fi done fi bootcmd="boot ${path}:${part} ${boot}vmlinuz root=${rootfs}" template=nobootloader/confirmation_powerpc_chrp_pegasos db_subst $template KERNEL_BOOT "${bootcmd}" db_subst $template OF_BOOT_DEVICE "${path}:${part}" db_subst $template OF_BOOT_FILE "${boot}vmlinuz root=${rootfs}" db_input high $template || true ;; powerpc/pasemi) # TODO: Need to figure out if we need to generate the ramdisk # TODO: Is this the right kernel path? # TODO: Need to generate the device name based on actual disk used kernel=vmlinuz initrd=initrd template=nobootloader/confirmation_powerpc_pasemi db_subst $template INITRD "sata0.0:/${boot}${initrd}" db_subst $template KERNFILE "sata0.0:/${boot}${kernel}" db_subst $template BOOTARGS "root=$rootfs" db_input high $template || true ;; hurd-i386/*|hurd-amd64/*) kernel=gnumach.gz template=nobootloader/confirmation_common db_subst $template ROOT "root=device:${rootfs#/dev/}" db_subst $template BOOT "${bootfs}" db_subst $template KERNEL "${kernel}" db_input high $template || true ;; *) db_get base-installer/kernel/linux/link_in_boot link_in_boot="$RET" if [ "$link_in_boot" = "true" ]; then boot_link="boot/" else boot_link="" boot="" bootfs=${rootfs} fi if [ -e /target/${boot_link}vmlinuz ]; then kernel="/${boot}vmlinuz" elif [ -e /target/${boot_link}vmlinux ]; then kernel="/${boot}vmlinux" fi uparams=$(user-params) || true template=nobootloader/confirmation_common db_subst $template ROOT "root=${rootfs} ${uparams}" db_subst $template BOOT "${bootfs}" db_subst $template KERNEL "${kernel}" db_input high $template || true ;; esac db_go || true