Created
December 21, 2010 22:58
-
-
Save bcantrill/750766 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/ksh -p | |
# | |
# Copyright 2008 Sun Microsystems, Inc. All rights reserved. | |
# Use is subject to license terms. | |
# | |
#ident "@(#)mkusb.ksh 1.1 08/05/14 SMI" | |
# | |
# mkusb | |
# | |
# Given an AK ISO image (output by mkak -I), generate a bootable USB stick | |
# by mounting the ISO, formatting the USB stick with a Solaris partition, | |
# copying the ISO content there, and then installing bootable GRUB. | |
# | |
if [[ $# -ne 2 ]]; then | |
echo "Usage: $0 file.iso /dev/rdsk/<usb>p0" >& 2 | |
exit 2 | |
fi | |
function fail | |
{ | |
cd / | |
if [[ -n "$lofidev" ]]; then | |
umount $rmnt >/dev/null 2>&1 | |
lofiadm -d $lofidev >/dev/null 2>&1 | |
fi | |
umount $wmnt >/dev/null 2>&1 | |
rmdir $rmnt $wmnt >/dev/null 2>&1 | |
echo "$0: $*" >&2 | |
exit 1 | |
} | |
iso=$1 | |
pdsk=$2 | |
rdsk=${pdsk%p0} | |
dsk=$(echo $rdsk | sed 's:/rdsk:/dsk:') | |
rmnt=/tmp/mkusb-r.$$ | |
wmnt=/tmp/mkusb-w.$$ | |
rm -rf $rmnt $wmnt >/dev/null 2>&1 | |
mkdir -m 0700 $rmnt || fail "failed to mkdir: $rmnt" | |
mkdir -m 0700 $wmnt || fail "failed to mkdir: $wmnt" | |
[[ -r $iso ]] || fail "ISO is missing or not readable: $iso" | |
lofidev=$(lofiadm -a $iso) | |
[[ -n "$lofidev" ]] || fail "failed to mount ISO: $iso" | |
mount -F hsfs -o ro $lofidev $rmnt | |
rlofidev=$(echo $lofidev | sed s/lofi/rlofi/) | |
rmformat -l $pdsk 2>/dev/null | grep 'Bus: USB' >/dev/null 2>&1 || | |
fail "USB device path does not appear to be valid: $pdsk" | |
echo "Formatting USB device ... \c" | |
fdisk -B $pdsk || fail "failed to create USB partition" | |
set -- $(rmformat -l $pdsk 2>/dev/null | \ | |
egrep '(Device|Size):' | cut -d: -f2-) | |
eval $(prtvtoc $pdsk | grep '^\*' | awk ' | |
$3 == "bytes/sector" { printf("bytes_per_sec=%s\n", $2); } | |
$3 == "sectors/cylinder" { printf("secs_per_cyl=%s\n", $2); } | |
$3 == "accessible" { printf("cylinders=%s\n", $2); }') | |
[[ -z "$bytes_per_sec" || -z "$secs_per_cyl" || -z "$cylinders" ]] && \ | |
fail "failed to read vtoc attributes for $pdsk" | |
let sectors="$cylinders * $secs_per_cyl" | |
grub_sec0=0 | |
grub_secs=$secs_per_cyl | |
grub_part=s8 | |
let root_sec0="$grub_sec0 + $grub_secs" | |
let root_secs="$sectors - $root_sec0" | |
root_part=s0 | |
dump_sec0=0 | |
dump_secs=$sectors | |
dump_part=s2 | |
[[ $root_sec0 -lt $sectors ]] || fail "root disk too small" | |
fmthard -s - $pdsk >/dev/null <<-EOF | |
${root_part#s} 2 0x00 $root_sec0 $root_secs | |
${dump_part#s} 5 0x00 $dump_sec0 $dump_secs | |
${grub_part#s} 1 0x01 $grub_sec0 $grub_secs | |
EOF | |
[[ $? -eq 0 ]] && echo "$*" || fail "failed to format USB stick" | |
newfs -m 0 $rdsk$root_part </dev/null 2>/dev/null || "failed to newfs USB stick" | |
mount -F ufs $dsk$root_part $wmnt || fail "failed to mount USB stick" | |
echo "Copying ISO contents to USB ... " | |
cd $rmnt && find . -depth -print | cpio -pdVmu $wmnt || fail "cpio failed" | |
echo "Editing USB boot menu ... \c" | |
mv -f $wmnt/boot/grub/menu.lst $wmnt/boot/grub/menu.lst.iso | |
sed 's/ak_media=cd/ak_media=usb/g' $wmnt/boot/grub/menu.lst.iso \ | |
>$wmnt/boot/grub/menu.lst || fail "failed to edit menu file" | |
chmod 0444 $wmnt/boot/grub/menu.lst | |
echo "done." | |
echo "Installing USB boot ... \c" | |
installgrub -f -m $wmnt/boot/grub/stage1 $wmnt/boot/grub/stage2 \ | |
$rdsk$root_part >/dev/null || fail "installgrub to $rdsk$root_part failed" | |
cd / | |
echo "done." | |
umount $wmnt | |
umount $rmnt | |
lofiadm -d $lofidev | |
echo "done." | |
exit 0 |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment