2 # live.py : LiveImageCreator class for creating Live CD images
4 # Copyright 2007, Red Hat Inc.
6 # This program is free software; you can redistribute it and/or modify
7 # it under the terms of the GNU General Public License as published by
8 # the Free Software Foundation; version 2 of the License.
10 # This program is distributed in the hope that it will be useful,
11 # but WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 # GNU Library General Public License for more details.
15 # You should have received a copy of the GNU General Public License
16 # along with this program; if not, write to the Free Software
17 # Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
26 from imgcreate
.errors
import *
27 from imgcreate
.fs
import *
28 from imgcreate
.creator
import *
30 class LiveImageCreatorBase(LoopImageCreator
):
31 """A base class for LiveCD image creators.
33 This class serves as a base class for the architecture-specific LiveCD
34 image creator subclass, LiveImageCreator.
36 LiveImageCreator creates a bootable ISO containing the system image,
37 bootloader, bootloader configuration, kernel and initramfs.
41 def __init__(self
, *args
):
42 """Initialise a LiveImageCreator instance.
44 This method takes the same arguments as ImageCreator.__init__().
47 LoopImageCreator
.__init
__(self
, *args
)
49 self
.compress_type
= "gzip"
50 """mksquashfs compressor to use."""
52 self
.skip_compression
= False
53 """Controls whether to use squashfs to compress the image."""
55 self
.skip_minimize
= False
56 """Controls whether an image minimizing snapshot should be created.
58 This snapshot can be used when copying the system image from the ISO in
59 order to minimize the amount of data that needs to be copied; simply,
60 it makes it possible to create a version of the image's filesystem with
65 self
._timeout
= kickstart
.get_timeout(self
.ks
, 10)
66 """The bootloader timeout from kickstart."""
68 self
._default
_kernel
= kickstart
.get_default_kernel(self
.ks
, "kernel")
69 """The default kernel type from kickstart."""
73 self
.__modules
= ["=ata", "sym53c8xx", "aic7xxx", "=usb", "=firewire", "=mmc", "=pcmcia", "mptsas", "udf"]
74 self
.__modules
.extend(kickstart
.get_modules(self
.ks
))
76 self
._isofstype
= "iso9660"
79 # Hooks for subclasses
81 def _configure_bootloader(self
, isodir
):
82 """Create the architecture specific booloader configuration.
84 This is the hook where subclasses must create the booloader
85 configuration in order to allow a bootable ISO to be built.
87 isodir -- the directory where the contents of the ISO are to be staged
90 raise CreatorError("Bootloader configuration is arch-specific, "
91 "but not implemented for this arch!")
93 def _get_kernel_options(self
):
94 """Return a kernel options string for bootloader configuration.
96 This is the hook where subclasses may specify a set of kernel options
97 which should be included in the images bootloader configuration.
99 A sensible default implementation is provided.
102 r
= kickstart
.get_kernel_args(self
.ks
)
103 if os
.path
.exists(self
._instroot
+ "/usr/bin/rhgb"):
105 if os
.path
.exists(self
._instroot
+ "/usr/bin/plymouth"):
109 def _get_mkisofs_options(self
, isodir
):
110 """Return the architecture specific mkisosfs options.
112 This is the hook where subclasses may specify additional arguments to
113 mkisofs, e.g. to enable a bootable ISO to be built.
115 By default, an empty list is returned.
121 # Helpers for subclasses
123 def _has_checkisomd5(self
):
124 """Check whether checkisomd5 is available in the install root."""
125 def exists(instroot
, path
):
126 return os
.path
.exists(instroot
+ path
)
128 if (exists(self
._instroot
, "/usr/lib/anaconda-runtime/checkisomd5") or
129 exists(self
._instroot
, "/usr/bin/checkisomd5")):
135 # Actual implementation
137 def _base_on(self
, base_on
):
138 """helper function to extract ext3 file system from a live CD ISO"""
139 isoloop
= DiskMount(LoopbackDisk(base_on
, 0), self
._mkdtemp
())
143 except MountError
, e
:
144 raise CreatorError("Failed to loopback mount '%s' : %s" %
147 # legacy LiveOS filesystem layout support, remove for F9 or F10
148 if os
.path
.exists(isoloop
.mountdir
+ "/squashfs.img"):
149 squashimg
= isoloop
.mountdir
+ "/squashfs.img"
151 squashimg
= isoloop
.mountdir
+ "/LiveOS/squashfs.img"
153 squashloop
= DiskMount(LoopbackDisk(squashimg
, 0), self
._mkdtemp
(), "squashfs")
156 if not squashloop
.disk
.exists():
157 raise CreatorError("'%s' is not a valid live CD ISO : "
158 "squashfs.img doesn't exist" % base_on
)
162 except MountError
, e
:
163 raise CreatorError("Failed to loopback mount squashfs.img "
164 "from '%s' : %s" % (base_on
, e
))
166 # legacy LiveOS filesystem layout support, remove for F9 or F10
167 if os
.path
.exists(squashloop
.mountdir
+ "/os.img"):
168 os_image
= squashloop
.mountdir
+ "/os.img"
170 os_image
= squashloop
.mountdir
+ "/LiveOS/ext3fs.img"
172 if not os
.path
.exists(os_image
):
173 raise CreatorError("'%s' is not a valid live CD ISO : neither "
174 "LiveOS/ext3fs.img nor os.img exist" %
178 shutil
.copyfile(os_image
, self
._image
)
180 raise CreatorError("Failed to copy base live image to %s for modification: %s" %(self
._image
, e
))
185 def _mount_instroot(self
, base_on
= None):
186 LoopImageCreator
._mount
_instroot
(self
, base_on
)
187 self
.__write
_initrd
_conf
(self
._instroot
+ "/etc/sysconfig/mkinitrd")
188 self
.__write
_dracut
_conf
(self
._instroot
+ "/etc/dracut.conf")
190 def _unmount_instroot(self
):
191 self
.__restore
_file
(self
._instroot
+ "/etc/sysconfig/mkinitrd")
192 self
.__restore
_file
(self
._instroot
+ "/etc/dracut.conf")
193 LoopImageCreator
._unmount
_instroot
(self
)
195 def __ensure_isodir(self
):
196 if self
.__isodir
is None:
197 self
.__isodir
= self
._mkdtemp
("iso-")
200 def _create_bootconfig(self
):
201 """Configure the image so that it's bootable."""
202 self
._configure
_bootloader
(self
.__ensure
_isodir
())
204 def _get_post_scripts_env(self
, in_chroot
):
205 env
= LoopImageCreator
._get
_post
_scripts
_env
(self
, in_chroot
)
208 env
["LIVE_ROOT"] = self
.__ensure
_isodir
()
212 def __extra_filesystems(self
):
213 return "squashfs ext4 ext3 ext2 vfat msdos ";
215 def __extra_drivers(self
):
216 retval
= "sr_mod sd_mod ide-cd cdrom "
217 for module
in self
.__modules
:
219 retval
= retval
+ "ehci_hcd uhci_hcd ohci_hcd "
220 retval
= retval
+ "usb_storage usbhid "
221 elif module
== "=firewire":
222 retval
= retval
+ "firewire-sbp2 firewire-ohci "
223 retval
= retval
+ "sbp2 ohci1394 ieee1394 "
224 elif module
== "=mmc":
225 retval
= retval
+ "mmc_block sdhci sdhci-pci "
226 elif module
== "=pcmcia":
227 retval
= retval
+ "pata_pcmcia "
229 retval
= retval
+ module
+ " "
232 def __restore_file(self
,path
):
237 if os
.path
.exists(path
+ '.rpmnew'):
238 os
.rename(path
+ '.rpmnew', path
)
240 def __write_initrd_conf(self
, path
):
241 if not os
.path
.exists(os
.path
.dirname(path
)):
242 makedirs(os
.path
.dirname(path
))
244 f
.write('LIVEOS="yes"\n')
245 f
.write('PROBE="no"\n')
246 f
.write('MODULES+="' + self
.__extra
_filesystems
() + '"\n')
247 f
.write('MODULES+="' + self
.__extra
_drivers
() + '"\n')
250 def __write_dracut_conf(self
, path
):
251 if not os
.path
.exists(os
.path
.dirname(path
)):
252 makedirs(os
.path
.dirname(path
))
254 f
.write('filesystems+="' + self
.__extra
_filesystems
() + ' "\n')
255 f
.write('drivers+="' + self
.__extra
_drivers
() + ' "\n')
258 def __create_iso(self
, isodir
):
259 iso
= self
._outdir
+ "/" + self
.name
+ ".iso"
261 args
= ["/usr/bin/mkisofs",
263 "-hide-rr-moved", "-hide-joliet-trans-tbl",
267 args
.extend(self
._get
_mkisofs
_options
(isodir
))
268 if self
._isofstype
== "udf":
269 args
.append("-allow-limited-size")
273 if subprocess
.call(args
) != 0:
274 raise CreatorError("ISO creation failed!")
276 if os
.path
.exists("/usr/bin/isohybrid"):
277 subprocess
.call(["/usr/bin/isohybrid", iso
])
279 self
.__implant
_md
5sum
(iso
)
281 def __implant_md5sum(self
, iso
):
282 """Implant an isomd5sum."""
283 if os
.path
.exists("/usr/bin/implantisomd5"):
284 implantisomd5
= "/usr/bin/implantisomd5"
285 elif os
.path
.exists("/usr/lib/anaconda-runtime/implantisomd5"):
286 implantisomd5
= "/usr/lib/anaconda-runtime/implantisomd5"
288 logging
.warn("isomd5sum not installed; not setting up mediacheck")
291 subprocess
.call([implantisomd5
, iso
])
293 def _stage_final_image(self
):
295 makedirs(self
.__ensure
_isodir
() + "/LiveOS")
299 if not self
.skip_minimize
:
300 create_image_minimizer(self
.__isodir
+ "/LiveOS/osmin.img", self
._image
, self
.compress_type
)
302 if self
.skip_compression
:
303 shutil
.move(self
._image
, self
.__isodir
+ "/LiveOS/ext3fs.img")
304 if os
.stat(self
.__isodir
+ "/LiveOS/ext3fs.img").st_size
>= 4*1024*1024*1024:
305 self
._isofstype
= "udf"
306 logging
.warn("Switching to UDF due to size of LiveOS/ext3fs.img")
308 makedirs(os
.path
.join(os
.path
.dirname(self
._image
), "LiveOS"))
309 shutil
.move(self
._image
,
310 os
.path
.join(os
.path
.dirname(self
._image
),
311 "LiveOS", "ext3fs.img"))
312 mksquashfs(os
.path
.dirname(self
._image
),
313 self
.__isodir
+ "/LiveOS/squashfs.img",
315 if os
.stat(self
.__isodir
+ "/LiveOS/squashfs.img").st_size
>= 4*1024*1024*1024:
316 self
._isofstype
= "udf"
317 logging
.warn("Switching to UDF due to size of LiveOS/squashfs.img")
320 self
.__create
_iso
(self
.__isodir
)
322 shutil
.rmtree(self
.__isodir
, ignore_errors
= True)
325 class x86LiveImageCreator(LiveImageCreatorBase
):
326 """ImageCreator for x86 machines"""
327 def _get_mkisofs_options(self
, isodir
):
328 return [ "-b", "isolinux/isolinux.bin",
329 "-c", "isolinux/boot.cat",
330 "-no-emul-boot", "-boot-info-table",
331 "-boot-load-size", "4" ]
333 def _get_required_packages(self
):
334 return ["syslinux"] + LiveImageCreatorBase
._get
_required
_packages
(self
)
336 def _get_isolinux_stanzas(self
, isodir
):
339 def __find_syslinux_menu(self
):
340 for menu
in ("vesamenu.c32", "menu.c32"):
341 for dir in ("/usr/lib/syslinux/", "/usr/share/syslinux/"):
342 if os
.path
.isfile(self
._instroot
+ dir + menu
):
345 raise CreatorError("syslinux not installed : "
346 "no suitable *menu.c32 found")
348 def __find_syslinux_mboot(self
):
350 # We only need the mboot module if we have any xen hypervisors
352 if not glob
.glob(self
._instroot
+ "/boot/xen.gz*"):
357 def __copy_syslinux_files(self
, isodir
, menu
, mboot
= None):
358 files
= ["isolinux.bin", menu
]
363 if os
.path
.exists(self
._instroot
+ "/usr/lib/syslinux/" + f
):
364 path
= self
._instroot
+ "/usr/lib/syslinux/" + f
365 elif os
.path
.exists(self
._instroot
+ "/usr/share/syslinux/" + f
):
366 path
= self
._instroot
+ "/usr/share/syslinux/" + f
367 if not os
.path
.isfile(path
):
368 raise CreatorError("syslinux not installed : "
369 "%s not found" % path
)
371 shutil
.copy(path
, isodir
+ "/isolinux/")
373 def __copy_syslinux_background(self
, isodest
):
374 background_path
= self
._instroot
+ \
375 "/usr/share/anaconda/syslinux-vesa-splash.jpg"
377 if not os
.path
.exists(background_path
):
378 # fallback to F13 location
379 background_path
= self
._instroot
+ \
380 "/usr/lib/anaconda-runtime/syslinux-vesa-splash.jpg"
382 if not os
.path
.exists(background_path
):
385 shutil
.copyfile(background_path
, isodest
)
389 def __copy_kernel_and_initramfs(self
, isodir
, version
, index
):
390 bootdir
= self
._instroot
+ "/boot"
392 shutil
.copyfile(bootdir
+ "/vmlinuz-" + version
,
393 isodir
+ "/isolinux/vmlinuz" + index
)
396 if os
.path
.exists(bootdir
+ "/initramfs-" + version
+ ".img"):
397 shutil
.copyfile(bootdir
+ "/initramfs-" + version
+ ".img",
398 isodir
+ "/isolinux/initrd" + index
+ ".img")
401 shutil
.copyfile(bootdir
+ "/initrd-" + version
+ ".img",
402 isodir
+ "/isolinux/initrd" + index
+ ".img")
405 if os
.path
.exists(bootdir
+ "/xen.gz-" + version
[:-3]):
406 shutil
.copyfile(bootdir
+ "/xen.gz-" + version
[:-3],
407 isodir
+ "/isolinux/xen" + index
+ ".gz")
410 return (is_xen
, isDracut
)
412 def __is_default_kernel(self
, kernel
, kernels
):
413 if len(kernels
) == 1:
416 if kernel
== self
._default
_kernel
:
419 if kernel
.startswith("kernel-") and kernel
[7:] == self
._default
_kernel
:
424 def __get_basic_syslinux_config(self
, **args
):
430 menu title Welcome to %(name)s!
431 menu color border 0 #ffffffff #00000000
432 menu color sel 7 #ffffffff #ff000000
433 menu color title 0 #ffffffff #00000000
434 menu color tabmsg 0 #ffffffff #00000000
435 menu color unsel 0 #ffffffff #00000000
436 menu color hotsel 0 #ff000000 #ffffffff
437 menu color hotkey 7 #ffffffff #ff000000
438 menu color timeout_msg 0 #ffffffff #00000000
439 menu color timeout 0 #ffffffff #00000000
440 menu color cmdline 0 #ffffffff #00000000
445 def __get_image_stanza(self
, is_xen
, isDracut
, **args
):
447 args
["rootlabel"] = "live:CDLABEL=%(fslabel)s" % args
449 args
["rootlabel"] = "CDLABEL=%(fslabel)s" % args
452 template
= """label %(short)s
454 kernel vmlinuz%(index)s
455 append initrd=initrd%(index)s.img root=%(rootlabel)s rootfstype=%(isofstype)s %(liveargs)s %(xdriver)s %(extra)s
458 template
= """label %(short)s
461 append xen%(index)s.gz --- vmlinuz%(index)s root=%(rootlabel)s rootfstype=%(isofstype)s %(liveargs)s %(xdriver)s %(extra)s --- initrd%(index)s.img
463 return template
% args
465 def __get_image_stanzas(self
, isodir
):
467 kernels
= self
._get
_kernel
_versions
()
468 for kernel
in kernels
:
469 for version
in kernels
[kernel
]:
470 versions
.append(version
)
472 kernel_options
= self
._get
_kernel
_options
()
474 checkisomd5
= self
._has
_checkisomd
5()
479 for version
in versions
:
480 (is_xen
, isDracut
) = self
.__copy
_kernel
_and
_initramfs
(isodir
, version
, index
)
482 self
._isDracut
= isDracut
484 default
= self
.__is
_default
_kernel
(kernel
, kernels
)
488 elif kernel
.startswith("kernel-"):
489 long = "Boot %s(%s)" % (self
.name
, kernel
[7:])
491 long = "Boot %s(%s)" % (self
.name
, kernel
)
494 basic
= "system with basic video driver"
495 xdriver
= "xdriver=vesa nomodeset"
498 # tell dracut not to ask for LUKS passwords or activate mdraid sets
500 kern_opts
= kernel_options
+ " rd_NO_LUKS rd_NO_MD rd_NO_DM"
502 kern_opts
= kernel_options
504 cfg
+= self
.__get
_image
_stanza
(is_xen
, isDracut
,
505 fslabel
= self
.fslabel
,
507 liveargs
= kern_opts
,
509 short
= "linux" + index
,
516 cfg
+= "menu default\n"
518 cfg
+= self
.__get
_image
_stanza
(is_xen
, isDracut
,
519 fslabel
= self
.fslabel
,
521 liveargs
= kern_opts
,
523 short
= "linux" + index
,
530 cfg
+= self
.__get
_image
_stanza
(is_xen
, isDracut
,
531 fslabel
= self
.fslabel
,
533 liveargs
= kernel_options
,
534 long = "Verify and " + long,
535 short
= "check" + index
,
541 index
= str(int(index
) + 1)
545 def __get_memtest_stanza(self
, isodir
):
546 memtest
= glob
.glob(self
._instroot
+ "/boot/memtest86*")
550 shutil
.copyfile(memtest
[0], isodir
+ "/isolinux/memtest")
552 return """label memtest
553 menu label Memory Test
557 def __get_local_stanza(self
, isodir
):
558 return """label local
559 menu label Boot from local drive
563 def _configure_syslinux_bootloader(self
, isodir
):
564 """configure the boot loader"""
565 makedirs(isodir
+ "/isolinux")
567 menu
= self
.__find
_syslinux
_menu
()
569 self
.__copy
_syslinux
_files
(isodir
, menu
,
570 self
.__find
_syslinux
_mboot
())
573 if self
.__copy
_syslinux
_background
(isodir
+ "/isolinux/splash.jpg"):
574 background
= "menu background splash.jpg"
576 cfg
= self
.__get
_basic
_syslinux
_config
(menu
= menu
,
577 background
= background
,
579 timeout
= self
._timeout
* 10)
581 cfg
+= self
.__get
_image
_stanzas
(isodir
)
582 cfg
+= self
.__get
_memtest
_stanza
(isodir
)
583 cfg
+= self
.__get
_local
_stanza
(isodir
)
584 cfg
+= self
._get
_isolinux
_stanzas
(isodir
)
586 cfgf
= open(isodir
+ "/isolinux/isolinux.cfg", "w")
590 def __copy_efi_files(self
, isodir
):
591 if not os
.path
.exists(self
._instroot
+ "/boot/efi/EFI/redhat/grub.efi"):
593 shutil
.copy(self
._instroot
+ "/boot/efi/EFI/redhat/grub.efi",
594 isodir
+ "/EFI/boot/grub.efi")
595 shutil
.copy(self
._instroot
+ "/boot/grub/splash.xpm.gz",
596 isodir
+ "/EFI/boot/splash.xpm.gz")
600 def __get_basic_efi_config(self
, **args
):
603 splashimage=/EFI/boot/splash.xpm.gz
609 def __get_efi_image_stanza(self
, **args
):
611 args
["rootlabel"] = "live:LABEL=%(fslabel)s" % args
613 args
["rootlabel"] = "CDLABEL=%(fslabel)s" % args
614 return """title %(long)s
615 kernel /EFI/boot/vmlinuz%(index)s root=%(rootlabel)s rootfstype=%(isofstype)s %(liveargs)s %(extra)s
616 initrd /EFI/boot/initrd%(index)s.img
619 def __get_efi_image_stanzas(self
, isodir
, name
):
620 # FIXME: this only supports one kernel right now...
622 kernel_options
= self
._get
_kernel
_options
()
623 checkisomd5
= self
._has
_checkisomd
5()
627 for index
in range(0, 9):
628 # we don't support xen kernels
629 if os
.path
.exists("%s/EFI/boot/xen%d.gz" %(isodir
, index
)):
631 cfg
+= self
.__get
_efi
_image
_stanza
(fslabel
= self
.fslabel
,
633 liveargs
= kernel_options
,
635 extra
= "", index
= index
)
637 cfg
+= self
.__get
_efi
_image
_stanza
(fslabel
= self
.fslabel
,
639 liveargs
= kernel_options
,
640 long = "Verify and Boot " + name
,
647 def _configure_efi_bootloader(self
, isodir
):
648 """Set up the configuration for an EFI bootloader"""
649 makedirs(isodir
+ "/EFI/boot")
651 if not self
.__copy
_efi
_files
(isodir
):
652 shutil
.rmtree(isodir
+ "/EFI")
655 for f
in os
.listdir(isodir
+ "/isolinux"):
656 os
.link("%s/isolinux/%s" %(isodir
, f
),
657 "%s/EFI/boot/%s" %(isodir
, f
))
660 cfg
= self
.__get
_basic
_efi
_config
(name
= self
.name
,
661 timeout
= self
._timeout
)
662 cfg
+= self
.__get
_efi
_image
_stanzas
(isodir
, self
.name
)
664 cfgf
= open(isodir
+ "/EFI/boot/grub.conf", "w")
668 # first gen mactel machines get the bootloader name wrong apparently
669 if rpmUtils
.arch
.getBaseArch() == "i386":
670 os
.link(isodir
+ "/EFI/boot/grub.efi", isodir
+ "/EFI/boot/boot.efi")
671 os
.link(isodir
+ "/EFI/boot/grub.conf", isodir
+ "/EFI/boot/boot.conf")
673 # for most things, we want them named boot$efiarch
674 efiarch
= {"i386": "ia32", "x86_64": "x64"}
675 efiname
= efiarch
[rpmUtils
.arch
.getBaseArch()]
676 os
.rename(isodir
+ "/EFI/boot/grub.efi", isodir
+ "/EFI/boot/boot%s.efi" %(efiname
,))
677 os
.link(isodir
+ "/EFI/boot/grub.conf", isodir
+ "/EFI/boot/boot%s.conf" %(efiname
,))
680 def _configure_bootloader(self
, isodir
):
681 self
._configure
_syslinux
_bootloader
(isodir
)
682 self
._configure
_efi
_bootloader
(isodir
)
684 class ppcLiveImageCreator(LiveImageCreatorBase
):
685 def _get_mkisofs_options(self
, isodir
):
686 return [ "-hfs", "-no-desktop", "-part",
687 "-map", isodir
+ "/ppc/mapping",
688 "-hfs-bless", isodir
+ "/ppc/mac",
689 "-hfs-volid", self
.fslabel
]
691 def _get_required_packages(self
):
692 return ["yaboot"] + \
693 LiveImageCreatorBase
._get
_required
_packages
(self
)
695 def _get_excluded_packages(self
):
696 # kind of hacky, but exclude memtest86+ on ppc so it can stay in cfg
697 return ["memtest86+"] + \
698 LiveImageCreatorBase
._get
_excluded
_packages
(self
)
700 def __copy_boot_file(self
, destdir
, file):
701 for dir in ["/usr/share/ppc64-utils",
702 "/usr/lib/anaconda-runtime/boot"]:
703 path
= self
._instroot
+ dir + "/" + file
704 if not os
.path
.exists(path
):
708 shutil
.copy(path
, destdir
)
711 raise CreatorError("Unable to find boot file " + file)
713 def __kernel_bits(self
, kernel
):
714 testpath
= (self
._instroot
+ "/lib/modules/" +
715 kernel
+ "/kernel/arch/powerpc/platforms")
717 if not os
.path
.exists(testpath
):
718 return { "32" : True, "64" : False }
720 return { "32" : False, "64" : True }
722 def __copy_kernel_and_initramfs(self
, destdir
, version
):
724 bootdir
= self
._instroot
+ "/boot"
728 shutil
.copyfile(bootdir
+ "/vmlinuz-" + version
,
729 destdir
+ "/vmlinuz")
731 if os
.path
.exists(bootdir
+ "/initramfs-" + version
+ ".img"):
732 shutil
.copyfile(bootdir
+ "/initramfs-" + version
+ ".img",
733 destdir
+ "/initrd.img")
736 shutil
.copyfile(bootdir
+ "/initrd-" + version
+ ".img",
737 destdir
+ "/initrd.img")
741 def __get_basic_yaboot_config(self
, **args
):
743 init-message = "Welcome to %(name)s"
747 def __get_image_stanza(self
, **args
):
749 args
["rootlabel"] = "live:LABEL=%(fslabel)s" % args
751 args
["rootlabel"] = "CDLABEL=%(fslabel)s" % args
754 image=/ppc/ppc%(bit)s/vmlinuz
756 initrd=/ppc/ppc%(bit)s/initrd.img
758 append="root=%(rootlabel)s rootfstype=%(isofstype)s %(liveargs)s %(extra)s"
762 def __write_yaboot_config(self
, isodir
, bit
, isDracut
= False):
763 cfg
= self
.__get
_basic
_yaboot
_config
(name
= self
.name
,
764 timeout
= self
._timeout
* 100)
766 kernel_options
= self
._get
_kernel
_options
()
768 cfg
+= self
.__get
_image
_stanza
(fslabel
= self
.fslabel
,
771 long = "Run from image",
774 liveargs
= kernel_options
,
777 if self
._has
_checkisomd
5():
778 cfg
+= self
.__get
_image
_stanza
(fslabel
= self
.fslabel
,
781 long = "Verify and run from image",
784 liveargs
= kernel_options
,
787 f
= open(isodir
+ "/ppc/ppc" + bit
+ "/yaboot.conf", "w")
791 def __write_not_supported(self
, isodir
, bit
):
792 makedirs(isodir
+ "/ppc/ppc" + bit
)
794 message
= "Sorry, this LiveCD does not support your hardware"
796 f
= open(isodir
+ "/ppc/ppc" + bit
+ "/yaboot.conf", "w")
797 f
.write('init-message = "' + message
+ '"')
801 def __write_dualbits_yaboot_config(isodir
, **args
):
803 init-message = "\nWelcome to %(name)s!\nUse 'linux32' for 32-bit kernel.\n\n"
807 image=/ppc/ppc64/vmlinuz
810 initrd=/ppc/ppc64/initrd.img
813 image=/ppc/ppc32/vmlinuz
815 initrd=/ppc/ppc32/initrd.img
819 f
= open(isodir
+ "/etc/yaboot.conf", "w")
823 def _configure_bootloader(self
, isodir
):
824 """configure the boot loader"""
825 havekernel
= { 32: False, 64: False }
827 self
.__copy
_boot
_file
(isodir
+ "/ppc", "mapping")
828 self
.__copy
_boot
_file
(isodir
+ "/ppc", "bootinfo.txt")
829 self
.__copy
_boot
_file
(isodir
+ "/ppc/mac", "ofboot.b")
831 shutil
.copyfile(self
._instroot
+ "/usr/lib/yaboot/yaboot",
832 isodir
+ "/ppc/mac/yaboot")
834 makedirs(isodir
+ "/ppc/chrp")
835 shutil
.copyfile(self
._instroot
+ "/usr/lib/yaboot/yaboot",
836 isodir
+ "/ppc/chrp/yaboot")
838 subprocess
.call(["/usr/sbin/addnote", isodir
+ "/ppc/chrp/yaboot"])
841 # FIXME: ppc should support multiple kernels too...
843 kernel
= self
._get
_kernel
_versions
().values()[0][0]
845 kernel_bits
= self
.__kernel
_bits
(kernel
)
847 for (bit
, present
) in kernel_bits
.items():
849 self
.__write
_not
_supported
(isodir
, bit
)
852 isDracut
= self
.__copy
_kernel
_and
_initramfs
(isodir
+ "/ppc/ppc" + bit
, kernel
)
853 self
.__write
_yaboot
_config
(isodir
, bit
, isDracut
)
855 makedirs(isodir
+ "/etc")
856 if kernel_bits
["32"] and not kernel_bits
["64"]:
857 shutil
.copyfile(isodir
+ "/ppc/ppc32/yaboot.conf",
858 isodir
+ "/etc/yaboot.conf")
859 elif kernel_bits
["64"] and not kernel_bits
["32"]:
860 shutil
.copyfile(isodir
+ "/ppc/ppc64/yaboot.conf",
861 isodir
+ "/etc/yaboot.conf")
863 self
.__write
_dualbits
_yaboot
_config
(isodir
,
865 timeout
= self
._timeout
* 100)
868 # FIXME: build 'netboot' images with kernel+initrd, like mk-images.ppc
871 class ppc64LiveImageCreator(ppcLiveImageCreator
):
872 def _get_excluded_packages(self
):
874 # while kernel.ppc and kernel.ppc64 co-exist,
876 return ["kernel.ppc"] + \
877 ppcLiveImageCreator
._get
_excluded
_packages
(self
)
879 arch
= rpmUtils
.arch
.getBaseArch()
880 if arch
in ("i386", "x86_64"):
881 LiveImageCreator
= x86LiveImageCreator
882 elif arch
in ("ppc",):
883 LiveImageCreator
= ppcLiveImageCreator
884 elif arch
in ("ppc64",):
885 LiveImageCreator
= ppc64LiveImageCreator
887 raise CreatorError("Architecture not supported!")