Note lz4 compression in help
[livecd.git] / tools / livecd-iso-to-disk.sh
blobcbbdd949054edfaea36963744c049dc2d15c08b2
1 #!/bin/bash
2 # Transfer a Live image so that it's bootable off of a USB/SD device.
3 # Copyright 2007-2012 Red Hat, Inc.
5 # Jeremy Katz <katzj@redhat.com>
6 # Brian C. Lane <bcl@redhat.com>
8 # overlay/persistence enhancements by Douglas McClendon <dmc@viros.org>
9 # GPT+MBR hybrid enhancements by Stewart Adam <s.adam@diffingo.com>
11 # This program is free software; you can redistribute it and/or modify
12 # it under the terms of the GNU General Public License as published by
13 # the Free Software Foundation; version 2 of the License.
15 # This program is distributed in the hope that it will be useful,
16 # but WITHOUT ANY WARRANTY; without even the implied warranty of
17 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 # GNU Library General Public License for more details.
20 # You should have received a copy of the GNU General Public License
21 # along with this program; if not, write to the Free Software
22 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
25 export PATH=/sbin:/usr/sbin:$PATH
27 shortusage() {
28 echo "
29 SYNTAX
31 livecd-iso-to-disk [--help] [--noverify] [--format] [--msdos] [--reset-mbr]
32 [--efi] [--skipcopy] [--force] [--xo] [--xo-no-home]
33 [--timeout <time>] [--totaltimeout <time>]
34 [--extra-kernel-args <args>] [--multi] [--livedir <dir>]
35 [--compress] [--skipcompress] [--swap-size-mb <size>]
36 [--overlay-size-mb <size>] [--home-size-mb <size>]
37 [--delete-home] [--crypted-home] [--unencrypted-home]
38 [--updates updates.img] [--ks kickstart] [--label label]
39 <source> <target device>
41 (Enter livecd-iso-to-disk --help on the command line for more information.)"
44 usage() {
45 echo "
47 shortusage
48 echo "
49 livecd-iso-to-disk - Transfer a LiveOS image so that it's bootable off of
50 a USB/SD device.
52 The script may be run in simplest form with just the two arguments:
54 <source>
55 This may be the filesystem path to a LiveOS .iso image file,
56 such as from a CD-ROM, DVD, or download. It could also be the
57 device node reference for the mount point of another LiveOS
58 filesystem, including the currently-running one (such as a
59 booted Live CD/DVD/USB, where /dev/live references the running
60 image device).
62 <target device>
63 This should be the device partition name for the attached,
64 target device, such as /dev/sdb1 or /dev/sdc1. (Issue the
65 df -Th command to get a listing of the mounted partitions,
66 where you can confirm the filesystem types, available space,
67 and device names.) Be careful to specify the correct device,
68 or you may overwrite important data on another disk!
70 To execute the script to completion, you will need to run it with root user
71 permissions.
72 SYSLINUX must be installed on the computer running the installation script.
74 DESCRIPTION
76 livecd-iso-to-disk installs a Live CD/DVD/USB image (LiveOS) onto a USB/SD
77 storage device (or any storage partition that will boot with a SYSLINUX
78 bootloader). The target storage device can then boot the installed
79 operating system on systems that support booting via the USB or the SD
80 interface. The script requires a LiveOS source image and a target storage
81 device. The source image may be either a LiveOS .iso file, the currently-
82 running LiveOS image, the device node reference for an attached device with
83 an installed LiveOS image, or a file backed by a block device with an
84 installed LiveOS image. If the operating system supports persistent
85 overlays for saving system changes, a pre-sized overlay may be included with
86 the installation.
88 Unless you request the --format option, the installation does not destroy
89 data outside of the LiveOS, syslinux, & EFI folders on your target device.
90 This allows one to maintain other files on the target disk outside of the
91 LiveOS filesystem.
93 LiveOS images provide embedded filesystems through the Device-mapper
94 component of the Linux kernel. The embedded filesystems exist within files
95 such as /LiveOS/squashfs.img (the default compressed storage) or
96 /LiveOS/ext3fs.img (an uncompressed version) on the primary volume partition
97 of the storage device. In use, these are read-only filesystems. Optionally,
98 one may specify a persistent LiveOS overlay to hold image-change snapshots
99 (that use write-once, difference-tracking storage) in the
100 /LiveOS/overlay-<device_id> file, which, *one should note*, always grows in
101 size due to the storage mechanism. (The fraction of allocated space that
102 has been consumed by system activity and changes may be displayed by issuing
103 the 'dmsetup status' command in a terminal session of a running LiveOS
104 image.) One way to conserve the unrecoverable, overlay file space, is to
105 specify a persistent home folder for user files, which will be saved in a
106 /LiveOS/home.img filesystem image file. This file space is encrypted by
107 default, but is not compressed. (One may bypass encryption with the
108 --unencrypted-home installation option.) Files in this home folder may be
109 erased to recover and reuse their storage space. The home.img file is also
110 convenient for backing up or swapping user account files.
112 OPTIONS
114 --help
115 Displays usage information and exits.
117 --noverify
118 Disables the image validation process that occurs before the image is
119 installed from the original Live CD .iso image. When this option is
120 specified, the image is not verified before loading onto the target
121 storage device.
123 --format
124 Formats the target device and creates an MS-DOS partition table (or GPT
125 partition table, if the --efi option is passed).
127 --msdos
128 Forces format to use msdos instead of ext4.
130 --reset-mbr
131 Sets the Master Boot Record (MBR) of the target storage device to the
132 mbr.bin file from the installation system's syslinux directory. This
133 may be helpful in recovering a damaged or corrupted device.
135 --efi
136 Creates a GUID partition table when --format is passed, and installs a
137 hybrid Extensible Firmware Interface (EFI)/MBR bootloader on the disk.
138 This is necessary for most Intel Macs.
140 --skipcopy
141 Skips the copying of the live image to the target device, bypassing the
142 actions of the --format, --overlay-size-mb, --home-size-mb, &
143 --swap-size-mb options, if present on the command line. (The --skipcopy
144 option may be used while testing the script, in order to avoid repeated
145 and lengthy copy commands, or to repair boot configuration files on a
146 previously installed device.)
148 --force
149 This option allows the installation script to bypass a delete
150 confirmation dialog in the event that a pre-existing LiveOS directory
151 is found on the target device.
153 --xo
154 Used to prepare an image for the OLPC XO-1 laptop with its compressed,
155 JFFS2 filesystem. Do not use the following options with --xo:
156 --overlay-size-mb <size>, home-size-mb <size>, --delete-home,
157 --compress
159 --xo-no-home
160 Used together with the --xo option to prepare an image for an OLPC XO
161 laptop with the home folder on an SD card instead of the internal flash
162 storage.
164 --timeout
165 Modifies the bootloader's timeout value, which indicates how long to
166 pause at the boot: prompt before booting automatically. This overrides
167 the value set during iso creation. Units are 1/10 s. The timeout is
168 canceled when any key is pressed, the assumption being that the user
169 will complete the command line. A timeout of zero will disable the
170 timeout completely.
172 --totaltimeout
173 Adds a bootloader totaltimeout, which indicates how long to wait before
174 booting automatically. This is used to force an automatic boot. This
175 timeout cannot be canceled by the user. Units are 1/10 s.
177 --extra-kernel-args <args>
178 Specifies additional kernel arguments, <args>, that will be inserted
179 into the syslinux and EFI boot configurations. Multiple arguments
180 should be specified in one string, i.e.,
181 --extra-kernel-args \"arg1 arg2 ...\"
183 --multi
184 Used when installing multiple image copies to signal configuration of
185 the boot files for the image in the --livedir <dir> parameter.
188 --livedir <dir>
189 Used with multiple image installations to designate the directory <dir>
190 for the particular image.
192 --compress (default state for the operating system files)
193 The default, compressed SquashFS filesystem image is copied on
194 installation. This option has no effect when the source filesystem is
195 already expanded.
197 --skipcompress (default option when --xo is specified)
198 Expands the source SquashFS image on installation into the read-only
199 /LiveOS/ext3fs.img filesystem image file.
201 --swap-size-mb <size>
202 Sets up a swap file of <size> mebibytes (integer values only) on the
203 target device.
205 --overlay-size-mb <size>
206 This option sets the overlay size in mebibytes (integer values only).
207 The overlay makes persistent storage available to the live operating
208 system, if the operating system supports it. The persistent LiveOS
209 overlay holds image-change snapshots (using write-once, difference-
210 tracking storage) in the /LiveOS/overlay-<device_id> file, which, *one
211 should note*, always grows in size due to the storage mechanism. (The
212 fraction of allocated space that has been consumed may be displayed by
213 issuing the 'dmsetup status' command in a terminal session of a running
214 LiveOS installation.) One way to conserve the unrecoverable, overlay
215 file space, is to specify a persistent home folder for user files, see
216 --home-size-mb below. The target storage device must have enough free
217 space for the image and the overlay. A maximum <size> of 4095 MiB is
218 permitted for vfat-formatted devices. If there is insufficient room on
219 your device, you will be given information to help in adjusting your
220 settings.
222 --home-size-mb <size>
223 Sets the home directory size in mebibytes (integer values only). A
224 persistent home directory will be made in the /LiveOS/home.img
225 filesystem image file. This file space is encrypted by default, but not
226 compressed (one may bypass encryption with the --unencrypted-home
227 installation option). Files in this home folder may be erased to
228 recover and reuse their storage space. The target storage device must
229 have enough free space for the image, any overlay, and the home
230 directory. Note that the --delete-home option must also be selected to
231 replace an existing persistent home with a new, empty one. A maximum
232 <size> of 4095 MiB is permitted for vfat-formatted devices. If there is
233 insufficient room on your device, you will be given information to help
234 in adjusting your settings.
236 --delete-home
237 To prevent unwitting deletion of user files, this option must be
238 explicitly selected when the option --home-size-mb <size> is selected
239 and there is an existing persistent home directory on the target device.
241 --crypted-home (default that only applies to new home-size-mb requests)
242 Specifies the default option to encrypt a new persistent home directory
243 if --home-size-mb <size> is specified.
245 --unencrypted-home
246 Prevents the default option to encrypt a new persistent home directory.
248 --updates updates.img
249 Setup inst.updates to point to an updates image on the device. Anaconda
250 uses this for testing updates to an iso without needing to make a new iso.
252 --ks kickstart
253 Setup inst.ks to point to an kickstart file on the device. Use this for
254 automating installs on boot.
256 --label label
257 Specifies a specific label instead of default LIVE. Useful when you do
258 unattended installs which pas a label to inst.ks
260 CONTRIBUTORS
262 livecd-iso-to-disk: David Zeuthen, Jeremy Katz, Douglas McClendon,
263 Chris Curran and other contributors.
264 (See the AUTHORS file in the source distribution for
265 the complete list of credits.)
267 BUGS
269 Report bugs to the mailing list
270 http://admin.fedoraproject.org/mailman/listinfo/livecd or directly to
271 Bugzilla http://bugzilla.redhat.com/bugzilla/ against the Fedora product,
272 and the livecd-tools component.
274 COPYRIGHT
276 Copyright (C) Fedora Project 2008, 2009, 2010 and various contributors.
277 This is free software. You may redistribute copies of it under the terms of
278 the GNU General Public License http://www.gnu.org/licenses/gpl.html.
279 There is NO WARRANTY, to the extent permitted by law.
281 SEE ALSO
283 livecd-creator, project website http://fedoraproject.org/wiki/FedoraLiveCD
285 exit 1
288 cleanup() {
289 sleep 2
290 [ -d "$SRCMNT" ] && umount $SRCMNT && rmdir $SRCMNT
291 [ -d "$TGTMNT" ] && umount $TGTMNT && rmdir $TGTMNT
294 exitclean() {
295 RETVAL=$?
296 if [ -d "$SRCMNT" ] || [ -d "$TGTMNT" ];
297 then
298 [ "$RETVAL" = 0 ] || echo "Cleaning up to exit..."
299 cleanup
301 exit $RETVAL
304 isdevloop() {
305 [ x"${1#/dev/loop}" != x"$1" ]
308 # Return the matching file ignoring case or 1 if no match
309 nocase_path() {
310 local ret=0
311 shopt -s nocaseglob
312 [ -e "$1" ] || ret=1
313 echo $1
314 shopt -u nocaseglob
315 return $ret
318 getdisk() {
319 DEV=$1
321 if isdevloop "$DEV"; then
322 device="$DEV"
323 return
326 p=$(udevadm info -q path -n $DEV)
327 if [ $? -gt 0 ]; then
328 echo "Error getting udev path to $DEV"
329 exitclean
331 if [ -e /sys/$p/device ]; then
332 device=$(basename /sys/$p)
333 else
334 device=$(basename $(readlink -f /sys/$p/../))
336 if [ ! -e /sys/block/$device -o ! -e /dev/$device ]; then
337 echo "Error finding block device of $DEV. Aborting!"
338 exitclean
341 device="/dev/$device"
342 # FIXME: weird dev names could mess this up I guess
343 p=/dev/$(basename $p)
344 partnum=${p##$device}
347 resetMBR() {
348 if isdevloop "$DEV"; then
349 return
351 getdisk $1
352 # if efi, we need to use the hybrid MBR
353 if [ -n "$efi" ]; then
354 if [ -f /usr/lib/syslinux/gptmbr.bin ]; then
355 cat /usr/lib/syslinux/gptmbr.bin > $device
356 elif [ -f /usr/share/syslinux/gptmbr.bin ]; then
357 cat /usr/share/syslinux/gptmbr.bin > $device
358 else
359 echo "Could not find gptmbr.bin (syslinux)"
360 exitclean
362 # Make it bootable on EFI and BIOS
363 parted -s $device set $partnum legacy_boot on
364 else
365 if [ -f /usr/lib/syslinux/mbr.bin ]; then
366 cat /usr/lib/syslinux/mbr.bin > $device
367 elif [ -f /usr/share/syslinux/mbr.bin ]; then
368 cat /usr/share/syslinux/mbr.bin > $device
369 else
370 echo "Could not find mbr.bin (syslinux)"
371 exitclean
376 checkMBR() {
377 if isdevloop "$DEV"; then
378 return 0
380 getdisk $1
382 bs=$(mktemp /tmp/bs.XXXXXX)
383 dd if=$device of=$bs bs=512 count=1 2>/dev/null || exit 2
385 mbrword=$(hexdump -n 2 $bs |head -n 1|awk {'print $2;'})
386 rm -f $bs
387 if [ "$mbrword" = "0000" ]; then
388 if [ -z "$format" ]; then
389 echo "MBR appears to be blank."
390 echo "Press Enter to replace the MBR and continue or ctrl-c to abort"
391 read
393 resetMBR $1
396 return 0
399 checkPartActive() {
400 dev=$1
401 getdisk $dev
403 # if we're installing to whole-disk and not a partition, then we
404 # don't need to worry about being active
405 if [ "$dev" = "$device" ]; then
406 return
408 if isdevloop "$DEV"; then
409 return
412 if [ "$(/sbin/fdisk -l $device 2>/dev/null |grep -m1 $dev |awk {'print $2;'})" != "*" ]; then
413 echo "Partition isn't marked bootable!"
414 echo "You can mark the partition as bootable with "
415 echo " # /sbin/parted $device"
416 echo " (parted) toggle N boot"
417 echo " (parted) quit"
418 exitclean
422 checkLVM() {
423 dev=$1
425 if [ -x /sbin/pvs -a \
426 "$(/sbin/pvs -o vg_name --noheadings $dev* 2>/dev/null || :)" ]; then
427 echo "Device, $dev, contains a volume group and cannot be formated!"
428 echo "You can remove the volume group using vgremove."
429 exitclean
431 return 0
434 createGPTLayout() {
435 dev=$1
436 getdisk $dev
438 echo "WARNING: THIS WILL DESTROY ANY DATA ON $device!!!"
439 echo "Press Enter to continue or ctrl-c to abort"
440 read
441 umount ${device}* &> /dev/null || :
442 wipefs -a ${device}
443 /sbin/parted --script $device mklabel gpt
444 partinfo=$(LC_ALL=C /sbin/parted --script -m $device "unit MB print" |grep ^$device:)
445 dev_size=$(echo $partinfo |cut -d : -f 2 |sed -e 's/MB$//')
446 p1_size=$(($dev_size - 3))
448 if [ $p1_size -le 0 ]; then
449 echo "Your device isn't big enough to hold $SRC"
450 echo "It is $(($p1_size * -1)) MB too small"
451 exitclean
453 p1_start=1
454 p1_end=$(($p1_size + 1))
455 /sbin/parted -s $device u MB mkpart '"EFI System Partition"' fat32 $p1_start $p1_end set 1 boot on
456 # Sometimes automount can be _really_ annoying.
457 echo "Waiting for devices to settle..."
458 /sbin/udevadm settle
459 sleep 5
460 TGTDEV=${device}1
461 umount $TGTDEV &> /dev/null || :
462 /sbin/mkdosfs -n $label $TGTDEV
463 TGTLABEL="UUID=$(/sbin/blkid -s UUID -o value $TGTDEV)"
466 createMSDOSLayout() {
467 dev=$1
468 getdisk $dev
470 echo "WARNING: THIS WILL DESTROY ANY DATA ON $device!!!"
471 echo "Press Enter to continue or ctrl-c to abort"
472 read
473 umount ${device}* &> /dev/null || :
474 wipefs -a ${device}
475 /sbin/parted --script $device mklabel msdos
476 partinfo=$(LC_ALL=C /sbin/parted --script -m $device "unit MB print" |grep ^$device:)
477 dev_size=$(echo $partinfo |cut -d : -f 2 |sed -e 's/MB$//')
478 p1_size=$(($dev_size - 3))
480 if [ $p1_size -le 0 ]; then
481 echo "Your device isn't big enough to hold $SRC"
482 echo "It is $(($p1_size * -1)) MB too small"
483 exitclean
485 p1_start=1
486 p1_end=$(($p1_size + 1))
487 /sbin/parted -s $device u MB mkpart primary fat32 $p1_start $p1_end set 1 boot on
488 # Sometimes automount can be _really_ annoying.
489 echo "Waiting for devices to settle..."
490 /sbin/udevadm settle
491 sleep 5
492 if ! isdevloop "$DEV"; then
493 TGTDEV=${device}1
494 else
495 TGTDEV=${device}
497 umount $TGTDEV &> /dev/null || :
498 /sbin/mkdosfs -n LIVE $TGTDEV
499 TGTLABEL="UUID=$(/sbin/blkid -s UUID -o value $TGTDEV)"
502 createEXTFSLayout() {
503 dev=$1
504 getdisk $dev
506 echo "WARNING: THIS WILL DESTROY ANY DATA ON $device!!!"
507 echo "Press Enter to continue or ctrl-c to abort"
508 read
509 umount ${device}* &> /dev/null || :
510 wipefs -a ${device}
511 /sbin/parted -s $device mklabel msdos
512 partinfo=$(LC_ALL=C /sbin/parted -s -m $device "u MB print" |grep ^$device:)
513 dev_size=$(echo $partinfo |cut -d : -f 2 |sed -e 's/MB$//')
514 p1_size=$(($dev_size - 3))
516 if [ $p1_size -le 0 ]; then
517 echo "Your device isn't big enough to hold $SRC"
518 echo "It is $(($p1_size * -1)) MB too small"
519 exitclean
521 p1_start=1
522 p1_end=$(($p1_size + 1))
523 /sbin/parted -s $device u MB mkpart primary ext2 $p1_start $p1_end set 1 boot on
524 # Sometimes automount can be _really_ annoying.
525 echo "Waiting for devices to settle..."
526 /sbin/udevadm settle
527 sleep 5
528 TGTDEV=${device}1
529 umount $TGTDEV &> /dev/null || :
531 # Check extlinux version
532 if extlinux -v 2>&1 | grep -q 'extlinux 3'; then
533 mkfs=/sbin/mkfs.ext3
534 else
535 mkfs=/sbin/mkfs.ext4
537 $mkfs -L $label $TGTDEV
538 TGTLABEL="UUID=$(/sbin/blkid -s UUID -o value $TGTDEV)"
541 checkGPT() {
542 dev=$1
543 getdisk $dev
545 if [ "$(LC_ALL=C /sbin/parted -m $device p 2>/dev/null |grep -ic :gpt:)" -eq "0" ]; then
546 echo "EFI boot requires a GPT partition table."
547 echo "This can be done manually or you can run with --format"
548 exitclean
551 partinfo=$(LC_ALL=C /sbin/parted --script -m $device "print" |grep ^$partnum:)
552 volname=$(echo $partinfo |cut -d : -f 6)
553 flags=$(echo $partinfo |cut -d : -f 7)
554 if [ "$volname" != "EFI System Partition" ]; then
555 echo "Partition name must be 'EFI System Partition'"
556 echo "This can be set in parted or you can run with --reset-mbr"
557 exitclean
559 if [ "$(echo $flags |grep -c boot)" = "0" ]; then
560 echo "Partition isn't marked bootable!"
561 echo "You can mark the partition as bootable with "
562 echo " # /sbin/parted $device"
563 echo " (parted) toggle N boot"
564 echo " (parted) quit"
565 exitclean
569 checkFilesystem() {
570 dev=$1
572 TGTFS=$(/sbin/blkid -s TYPE -o value $dev || :)
573 if [ "$TGTFS" != "vfat" ] && [ "$TGTFS" != "msdos" ]; then
574 if [ "$TGTFS" != "ext2" ] && [ "$TGTFS" != "ext3" ] && [ "$TGTFS" != "ext4" ] && [ "$TGTFS" != "btrfs" ]; then
575 echo "Target filesystem ($dev:$TGTFS) must be vfat, ext[234] or btrfs"
576 exitclean
580 if [ "$TGTFS" = "ext2" -o "$TGTFS" = "ext3" -o "$TGTFS" = "ext4" ] && [ ! -x /usr/sbin/extlinux ]; then
581 echo "Target filesystem ($TGTFS) requires syslinux-extlinux to be installed."
582 exitclean
586 TGTLABEL=$(/sbin/blkid -s LABEL -o value $dev)
587 if [ "$TGTLABEL" != "$label" ]; then
588 if [ "$TGTFS" = "vfat" -o "$TGTFS" = "msdos" ]; then
589 /sbin/dosfslabel $dev $label
590 if [ $? -gt 0 ]; then
591 echo "dosfslabel failed on $dev, device not setup"
592 exitclean
594 elif [ "$TGTFS" = "ext2" -o "$TGTFS" = "ext3" -o "$TGTFS" = "ext4" ]; then
595 /sbin/e2label $dev $label
596 if [ $? -gt 0 ]; then
597 echo "e2label failed on $dev, device not setup"
598 exitclean
600 else
601 echo "Unknown filesystem type. Try setting its label to $label and re-running"
602 exitclean
606 # Use UUID if available
607 TGTUUID=$(/sbin/blkid -s UUID -o value $dev)
608 if [ -n "$TGTUUID" ]; then
609 TGTLABEL="UUID=$TGTUUID"
610 else
611 TGTLABEL="LABEL=$label"
614 if [ "$TGTFS" = "vfat" -o "$TGTFS" = "msdos" ]; then
615 mountopts="-o shortname=winnt,umask=0077"
619 checkSyslinuxVersion() {
620 if [ ! -x /usr/bin/syslinux ]; then
621 echo "You need to have syslinux installed to run this script"
622 exit 1
624 check=($(syslinux --version 2>&1)) || :
625 if [[ 'syslinux' != $check ]]; then
626 SYSLINUXPATH=""
627 elif [ -n "$multi" ]; then
628 SYSLINUXPATH="$LIVEOS/syslinux"
629 else
630 SYSLINUXPATH="syslinux"
634 checkMounted() {
635 dev=$1
636 if grep -q "^$dev " /proc/mounts ; then
637 echo "$dev is mounted, please unmount for safety"
638 exitclean
640 if grep -q "^$dev " /proc/swaps; then
641 echo "$dev is in use as a swap device, please disable swap"
642 exitclean
646 checkint() {
647 if ! test $1 -gt 0 2>/dev/null ; then
648 shortusage
649 exit 1
653 if [ $(id -u) != 0 ]; then
654 echo "You need to be root to run this script"
655 exit 1
658 detectsrctype() {
659 if [[ -e "$SRCMNT/Packages" ]]; then
660 echo "/Packages found, will copy source packages to target"
661 packages=1
663 if [[ -e "$SRCMNT/LiveOS/squashfs.img" ]]; then
664 # LiveOS style boot image
665 srctype=live
666 return
668 if [ -e $SRCMNT/images/install.img -o -e $SRCMNT/isolinux/initrd.img ]; then
669 if [ -n "$packages" ]; then
670 srctype=installer
671 else
672 srctype=netinst
674 imgtype=install
675 if [ ! -e $SRCMNT/images/install.img ]; then
676 echo "$SRC uses initrd.img w/o install.img"
677 imgtype=initrd
679 return
681 echo "ERROR: $SRC does not appear to be a Live image or DVD installer."
682 exitclean
685 cp_p() {
686 strace -q -ewrite cp -- "${1}" "${2}" 2>&1 \
687 | awk '{
688 count += $NF
689 if (count % 10 == 0) {
690 percent = count / total_size * 100
691 printf "%3d%% [", percent
692 for (i=0;i<=percent;i++)
693 printf "="
694 printf ">"
695 for (i=percent;i<100;i++)
696 printf " "
697 printf "]\r"
700 END { print "" }' total_size=$(stat -c '%s' "${1}") count=0
703 copyFile() {
704 if [ -x /usr/bin/rsync ]; then
705 rsync --inplace -P "$1" "$2"
706 return
708 if [ -x /usr/bin/gvfs-copy ]; then
709 gvfs-copy -p "$1" "$2"
710 return
712 if [ -x /usr/bin/strace -a -x /bin/awk ]; then
713 cp_p "$1" "$2"
714 return
716 cp "$1" "$2"
719 set -e
720 set -o pipefail
721 trap exitclean EXIT
722 shopt -s extglob
724 cryptedhome=1
725 keephome=1
726 homesizemb=0
727 swapsizemb=0
728 overlaysizemb=0
729 srctype=
730 imgtype=
731 packages=
732 LIVEOS=LiveOS
733 HOMEFILE="home.img"
734 updates=
736 label="LIVE"
738 while true ; do
739 case $1 in
740 --help | -h | -?)
741 usage
743 --noverify)
744 noverify=1
746 --format)
747 format=1
749 --msdos)
750 usemsdos=1
752 --reset-mbr|--resetmbr)
753 resetmbr=1
755 --efi|--mactel)
756 efi=1
758 --skipcopy)
759 skipcopy=1
761 --force)
762 force=1
764 --xo)
765 xo=1
766 skipcompress=1
768 --xo-no-home)
769 xonohome=1
771 --timeout)
772 checkint $2
773 timeout=$2
774 shift
776 --totaltimeout)
777 checkint $2
778 totaltimeout=$2
779 shift
781 --extra-kernel-args)
782 kernelargs=$2
783 shift
785 --multi)
786 multi=1
788 --livedir)
789 LIVEOS=$2
790 shift
792 --compress)
793 skipcompress=""
795 --skipcompress)
796 skipcompress=1
798 --swap-size-mb)
799 checkint $2
800 swapsizemb=$2
801 shift
803 --overlay-size-mb)
804 checkint $2
805 overlaysizemb=$2
806 shift
808 --home-size-mb)
809 checkint $2
810 homesizemb=$2
811 shift
813 --crypted-home)
814 cryptedhome=1
816 --unencrypted-home)
817 cryptedhome=""
819 --delete-home)
820 keephome=""
822 --updates)
823 updates=$2
824 shift
826 --ks)
827 ks=$2
828 shift
830 --label)
831 label=$2
832 shift
834 --*)
835 echo "invalid arg -- $1"
836 shortusage
837 exit 1
840 break
842 esac
843 shift
844 done
846 if [ $# -ne 2 ]; then
847 echo "Missing arguments"
848 shortusage
849 exit 1
852 SRC=$(readlink -f "$1") || :
853 TGTDEV=$(readlink -f "$2") || :
855 if [ -z "$SRC" ]; then
856 echo "Missing source"
857 shortusage
858 exit 1
861 if [ ! -b "$SRC" -a ! -f "$SRC" ]; then
862 echo "$SRC is not a file or block device"
863 shortusage
864 exit 1
867 if [ -z "$TGTDEV" ]; then
868 echo "Missing target device"
869 shortusage
870 exit 1
873 if [ ! -b "$TGTDEV" ]; then
874 echo "$TGTDEV is not a block device"
875 shortusage
876 exit 1
879 if [ -z "$noverify" ]; then
880 # verify the image
881 echo "Verifying image..."
882 if ! checkisomd5 --verbose "$SRC"; then
883 echo "Are you SURE you want to continue?"
884 echo "Press Enter to continue or ctrl-c to abort"
885 read
889 # do some basic sanity checks.
890 checkMounted $TGTDEV
892 # FIXME: would be better if we had better mountpoints
893 SRCMNT=$(mktemp -d /media/srctmp.XXXXXX)
894 if [ -b "$SRC" ]; then
895 mount -o ro "$SRC" $SRCMNT || exitclean
896 elif [ -f "$SRC" ]; then
897 mount -o loop,ro "$SRC" $SRCMNT || exitclean
898 else
899 echo "$SRC is not a file or block device."
900 exitclean
902 # Figure out what needs to be done based on the source image
903 detectsrctype
905 # Format the device
906 if [ -n "$format" -a -z "$skipcopy" ]; then
907 checkLVM $TGTDEV
909 if [ -n "$efi" ]; then
910 createGPTLayout $TGTDEV
911 elif [ -n "$usemsdos" -o ! -x /sbin/extlinux ]; then
912 createMSDOSLayout $TGTDEV
913 else
914 createEXTFSLayout $TGTDEV
918 checkFilesystem $TGTDEV
919 if [ -n "$efi" ]; then
920 checkGPT $TGTDEV
923 checkSyslinuxVersion
924 # Because we can't set boot flag for EFI Protective on msdos partition tables
925 [ -z "$efi" ] && checkPartActive $TGTDEV
926 [ -n "$resetmbr" ] && resetMBR $TGTDEV
927 checkMBR $TGTDEV
930 if [ "$overlaysizemb" -gt 0 ]; then
931 if [ "$TGTFS" = "vfat" -a "$overlaysizemb" -gt 4095 ]; then
932 echo "Can't have an overlay of 4095MB or greater on VFAT"
933 exitclean
935 LABEL=$(/sbin/blkid -s LABEL -o value $TGTDEV)
936 if [[ "$LABEL" =~ ( ) ]]; then
937 echo "The LABEL($LABEL) on $TGTDEV has spaces in it, which do not work with the overlay"
938 echo "You can re-format or use dosfslabel/e2fslabel to change it"
939 exitclean
943 if [ "$homesizemb" -gt 0 -a "$TGTFS" = "vfat" ]; then
944 if [ "$homesizemb" -gt 4095 ]; then
945 echo "Can't have a home overlay greater than 4095MB on VFAT"
946 exitclean
950 if [ "$swapsizemb" -gt 0 -a "$TGTFS" = "vfat" ]; then
951 if [ "$swapsizemb" -gt 4095 ]; then
952 echo "Can't have a swap file greater than 4095MB on VFAT"
953 exitclean
957 TGTMNT=$(mktemp -d /media/tgttmp.XXXXXX)
958 mount $mountopts $TGTDEV $TGTMNT || exitclean
960 trap exitclean SIGINT SIGTERM
962 if [ -f "$TGTMNT/$LIVEOS/$HOMEFILE" -a -n "$keephome" -a "$homesizemb" -gt 0 ]; then
963 echo "ERROR: Requested keeping existing /home and specified a size for /home"
964 echo "Please either don't specify a size or specify --delete-home"
965 exitclean
968 if [ -n "$efi" ]; then
969 if [ -d $SRCMNT/EFI/BOOT ]; then
970 EFI_BOOT="/EFI/BOOT"
971 elif [ -d $SRCMNT/EFI/boot ]; then
972 EFI_BOOT="/EFI/boot"
973 else
974 echo "ERROR: This live image does not support EFI booting"
975 exitclean
979 # let's try to make sure there's enough room on the target device
980 if [[ -d $TGTMNT/$LIVEOS ]]; then
981 tbd=($(du -B 1M $TGTMNT/$LIVEOS))
982 if [[ -s $TGTMNT/$LIVEOS/$HOMEFILE ]] && [[ -n $keephome ]]; then
983 homesize=($(du -B 1M $TGTMNT/$LIVEOS/$HOMEFILE))
984 tbd=$((tbd - homesize))
986 else
987 tbd=0
990 if [[ live == $srctype ]]; then
991 targets="$TGTMNT/$SYSLINUXPATH"
992 [[ -n $efi ]] && targets+=" $TGTMNT$EFI_BOOT"
993 [[ -n $xo ]] && targets+=" $TGTMNT/boot/olpc.fth"
994 target_size=$(du -s -c -B 1M $targets 2> /dev/null | awk '/total$/ {print $1;}') || :
995 tbd=$((tbd + target_size))
998 if [[ -n $skipcompress ]] && [[ -s $SRCMNT/LiveOS/squashfs.img ]]; then
999 if mount -o loop $SRCMNT/LiveOS/squashfs.img $SRCMNT; then
1000 livesize=($(du -B 1M --apparent-size $SRCMNT/LiveOS/ext3fs.img))
1001 umount $SRCMNT
1002 if ((livesize > 4095)) && [[ vfat == $TGTFS ]]; then
1003 echo "
1004 An uncompressed image size greater than 4095 MB is not suitable
1005 for a VFAT-formatted device. The compressed SquashFS will be
1006 copied to the target device.
1008 skipcompress=""
1009 livesize=0
1011 else
1012 echo "WARNING: --skipcompress or --xo was specified but the
1013 currently-running kernel can not mount the SquashFS from the source
1014 file to extract it. Instead, the compressed SquashFS will be copied
1015 to the target device."
1016 skipcompress=""
1019 if [[ live == $srctype ]]; then
1020 thisScriptpath=$(readlink -f "$0")
1021 sources="$SRCMNT/LiveOS/ext3fs.img $SRCMNT/LiveOS/osmin.img"
1022 [[ -z $skipcompress ]] && sources+=" $SRCMNT/LiveOS/squashfs.img"
1023 sources+=" $SRCMNT/isolinux $SRCMNT/syslinux"
1024 [[ -n $efi ]] && sources+=" $SRCMNT$EFI_BOOT"
1025 [[ -n $xo ]] && sources+=" $SRCMNT/boot/olpc.fth"
1026 source_size=$(du -s -c -B 1M "$thisScriptpath" $sources 2> /dev/null | awk '/total$/ {print $1;}') || :
1027 livesize=$((livesize + source_size))
1030 freespace=$(df -B 1M --total $TGTDEV | awk '/^total/ {print $4;}')
1032 if [[ live == $srctype ]]; then
1033 tba=$((overlaysizemb + homesizemb + livesize + swapsizemb))
1034 if ((tba > freespace + tbd)); then
1035 needed=$((tba - freespace - tbd))
1036 printf "\n The live image + overlay, home, & swap space, if requested,
1037 \r will NOT fit in the space available on the target device.\n
1038 \r + Size of live image: %10s MiB\n" $livesize
1039 (($overlaysizemb > 0)) && \
1040 printf " + Overlay size: %16s\n" $overlaysizemb
1041 (($homesizemb > 0)) && \
1042 printf " + Home directory size: %9s\n" $homesizemb
1043 (($swapsizemb > 0)) && \
1044 printf " + Swap overlay size: %11s\n" $swapsizemb
1045 printf " = Total requested space: %6s MiB\n" $tba
1046 printf " - Space available: %12s\n" $((freespace + tbd))
1047 printf " ==============================\n"
1048 printf " Space needed: %15s MiB\n\n" $needed
1049 printf " To fit the installation on this device,
1050 \r free space on the target, or decrease the
1051 \r requested size total by: %6s MiB\n\n" $needed
1052 exitclean
1056 # Verify available space for DVD installer
1057 if [ "$srctype" = "installer" ]; then
1058 if [ "$imgtype" = "install" ]; then
1059 imgpath=images/install.img
1060 else
1061 imgpath=isolinux/initrd.img
1063 installimgsize=$(du -s -B 1M $SRCMNT/$imgpath | awk {'print $1;'})
1065 tbd=0
1066 if [ -e $TGTMNT/$imgpath ]; then
1067 tbd=$(du -s -B 1M $TGTMNT/$imgpath | awk {'print $1;'})
1069 if [ -e "$TGTMNT/$(basename "$SRC")" ]; then
1070 tbd=$(($tbd + $(du -s -B 1M "$TGTMNT/$(basename "$SRC")" | awk {'print $1;'})))
1072 echo "Size of $imgpath: $installimgsize"
1073 echo "Available space: $((freespace + tbd))"
1074 if (( installimgsize > ((freespace + tbd)) )); then
1075 echo "ERROR: Unable to fit DVD image + install.img on available space on the target device."
1076 exitclean
1080 if [ -z "$skipcopy" ] && [ "$srctype" = "live" ]; then
1081 if [ -d $TGTMNT/$LIVEOS -a -z "$force" ]; then
1082 echo "Already set up as live image."
1083 if [ -z "$keephome" -a -e $TGTMNT/$LIVEOS/$HOMEFILE ]; then
1084 echo "WARNING: Persistent /home will be deleted!!!"
1085 echo "Press Enter to continue or ctrl-c to abort"
1086 read
1087 else
1088 echo "Deleting old OS in fifteen seconds..."
1089 sleep 15
1091 [ -e "$TGTMNT/$LIVEOS/$HOMEFILE" -a -n "$keephome" ] && mv $TGTMNT/$LIVEOS/$HOMEFILE $TGTMNT/$HOMEFILE
1094 rm -rf $TGTMNT/$LIVEOS
1098 # Bootloader is always reconfigured, so keep these out of the if skipcopy stuff.
1099 [ ! -d $TGTMNT/$SYSLINUXPATH ] && mkdir -p $TGTMNT/$SYSLINUXPATH
1100 [ -n "$efi" -a ! -d $TGTMNT$EFI_BOOT ] && mkdir -p $TGTMNT$EFI_BOOT
1102 # Live image copy
1103 if [ "$srctype" = "live" -a -z "$skipcopy" ]; then
1104 echo "Copying live image to target device."
1105 [ ! -d $TGTMNT/$LIVEOS ] && mkdir $TGTMNT/$LIVEOS
1106 [ -n "$keephome" -a -f "$TGTMNT/$HOMEFILE" ] && mv $TGTMNT/$HOMEFILE $TGTMNT/$LIVEOS/$HOMEFILE
1107 if [ -n "$skipcompress" -a -f $SRCMNT/LiveOS/squashfs.img ]; then
1108 mount -o loop $SRCMNT/LiveOS/squashfs.img $SRCMNT || exitclean
1109 copyFile $SRCMNT/LiveOS/ext3fs.img $TGTMNT/$LIVEOS/ext3fs.img || {
1110 umount $SRCMNT ; exitclean ; }
1111 umount $SRCMNT
1112 elif [ -f $SRCMNT/LiveOS/squashfs.img ]; then
1113 copyFile $SRCMNT/LiveOS/squashfs.img $TGTMNT/$LIVEOS/squashfs.img || exitclean
1114 elif [ -f $SRCMNT/LiveOS/ext3fs.img ]; then
1115 copyFile $SRCMNT/LiveOS/ext3fs.img $TGTMNT/$LIVEOS/ext3fs.img || exitclean
1117 if [ -f $SRCMNT/LiveOS/osmin.img ]; then
1118 copyFile $SRCMNT/LiveOS/osmin.img $TGTMNT/$LIVEOS/osmin.img || exitclean
1120 sync
1123 # Adjust syslinux sources for replication of installed images
1124 # between filesystem types.
1125 if [[ -d $SRCMNT/isolinux/ ]]; then
1126 cp $SRCMNT/isolinux/* $TGTMNT/$SYSLINUXPATH
1127 elif [[ -d $SRCMNT/syslinux/ ]]; then
1128 cp $SRCMNT/syslinux/* $TGTMNT/$SYSLINUXPATH
1129 if [[ -f $SRCMNT/syslinux/extlinux.conf ]]; then
1130 mv $TGTMNT/$SYSLINUXPATH/extlinux.conf \
1131 $TGTMNT/$SYSLINUXPATH/isolinux.cfg
1132 elif [[ -f $SRCMNT/syslinux/syslinux.cfg ]]; then
1133 mv $TGTMNT/$SYSLINUXPATH/syslinux.cfg $TGTMNT/$SYSLINUXPATH/isolinux.cfg
1136 BOOTCONFIG=$TGTMNT/$SYSLINUXPATH/isolinux.cfg
1137 # Set this to nothing so sed doesn't care
1138 BOOTCONFIG_EFI=
1139 if [ -n "$efi" ]; then
1140 echo "Setting up $EFI_BOOT"
1141 cp -r $SRCMNT$EFI_BOOT/* $TGTMNT$EFI_BOOT
1143 # The GRUB EFI config file can be one of:
1144 # boot?*.conf
1145 # BOOT?*.conf
1146 # grub.cfg
1147 if [ -e $TGTMNT$EFI_BOOT/grub.cfg ]; then
1148 BOOTCONFIG_EFI=$TGTMNT$EFI_BOOT/grub.cfg
1149 elif [ -e $(nocase_path "$TGTMNT$EFI_BOOT/boot*.conf") ]; then
1150 BOOTCONFIG_EFI=$(nocase_path "$TGTMNT$EFI_BOOT/boot*.conf")
1151 else
1152 echo "Unable to find EFI config file."
1153 exitclean
1155 rm -f $TGTMNT$EFI_BOOT/grub.conf
1157 # On some images (RHEL) the BOOT*.efi file isn't in $EFI_BOOT, but is in
1158 # the eltorito image, so try to extract it if it is missing
1160 # test for presence of *.efi grub binary
1161 if [ ! -f $(nocase_path "$TGTMNT$EFI_BOOT/boot*efi") ]; then
1162 if [ ! -x /usr/bin/dumpet ]; then
1163 echo "No /usr/bin/dumpet tool found. EFI image will not boot."
1164 echo "Source media is missing grub binary in /EFI/BOOT/*EFI"
1165 exitclean
1166 else
1167 # dump the eltorito image with dumpet, output is $SRC.1
1168 dumpet -i "$SRC" -d
1169 EFIMNT=$(mktemp -d /media/srctmp.XXXXXX)
1170 mount -o loop "$SRC".1 $EFIMNT
1172 if [ -f $(nocase_path "$EFIMNT$EFI_BOOT/boot*efi") ]; then
1173 cp $(nocase_path "$EFIMNT$EFI_BOOT/boot*efi") $TGTMNT$EFI_BOOT
1174 else
1175 echo "No BOOT*.EFI found in eltorito image. EFI will not boot"
1176 umount $EFIMNT
1177 rm "$SRC".1
1178 exitclean
1180 umount $EFIMNT
1181 rm "$SRC".1
1186 # DVD installer copy
1187 if [ -z "$skipcopy" -a \( "$srctype" = "installer" -o "$srctype" = "netinst" \) ]; then
1188 echo "Copying DVD image to target device."
1189 mkdir -p $TGTMNT/images/
1190 if [ "$imgtype" = "install" ]; then
1191 for img in install.img updates.img product.img; do
1192 if [ -e $SRCMNT/images/$img ]; then
1193 copyFile $SRCMNT/images/$img $TGTMNT/images/$img || exitclean
1195 done
1199 # Copy packages over.
1200 # Before Fedora17 we could copy the .iso and setup a repo=
1201 # F17 and later look for repodata on the source media.
1202 # The presence of packages and LiveOS indicates F17 or later.
1203 if [ -n "$packages" -a -z "$skipcopy" ]; then
1204 if [ "$srctype" != "live" ]; then
1205 echo "Copying $SRC to device"
1206 copyFile "$SRC" "$TGTMNT/"
1208 # Setup a repo= to point to the .iso
1209 sed -i -e "s;initrd.img;initrd.img inst.repo=hd:$TGTLABEL:/;g" $BOOTCONFIG
1210 if [ -n "$efi" ]; then
1211 sed -i -e "s;vmlinuz;vmlinuz inst.repo=hd:$TGTLABEL:/;g" $BOOTCONFIG_EFI
1213 else
1214 echo "Copying package data from $SRC to device"
1215 rsync --inplace -rLDP --exclude EFI/ --exclude images/ --exclude isolinux/ \
1216 --exclude TRANS.TBL --exclude LiveOS/ "$SRCMNT/" "$TGTMNT/"
1218 echo "Waiting for device to finish writing"
1219 sync
1222 if [ "$srctype" = "live" ]; then
1223 # Copy this installer script.
1224 cp -fT "$thisScriptpath" $TGTMNT/$LIVEOS/livecd-iso-to-disk
1225 chmod +x $TGTMNT/$LIVEOS/livecd-iso-to-disk &> /dev/null || :
1227 # When the source is an installed Live USB/SD image, restore the boot config
1228 # file to a base state before updating.
1229 if [[ -d $SRCMNT/syslinux/ ]]; then
1230 echo "Preparing boot config file."
1231 sed -i -e "s/root=live:[^ ]*/root=live:CDLABEL=name/"\
1232 -e "s/\(r*d*.*live.*ima*ge*\) .* quiet/\1 quiet/"\
1233 $BOOTCONFIG $BOOTCONFIG_EFI
1234 sed -i -e "s/^timeout.*$/timeout\ 100/"\
1235 -e "/^totaltimeout.*$/d" $BOOTCONFIG
1239 # Setup the updates.img
1240 if [ -n "$updates" ]; then
1241 copyFile "$updates" "$TGTMNT/updates.img"
1242 kernelargs+=" inst.updates=hd:$TGTLABEL:/updates.img"
1245 # Setup the kickstart
1246 if [ -n "$ks" ]; then
1247 copyFile "$ks" "$TGTMNT/ks.cfg"
1248 kernelargs+=" inst.ks=hd:$TGTLABEL:/ks.cfg"
1251 echo "Updating boot config file"
1252 # adjust label and fstype
1253 sed -i -e "s/CDLABEL=[^ ]*/$TGTLABEL/" -e "s/rootfstype=[^ ]*/rootfstype=$TGTFS/" -e "s/LABEL=[^ :]*/$TGTLABEL/" $BOOTCONFIG $BOOTCONFIG_EFI
1254 if [ -n "$kernelargs" ]; then
1255 sed -i -e "s;initrd.\?\.img;& ${kernelargs};" $BOOTCONFIG
1256 if [ -n "$efi" ]; then
1257 sed -i -e "s;vmlinuz.\?;& ${kernelargs} ;" $BOOTCONFIG_EFI
1260 if [ "$LIVEOS" != "LiveOS" ]; then
1261 sed -i -e "s;r*d*.*live.*ima*ge*;& live_dir=$LIVEOS;"\
1262 $BOOTCONFIG $BOOTCONFIG_EFI
1265 # EFI images are in $SYSLINUXPATH now
1266 if [ -n "$efi" ]; then
1267 sed -i -e "s;/isolinux/;/$SYSLINUXPATH/;g" $BOOTCONFIG_EFI
1268 sed -i -e "s;/images/pxeboot/;/$SYSLINUXPATH/;g" $BOOTCONFIG_EFI
1269 sed -i -e "s;findiso;;g" $BOOTCONFIG_EFI
1272 # DVD Installer for netinst
1273 if [ "$srctype" != "live" ]; then
1274 if [ "$imgtype" = "install" ]; then
1275 sed -i -e "s;initrd.img;initrd.img inst.stage2=hd:$TGTLABEL:/images/install.img;g" $BOOTCONFIG
1276 if [ -n "$efi" ]; then
1277 sed -i -e "s;vmlinuz;vmlinuz inst.stage2=hd:$TGTLABEL:/images/install.img;g" $BOOTCONFIG_EFI
1279 else
1280 # The initrd has everything, so no stage2
1281 sed -i -e "s;\S*stage2=\S*;;g" $BOOTCONFIG $BOOTCONFIG_EFI
1285 # Adjust the boot timeouts
1286 if [ -n "$timeout" ]; then
1287 sed -i -e "s/^timeout.*$/timeout\ $timeout/" $BOOTCONFIG
1289 if [ -n "$totaltimeout" ]; then
1290 sed -i -e "/^timeout.*$/a\totaltimeout\ $totaltimeout" $BOOTCONFIG
1293 if [ "$overlaysizemb" -gt 0 ]; then
1294 echo "Initializing persistent overlay file"
1295 OVERFILE="overlay-$( /sbin/blkid -s LABEL -o value $TGTDEV )-$( /sbin/blkid -s UUID -o value $TGTDEV )"
1296 if [ -z "$skipcopy" ]; then
1297 if [ "$TGTFS" = "vfat" ]; then
1298 # vfat can't handle sparse files
1299 dd if=/dev/zero of=$TGTMNT/$LIVEOS/$OVERFILE count=$overlaysizemb bs=1M
1300 else
1301 dd if=/dev/null of=$TGTMNT/$LIVEOS/$OVERFILE count=1 bs=1M seek=$overlaysizemb
1304 sed -i -e "s/r*d*.*live.*ima*ge*/& rd.live.overlay=${TGTLABEL}/"\
1305 $BOOTCONFIG $BOOTCONFIG_EFI
1306 sed -i -e "s/\ ro\ /\ rw\ /" $BOOTCONFIG $BOOTCONFIG_EFI
1309 if [ "$swapsizemb" -gt 0 -a -z "$skipcopy" ]; then
1310 echo "Initializing swap file"
1311 dd if=/dev/zero of=$TGTMNT/$LIVEOS/swap.img count=$swapsizemb bs=1M
1312 mkswap -f $TGTMNT/$LIVEOS/swap.img
1315 if [ "$homesizemb" -gt 0 -a -z "$skipcopy" ]; then
1316 echo "Initializing persistent /home"
1317 homesource=/dev/zero
1318 [ -n "$cryptedhome" ] && homesource=/dev/urandom
1319 if [ "$TGTFS" = "vfat" ]; then
1320 # vfat can't handle sparse files
1321 dd if=${homesource} of=$TGTMNT/$LIVEOS/$HOMEFILE count=$homesizemb bs=1M
1322 else
1323 dd if=/dev/null of=$TGTMNT/$LIVEOS/$HOMEFILE count=1 bs=1M seek=$homesizemb
1325 if [ -n "$cryptedhome" ]; then
1326 loop=$(losetup -f)
1327 losetup $loop $TGTMNT/$LIVEOS/$HOMEFILE
1329 echo "Encrypting persistent /home"
1330 while ! cryptsetup luksFormat -y -q $loop; do :; done;
1332 echo "Please enter the password again to unlock the device"
1333 while ! cryptsetup luksOpen $loop EncHomeFoo; do :; done;
1335 mkfs.ext4 -j /dev/mapper/EncHomeFoo
1336 tune2fs -c0 -i0 -ouser_xattr,acl /dev/mapper/EncHomeFoo
1337 sleep 2
1338 cryptsetup luksClose EncHomeFoo
1339 losetup -d $loop
1340 else
1341 echo "Formatting unencrypted /home"
1342 mkfs.ext4 -F -j $TGTMNT/$LIVEOS/$HOMEFILE
1343 tune2fs -c0 -i0 -ouser_xattr,acl $TGTMNT/$LIVEOS/$HOMEFILE
1347 # create the forth files for booting on the XO if requested
1348 # we'd do this unconditionally, but you have to have a kernel that will
1349 # boot on the XO anyway.
1350 if [ -n "$xo" ]; then
1351 echo "Setting up /boot/olpc.fth file"
1352 args=$(grep "^ *append" $TGTMNT/$SYSLINUXPATH/isolinux.cfg |head -n1 |sed -e 's/.*initrd=[^ ]*//')
1353 if [ -z "$xonohome" -a ! -f $TGTMNT/$LIVEOS/$HOMEFILE ]; then
1354 args="$args persistenthome=mtd0"
1356 args="$args reset_overlay"
1357 xosyspath=$(echo $SYSLINUXPATH | sed -e 's;/;\\;')
1358 if [ ! -d $TGTMNT/boot ]; then
1359 mkdir -p $TGTMNT/boot
1361 cat > $TGTMNT/boot/olpc.fth <<EOF
1362 \ Boot script for USB boot
1363 hex rom-pa fffc7 + 4 \$number drop h# 2e19 < [if]
1364 patch 2drop erase claim-params
1365 : high-ramdisk ( -- )
1366 cv-load-ramdisk
1367 h# 22c +lp l@ 1+ memory-limit umin /ramdisk - ffff.f000 and ( new-ramdisk-adr )
1368 ramdisk-adr over /ramdisk move ( new-ramdisk-adr )
1369 to ramdisk-adr
1371 ' high-ramdisk to load-ramdisk
1372 [then]
1374 : set-bootpath-dev ( -- )
1375 " /chosen" find-package if ( phandle )
1376 " bootpath" rot get-package-property 0= if ( propval$ )
1377 get-encoded-string ( bootpath$ )
1378 [char] \ left-parse-string 2nip ( dn$ )
1379 dn-buf place ( )
1380 then
1381 then
1383 " /sd" dn-buf count sindex 0>= if
1384 " sd:"
1385 else
1386 " u:"
1387 then
1388 " BOOTPATHDEV" \$set-macro
1391 set-bootpath-dev
1392 " $args" to boot-file
1393 " \${BOOTPATHDEV}$xosyspath\initrd0.img" expand$ to ramdisk
1394 " \${BOOTPATHDEV}$xosyspath\vmlinuz0" expand$ to boot-device
1395 unfreeze
1396 boot
1401 if [ -z "$multi" ]; then
1402 echo "Installing boot loader"
1403 if [ -n "$efi" ]; then
1404 # replace the ia32 hack
1405 if [ -f "$TGTMNT$EFI_BOOT/BOOT.conf" ]; then
1406 cp -f $TGTMNT$EFI_BOOT/BOOTia32.conf $TGTMNT$EFI_BOOT/BOOT.conf
1410 # this is a bit of a kludge, but syslinux doesn't guarantee the API for its com32 modules :/
1411 if [ -f $TGTMNT/$SYSLINUXPATH/vesamenu.c32 -a -f /usr/share/syslinux/vesamenu.c32 ]; then
1412 cp /usr/share/syslinux/vesamenu.c32 $TGTMNT/$SYSLINUXPATH/vesamenu.c32
1413 elif [ -f $TGTMNT/$SYSLINUXPATH/vesamenu.c32 -a -f /usr/lib/syslinux/vesamenu.c32 ]; then
1414 cp /usr/lib/syslinux/vesamenu.c32 $TGTMNT/$SYSLINUXPATH/vesamenu.c32
1415 elif [ -f $TGTMNT/$SYSLINUXPATH/menu.c32 -a -f /usr/share/syslinux/menu.c32 ]; then
1416 cp /usr/share/syslinux/menu.c32 $TGTMNT/$SYSLINUXPATH/menu.c32
1417 elif [ -f $TGTMNT/$SYSLINUXPATH/menu.c32 -a -f /usr/lib/syslinux/menu.c32 ]; then
1418 cp /usr/lib/syslinux/menu.c32 $TGTMNT/$SYSLINUXPATH/menu.c32
1421 if [ "$TGTFS" == "vfat" -o "$TGTFS" == "msdos" ]; then
1422 # syslinux expects the config to be named syslinux.cfg
1423 # and has to run with the file system unmounted
1424 mv $TGTMNT/$SYSLINUXPATH/isolinux.cfg $TGTMNT/$SYSLINUXPATH/syslinux.cfg
1425 # deal with mtools complaining about ldlinux.sys
1426 if [ -f $TGTMNT/$SYSLINUXPATH/ldlinux.sys ]; then
1427 rm -f $TGTMNT/$SYSLINUXPATH/ldlinux.sys
1429 cleanup
1430 if [ -n "$SYSLINUXPATH" ]; then
1431 syslinux -d $SYSLINUXPATH $TGTDEV
1432 else
1433 syslinux $TGTDEV
1435 elif [ "$TGTFS" == "ext2" -o "$TGTFS" == "ext3" -o "$TGTFS" == "ext4" -o "$TGTFS" == "btrfs" ]; then
1436 # extlinux expects the config to be named extlinux.conf
1437 # and has to be run with the file system mounted
1438 mv $TGTMNT/$SYSLINUXPATH/isolinux.cfg $TGTMNT/$SYSLINUXPATH/extlinux.conf
1439 extlinux -i $TGTMNT/$SYSLINUXPATH
1440 # Starting with syslinux 4 ldlinux.sys is used on all file systems.
1441 if [ -f "$TGTMNT/$SYSLINUXPATH/extlinux.sys" ]; then
1442 chattr -i $TGTMNT/$SYSLINUXPATH/extlinux.sys
1443 elif [ -f "$TGTMNT/$SYSLINUXPATH/ldlinux.sys" ]; then
1444 chattr -i $TGTMNT/$SYSLINUXPATH/ldlinux.sys
1446 cleanup
1448 else
1449 # we need to do some more config file tweaks for multi-image mode
1450 sed -i -e "s;kernel vm;kernel /$LIVEOS/syslinux/vm;" $TGTMNT/$SYSLINUXPATH/isolinux.cfg
1451 sed -i -e "s;initrd=i;initrd=/$LIVEOS/syslinux/i;" $TGTMNT/$SYSLINUXPATH/isolinux.cfg
1452 mv $TGTMNT/$SYSLINUXPATH/isolinux.cfg $TGTMNT/$SYSLINUXPATH/syslinux.cfg
1453 cleanup
1456 echo "Target device is now set up with a Live image!"