Darwin
<Google>WIKI</Google>
This page is about "Darwinx86" in general. Nothing specific to Apple TV. However, since Darwin is at the core of Apple TV, it is important to know how Darwin works. Everything 100% APSL compliant. We host it here since good, practical documentation for Darwin is hard to find.
Contents
- 1 About Darwin
- 2 Purpose of this page
- 3 Minimal hardware requirements for darwinx86-801.iso
- 4 Booting darwinx86-801.iso on a PC
- 5 Installing darwinx86-801.iso on a PC
- 6 Exploring Darwin
- 7 Installing third-party software
- 8 Shrinking Darwin
- 9 Installing "Darwin nano" on bootable USB drive
- 10 Minimal number of packages to boot the Darwin kernel
- 11 Darwin versions
- 12 Darwin install script
- 13 Bug reporting
About Darwin
As Apple advertises, Mac OS X is built on a "secure, reliable, Open Source foundation", namely Darwin. See http://www.apple.com/opensource/ for more information.
We want to use this system. There are a couple of reasons why Darwin is great:
- It can read and write HFS+ Journaled natively
- Mac and Apple TV users are familiar with the workings of the system
- There is lots of Open Source applications available, including a graphical X desktop
- Can be used e.g., for embedded applications
- Can be legally changed and re-distributed in accordance with APSL
Initially, there was large interest in Darwin, but as time progressed, the community lost interest (due to reasons that shall not be evaluated here). However, with the switch of Mac OS to Intel, there seems to be a lot of interest of the community again, but mainly focused on Mac OS X rather than Darwin itself.
Mac OS Forge
Mac OS Forge, hosted by Apple, is where Kernel (xnu), Launchd, and other parts of Darwin live.
- http://www.macosforge.org/
- #macosforge on irc.freenode.net
OpenDarwin
Unfortunately, this project closed due to a perceived "lack of interest" just when it became real interesting due to the move to Intel.
- http://www.opendarwin.org/ (archived)
- #opendarwin on irc.freenode.net (however, their motto now is "Do not talk about OpenDarwin!")
Project was launched by bbraun, a former Apple employee who today insists that this project is dead.
OpenDarwin is not the same as Darwin (since unlike OpenDarwin, Darwin is alive). However, Darwin itself contains references to "OpenDarwin". For example, /etc/rc.cdrom identifies itself as "OpenDarwin install script". Oh well.
GNU/Darwin
Tries to build a complete desktop-oriented, general-purpose distribution on Darwin.
Fink
A collection of Open Source software for Darwin. It is claimed that they also host pre-compiled, ready-made binaries for Intel, however the URLs of those are hard to impossible to find on the site.
Think of Fink as "debian on Darwin". This uses the .deb format and the dpkg tools. There is even a Mac application called "Fink Commander" that is very similar to synaptic.
Project was launched by Christoph Pfisterer (later rEFIt), now working for Google.
DarwinPorts
MacPorts is the successor to DarwinPorts
- http://darwinports.com/ (called a "a fraud site" by MacPorts developers)
MacPorts
Describes itself as "the project previously known as DarwinPorts". Hosted by Apple, this seems to be actively developed (Google Summer of Code 2007).
Think of MacPorts as "Gentoo on Darwin". There is no build server yet, which means that there are no pre-built binaries and you have to build everything yourself.
"Pure Darwin on x86"
- Contact: vmlemon
Purpose of this page
The first goal will be to install Darwin on a USB drive and boot a generic PC from there. This serves as a starting point for further projects based on Darwin.
Please note that this page is about 100% legitimate uses of the Darwin Open Source system only.
Minimal hardware requirements for darwinx86-801.iso
Found out by experimentation. Please add.
Processor
SSE2 and SSE3 are NOT required since Darwin 8.0.1 ISO boots fine on a Celeron 400 MHz machine from 1999 with a PIIX4.
(However, this system requires "platform=X86PC" because it otherwise stalls with an ACPI error message.)
Hard Disk
The Darwin installer puts 1.44 GB on disk. There is no apparent way to select less software in the installer. This is far more than what is needed for a minimal Darwin system.
Booting darwinx86-801.iso on a PC
Booting Darwin CD from IDE (works)
This is on a i915 chipset, DVD drive attached to IDE:
IOATAController device blocking bus AppleIntelPIIXPATA: ICH6 ATA/100 (CMD 0x1f0, CTR 0x3f4, IRQ 14 BM 0xffa0) Still waiting for root device Still waiting for root device Still waiting for root device
Changing the DVD drive jumper from cable select to Master solved this issue.
It boots up and asks where to install Darwin.
So in principle, darwinx86-801.iso contains a system that is capable of running on a generic PC.
Booting Darwin CD from USB (works)
The same darwinx86-801.iso also boots fine when the DVD drive is connected to the USB bus using a IDE2USB adapter.
So in fact darwinx86-801.iso contains a system that is capable of running on a generic PC from USB.
Can we turn this into a USB "bootstick"?
Booting Darwin CD into single user mode (works)
By default, the Darwin CD boots into a installer. However by using "-s" at the boot prompt, we can boot into "single user mode", which allows us to issue commands on the command line.
Installing darwinx86-801.iso on a PC
Now that we have booted darwinx86-801.iso, let's install it.
Trying to install Darwin to attached USB drive (fails)
Booting Darwin CD as described above, with plugged-in USB drive gives:
USBF: AppleUSBEHCI[0xc181b800]::Found a transaction past the completion deadline on bus 253, timing out! USBF: AppleUSBEHCI[0xc181b800]::Found a transaction past the completion deadline on bus 253, timing out! USBF: AppleUSBEHCI[0xc181b800]::Found a transaction which hasn't moved in 5 seconds on bus 253, timing out!
Apparently this is a Darwin bug. Please note here if otherwise.
Installing Darwin to attached IDE drive (works)
As above, but this time the disk is on the IDE bus.
.root.tar.bz2 files
During installation, a lot of .root.tar.bz2 files are uncompressed.
So the installer doesn't actually clone the system that is used to boot the CD, but uses the compressed files. Are they different?
There is no apparent way to determine what gets installed. So We are getting a lot of stuff that is not necessary for a bare bones installation, such as gcc.
What is the minimum configuration of .root.tar.bz2 files necessary?
Updating mkext cache
Wouldn't this be done at next boot anyway?
Personalization
- Installer asks for a root password
- Installer asks for a computer name (Bonjour hostname)
Booting into installed Darwin from IDE (works)
Fixing boot issue
If booted without any arguments, the boot fails. However, by entering
rd=disk0s1
Darwin fully boots into a login prompt.
The following procedure fixes the boot issue permanently:
mcedit /Library/Preferences/SystemConfiguration/com.apple.Boot.plist # edit Boot.plist, remove "Boot Device" entry reboot
USB issue (fixed)
The installed Darwin seems to fail recognizing any USB devices
kextstat | grep USB com.apple.iokit.IOUSBFamily (2.2.0) com.apple.driver.AppleUSBUHCI (2.2.0) com.apple.driver.AppleUSBEHCI (2.2.0) com.apple.driver.AppleUSBHub (2.2.0)
Trying to load IOUSBFamily.kext says "check ownership and permissions".
Apparently this is a Darwin bug of the installer. Please note here if otherwise.
So permissions need to be repaired. However, since there is no /Libaray/Receipts and no diskutil in Darwin, we need to do this manually
chmod -R 755 /System/Library/Extensions chown -R 0:0 /System/Library/Extensions touch /System/Library/Extensions reboot
This fixes the USB issue. An USB drive is now correctly recognized as /dev/disk1s, it is not automatically mounted however.
Mounting HFS+ (Journaled) USB drive (works)
mkdir /Volumes/Test mount -t hfs /dev/disk1s1 /Volumes/Test or mount_hfs /dev/disk1s1 /Volumne/Test
Booting into installed Darwin from USB (works)
Good news of the year!
The very same hard disk that boots from IDE also boots when connected with a IDE2USB cable. Yay!
Note that in addition to the USB kexts above, this time there are additional ones loaded:
kextstat | grep USB AppleUSBComposite (2.2.0) IOUSBStorageClass (1.4.0) IOUSBUserClient (2.2.0)
Exploring Darwin
Enabling sshd
killall sshd ssh-keygen -t rsa -f /etc/ssh_host_rsa_key # do NOT use passphrase ssh-keygen -t rsa1 -f /etc/ssh_host_key # do NOT use passphrase sshd
Edit /System/Library/LaunchDaemons/ssh.plist to launch sshd on each start:
<key>Disabled</key> <false/>
Enabling apache2
apache2 is installed in /opt by default. You can launch it with
/opt/apache2/bin/apachectl start
It is configured to listen on port 8080 by default. So you can access the machine via http://darwin.local:8080/ for example (if your computer name is set to "Dawin").
/etc/hostconfig
Various services are supposed to be automatically started by editing /etc/hostconfig, including
- AFP
- Webserver - This does NOT appear to work on Darwin. Is this a leftover from Mac OS X?
- SMB Server
- Spotlight - Is this a leftover from Mac OS X and disfunctional on Darwin?
Stuff that is in Darwin but not in Mac OS X
- /usr/local/bin: Optional binaries
- /usr/local/SecurityPieces
- /usr/local/OpenSourceVersions: Contains a .plist file each for the Open Source parts in Darwin. Is the format of this file documented?
- OpenSourceProject
- OpenSourceVersion
- OpenSourceURL
- OpenSourceSHA1
- OpenSourceImportDate
- OpenSourceModifications
- OpenSourceLicense
- OpenSourceLicenseFile
- /usr/local/OpenSourceLicenses: Contains the licenses of the Open Source parts in Darwin.
- /usr/include: Header files
Unpacking Installer packages
Mac software often comes as .pkg Installer packages.
Here is how to unpack these in Darwin:
gunzip -c *.pkg/Contents/Archive.pax.gz | pax -r
Mounting dmg files
According to this (to be tested):
/usr/libexec/vndevice attach /dev/vn0 my.dmg mount -t hfs /dev/vn0 /mnt/
Installing third-party software
There is third-party software available for Darwin (even a OpenGL-accellerated X.org server, and graphical applications). However, getting this software in Darwin is not as easy as getting software in Mac OS (yet).
Installing Fink (fails)
Fink hosts precompiled software for Darwinx86. So let's get some. Not so easy actually, since they seem to have designed the fink installation procedure with Mac OS in mind. It does run on Darwin proper, doesn't it?
- Get Fink dmg
- Mount dmg as described above
- Extract .pkg contents as described above
- Move sw/ to /sw
Unfortunately, most software from /sw/usr/bin fails: "Bad executable (or shared library)".
Further investigation required. Please note any solution here.
Debugging why Fink binaries refuse to run on Darwin 8.0.1
With the help of #fink:
- Installed cctools-* again, it contains otool (a debugging tool)
- otool -lv /sw/bin/dpkg and otool -hv /sw/bin/dpkg (output)
- ktrace and kdump
darwin:~ root# ktrace /sw/bin/dpkg ktrace: exec of '/sw/bin/dpkg' failed: Bad executable (or shared library) darwin:~ root# kdump 96 ktrace RET ktrace 0 96 ktrace CALL execve(0xbffffd43,0xbffffcec,0) 96 ktrace NAMI "/sw/bin/dpkg" 96 ktrace RET execve -1 errno 85 Bad executable (or shared library) 96 ktrace CALL stat(0xbffffd43,0xbffffcec) 96 ktrace NAMI "/sw/bin/dpkg" 96 ktrace RET stat 0 96 ktrace CALL write(0x2,0x8,0) 96 ktrace GIO fd 2 wrote 8 bytes "ktrace: " 96 ktrace RET write 8 96 ktrace CALL write(0x2,0x1d,0) 96 ktrace GIO fd 2 wrote 29 bytes "exec of '/sw/bin/dpkg' failed" 96 ktrace RET write 29/0x1d 96 ktrace CALL write(0x2,0x2,0) 96 ktrace GIO fd 2 wrote 2 bytes ": " 96 ktrace RET write 2 96 ktrace CALL write(0x2,0x23,0) 96 ktrace GIO fd 2 wrote 35 bytes "Bad executable (or shared library) " 96 ktrace RET write 35/0x23 96 ktrace CALL exit(0x1) darwin:~ root#
vasi: "ktrace can only trace userland stuff... the fact that it traced almost nothing would seem to indicate that the kernel is where the problem is seen. You can see that it calls 'execve' which fails. syscall fails => kernel problem"
Can it be that the latest Darwin ISO for x86 that Apple distributes refuses to run even the simplest CLI binaries built for Mac OS X 10.4.x Intel?
Apparently this is a Darwin bug. Please note here if otherwise. Maybe related to this?
Installing software from GNU-Darwin (fails)
GNU-Darwin hosts pre-compiled software for Darwinx86 as well. (Looking at their repository, most packages appear to be five years old however.)
curl http://www.gnu-darwin.org/packages/x86/www/wget-1.8.2_2.tgz -o wget-1.8.2_2.tgz tar xfvz wget-1.8.2_2.tgz ./bin/wget Bus error
Further investigation required. Please note any solution here.
Shrinking Darwin
Let's remove things that are not required for (minimal) operation
rm -rf /usr/include (0.2 GB) # header files find / -type f | grep "\.h$" | xargs -I {} rm -f {} # more header files rm -rf /opt/apache /usr/libexec/httpd/ # apache rm -rf /usr/local/ # (0.3 GB) apparently all optional stuff rm -rf /usr/share/man # (0.1 GB) documentation
It's probably better to do a "bottom-up" approach and install only those packages that we really want.
.root.tar.bz2 "Uninstaller" script
Since there appears to be no "uninstaller" for Darwin's .root.tar.bz2 packages, I wrote one.
It takes two arguments:
- path/to/root/partition (e.g. /Volumes/Darwin - the files contained in the .root.tar.bz2 are deleted from this volume
- path/to/package.root.tar.bz2 - the .root.tar.bz2 whose files you want to delete from the installed system
#!/bin/sh # # Package deleter script for Darwin # GPL # 0.1 # PACK=$2 PART=$1 function usage { echo " " echo "Package deleter script for Darwin" echo " " echo "Usage: $0 path/to/root/partition path/to/package.root.tar.bz2" echo " " exit 1 } # Check for correct number of arguments if [ "x$2" == "x" ] ; then usage fi # Exit if file is not bzip2 file "$PACK" | grep bzip2 >/dev/null || usage # Exit if there is no mach_kernel file "$PART/mach_kernel" | grep Mach-O >/dev/null || usage FILES=$( tar -tjvf ${PACK} | sort -r | awk '{print $6}' | sed "s|^\.\/|$PART\/|" ) f=0 d=0 for FILE in $FILES; do rm -f "$FILE" 2>/dev/null && let "f++" done for FILE in $FILES; do rmdir -p "$FILE" 2>/dev/null && let "d++" done echo "$f files and $d directories deleted"
Removing the following packages brings Darwin down to around 450 MB: apache- apache2- apache_mod_dav- apache_mod_hfs_apple-* apache_mod_perl-* apache_mod_php-* apache_mod_ssl-* autoconf-* automake-* bison-* bsdmake-* bsdmanpages-* cctools-* cctools_ofiles-* cups-* cups_ppc-* cvs-* cvs_wrapped-* cxxfilt-* developer_cmds-* diffstat-* distcc-* doc_cmds-* efax-* emacs-* enscript-* fetchmail-* flex-* gcc-* gcc_os-* gcc_os_35-* gcc_select-* gccfast-* gdb-* gimp_print-* glibtool-* gm4-* gnudiff-* gnumake-* gnuserv-* gperf-* groff-* graphviz-* headerdoc-* iodbc-* jam-* lukemftp-* lukemftpd-* mailman-* man-* modemccl-* net_snmp-* netcat-* objc4-* patch_cmds-* pb_makefiles-* pbx_jamfiles-* portmap-* postfix-* ppp-* procmail-* project_makefiles-* python-* rcs-* ruby-* samba-* screen-* smb-* srm-* stmalloc-* tcl-* tcpdump-* tcsh-* texi2html-* texinfo-* tidy-* vim-* webdavfs-* yacc-* zsh-*
Can perl-* be safely removed?
Installing "Darwin nano" on bootable USB drive
This is not working yet. Any help is greatly appreciated. From the experiments above it is apparent that this should work.
Plan
# Get Darwin 8.0.1 ISO for i386 from Apple # Boot it into single user mode (see above). From booted Darwin, do: # Prepare USB stick by formatting it as HFS+ (Journaled) and enabling permissions # Copy /usr /bin /sbin /System /Library /private /cores /mach_kernel from ISO to USB drive # (maybe need to use the .root.tar.bz2 files instead, see above) # Bless USB stick and set partition active # Change Boot.plist # Fix permissions and touch Extensions # Boot USB stick
This easily fits on a 512 MB USB stick, and probably can be slimmed down further (e.g. for embedded applications).
This does boot, but as soon as the kernel is supposed to appear, it reboots the PC (even before printing a kernel panic).
Minimal number of packages to boot the Darwin kernel
What are the minimum required packages that need to be installed in order to boot the Darwin kernel and to bring up a minimal shell?
# Please collect here xnu-792.root.tar.bz2 # contains the kernel objc4-266.root.tar.bz2 # can't log in otherwise (might not be required for -s) # ...
To look what is inside:
tar -tjvf xnu-792.root.tar.bz2
Darwin versions
- Darwin 8.0.1 = Mac OS X 10.4.x (what this page focuses on)
- Darwin 7.0.1 = Mac OS X 10.3.x
- Darwin 6.0.2 = Mac OS X 10.2.x
- Darwin 1.4.1 = Mac OS X 10.1.x
- Darwin 1.3.1 = Mac OS X 10.0.x
- Darwin 1.2.1 = Mac OS X Public Beta
- Darwin 1.0.2 = Developer Preview 4
Darwin install script
To be reviewed and to be re-used. Despite the fact that it says "OpenDarwin", it is from Darwin proper. Apparently this is a Darwin bug. Please note here if otherwise.
#!/bin/sh # OpenDarwin install script # $Id: rc.cdrom,v 1.30 2005/04/28 20:06:46 kevin Exp $ PATH=/bin:/sbin:/usr/bin:/usr/sbin:/usr/libexec:/etc:/private/etc ; export PATH ARCH=`arch` TARGET_MOUNT=/mnt AVAIL_SHELLS="sh tcsh csh bash zsh" T_UID_DEFAULT=1000 T_GID_DEFAULT=1000 abort () { echo "Aborting the installation" echo "Press enter to reboot" read REBOOT shutdown -r now } umount_target_disk () { umount -f ${ROOTPART} } finishup () { echo "Installation of the base system is now complete." echo "You may: " until [ ! : ] do echo "1) add a user to the new system" echo "2) Reboot" echo "3) Spawn a shell" echo -n "Your Choice: " read CHOICE case ${CHOICE} in 1) add_user ;; 2) umount_target_disk shutdown -r now break ;; 3) umount_target_disk /bin/sh break ;; esac done } add_user () { # a few helper vars # make T_PW and T_PW_2 not equal ADMIN_USER=0 SHELL_VALID=0 T_PW=0 T_PW_2=1 echo "" echo -n "Username: " read T_USERNAME echo -n "Realname: " read T_REALNAME echo -n "UID (default: ${T_UID_DEFAULT}): " read T_UID echo -n "GID (default: ${T_GID_DEFAULT}): " read T_GID if [ "$T_UID" == "" ]; then T_UID=${T_UID_DEFAULT} fi if [ "$T_GID" == "" ]; then T_GID=${T_GID_DEFAULT} fi until [ "$SHELL_VALID" == "1" ]; do echo -n "Available shells: " for shell in ${AVAIL_SHELLS} do echo -n "${shell} " done echo "" echo -n "Shell: " read T_SHELL; for shell in ${AVAIL_SHELLS} do if [ "$T_SHELL" == "$shell" ]; then SHELL_VALID=1 fi done done echo -n "Home directory (default: /Users/${T_USERNAME}): " read T_HOMEDIR; if [ "$T_HOMEDIR" == "" ]; then T_HOMEDIR=/Users/${T_USERNAME} fi echo -n "Add ${T_USERNAME} to the admin group? (yes/no): " read CHOICE; if [ "$CHOICE" == "yes" ]; then ADMIN_USER=1 fi while [ 1 ]; do T_PW=`openssl passwd` if [ ${?} == "0" ]; then break fi done echo "" echo "Username: ${T_USERNAME}" echo "Realname: ${T_REALNAME}" echo "UID: ${T_UID}" echo "GID: ${T_GID}" echo "Shell: ${T_SHELL}" echo "Home: ${T_HOMEDIR}" echo "" echo -n "Add (yes/no): " read CHOICE if [ "$CHOICE" == "yes" ]; then nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/${T_USERNAME} passwd ${T_PW} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/${T_USERNAME} realname ${REALNAME} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/${T_USERNAME} uid ${T_UID} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/${T_USERNAME} gid ${T_GID} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/${T_USERNAME} shell /bin/${T_SHELL} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/${T_USERNAME} home ${T_HOMEDIR} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /groups/${T_USERNAME} name ${T_USERNAME} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /groups/${T_USERNAME} gid ${T_GID} nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /groups/${T_USERNAME} passwd "*" if [ "$ADMIN_USER" == "1" ]; then nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /groups/admin users ${T_USERNAME} fi mkdir -p ${TARGET_MOUNT}/${T_HOMEDIR} chown ${T_UID}:${T_GID} ${TARGET_MOUNT}/${T_HOMEDIR} echo "User ${T_USERNAME} created" echo "" if [ "$T_UID" == "$T_UID_DEFAULT" ]; then T_UID_DEFAULT=$(($T_UID_DEFAULT+1)) T_GID_DEFAULT=$(($T_GID_DEFAULT+1)) fi fi } # and a way to iterate through the list of available services # with a method to initialize them enable_various_services() { echo "Following services can be enabled: " chroot ${TARGET_MOUNT} /sbin/service --list while [ 1 ]; do echo -n "Enter service to enabled ('quit' to abort, list to print list): " read SERVICE if [ "$SERVICE" == "quit" ]; then break fi if [ "$SERVICE" == "list" ]; then chroot ${TARGET_MOUNT} /sbin/service --list else echo "Enabling service: ${SERVICE}" sed -e 's/disable.*=.*yes/disable = no/' < ${TARGET_MOUNT}/etc/xinetd.d/${SERVICE} > ${TARGET_MOUNT}/etc/xinetd.d/${SERVICE}.new mv ${TARGET_MOUNT}/etc/xinetd.d/${SERVICE}.new ${TARGET_MOUNT}/etc/xinetd.d/${SERVICE} fi done } choose_filesystem_type () { while [ 1 ]; do echo "Choose the filesystem type from the following." echo " hfs) HFS+ (journaled) filesystem" echo " ufs) UFS filesystem" echo -n "Filesystem type: " read FILESYSTEMTYPE if [ "$FILESYSTEMTYPE" == "hfs" -o "$FILESYSTEMTYPE" == "ufs" ]; then break fi done } # This function will nuke the whole disk and create the 0xAB and 0xA8 # partitions. $INSTALLDEV and $RAWINSTDEV need to be set to the # device to nuke, and the corresponding raw device. partition_disk () { # needs help on ppc echo "Partitioning disk ${INSTALLDEV} using filesystem type ${FILESYSTEMTYPE}" echo "Warning: this will destroy all data on the disk!" echo -n "Continue? (y/n) " read CONT if [ "${CONT}" == "y" -o "${CONT}" == "yes" ]; then fdisk -i -y -a ${FILESYSTEMTYPE} ${RAWINSTDEV} else abort fi } # This will look for partitions on the selected disk, and # allow the user to select the 0xA8 partitions to use. # $INSTALLDEV needs to be set to the device to look for, # and $ROOTPART will be set to the chosen value upon return. use_partitions () { echo "" PARTS=`ls -1 ${INSTALLDEV}s*` echo "The following partitions are available:" for devs in ${PARTS} do echo ${devs} done ROOTPART="" until [[ ${ROOTPART} != "" && -b ${ROOTPART} ]] do echo "Which will be the root partition?" read ROOTPART done echo "Using: " echo "${ROOTPART} as the root partition" } # This just runs fdisk interactivly on the chosen raw install device run_fdisk () { echo "Starting fdisk" if [ "${ARCH}" == "i386" ]; then fdisk -e ${RAWINSTDEV} elif [ "${ARCH}" == "ppc" ]; then /usr/sbin/pdisk fi } install_booter () { if [ "${ARCH}" == "i386" ]; then cd / umount -f ${ROOTPART} RAWROOTPART=`echo ${ROOTPART} | sed 's/disk/rdisk/'` if [ "${FILESYSTEMTYPE}" == "ufs" ]; then dd if=/usr/standalone/i386/boot1u of=${RAWROOTPART} bs=512 count=15 >>/dev/null 2>&1 elif [ "${FILESYSTEMTYPE}" == "hfs" ]; then dd if=/usr/standalone/i386/boot1h of=${RAWROOTPART} bs=512 count=1 >>/dev/null 2>&1 /usr/sbin/startupfiletool ${RAWROOTPART} /usr/standalone/i386/boot >/dev/null 2>&1 bless -device ${ROOTPART} -setBoot >/dev/null 2>&1 fi mount -t ${FILESYSTEMTYPE} ${ROOTPART} ${TARGET_MOUNT} bless -mount ${TARGET_MOUNT} -setBoot >/dev/null 2>&1 cd ${TARGET_MOUNT} elif [ "${ARCH}" == "ppc" ]; then bless -folder ${TARGET_MOUNT}/System/Library/CoreServices -folder9 ${TARGET_MOUNT}/System/Library/CoreServices -bootinfo ${TARGET_MOUNT}/usr/standalone/ppc/bootx.bootinfo -setBoot fi } install_packages () { VOLUMENAME="Darwin" echo "WARNING: answering "yes" here will destroy all data on the partition" until [ ! : ] do echo -n "Would you like to do a clean install? (yes/no)" read ANSWER if [ "$ANSWER" == "yes" ]; then echo -n "Desired Volumename: " read VOLUMENAME echo "Creating ${FILESYSTEMTYPE} Filesystem on ${ROOTPART}" if [ "${FILESYSTEMTYPE}" == "hfs" ]; then newfs_hfs -J -v "${VOLUMENAME}" ${ROOTPART} >> /dev/null 2>&1 break elif [ "${FILESYSTEMTYPE}" == "ufs" ]; then newfs -v "${VOLUMENAME}" ${ROOTPART} >> /dev/null 2>&1 break else echo "error: nknown filesystem type: $FILESYSTEMTYPE" abort fi elif [ "$ANSWER" == "no" ]; then break fi done mount -t ${FILESYSTEMTYPE} ${ROOTPART} ${TARGET_MOUNT} cd ${TARGET_MOUNT} echo "Installing packages on ${ROOTPART}" for f in /System/Installation/Packages_${ARCH}/files-*.tar.bz2 \ /System/Installation/Packages_${ARCH}/*-*.tar.bz2 \ /System/Installation/BinaryDrivers_${ARCH}/*-*.tar.bz2 ; do echo "Uncompressing $(basename $f)" tar xjpf $f 2>/dev/null if [ "$?" != "0" ]; then echo "warning: error during extraction" fi done cd / } main() { if [ -f "/Release Notes.txt" ]; then echo "" echo "Welcome to the installation of" `grep 'Darwin [0-9.-]*' /Release\ Notes.txt | head -1 | awk '{print $1" "$2}'` echo "" fi if [ -f "/Important Notice.txt" ]; then cat "/Important Notice.txt" fi # Get the device the user wants to install onto. INSTALLDEV="novalue" until [[ ${INSTALLDEV} != "" && -b ${INSTALLDEV} ]] do echo "The following devices are available for installation:" until [[ ! -z "${FOO}" ]] do FOO=`iofindwholemedia` done iofindwholemedia echo "Enter 'shell' to drop into a shell" echo -n "Which device would you like to install Darwin onto? " read INSTALLDEV if [ "${INSTALLDEV}" == "shell" ]; then exec /bin/sh fi INSTALLDEV=`iofindwholemedia ${INSTALLDEV}` if [ ! -b "${INSTALLDEV}" ]; then echo "" echo "${INSTALLDEV} doesn't exist, please enter one of the listed devices." echo "" fi done RAWINSTDEV=`echo ${INSTALLDEV} | sed 's/disk/rdisk/'` if [ "${ARCH}" == "i386" ]; then if fdisk -t ${RAWINSTDEV} ; then echo "" echo "For partitioning the disk, you have the following choices:" until [ ! : ] do echo "1) Auto-partition the disk (Destroys all disk contents)" echo "2) Manually partition the disk using fdisk" echo "3) Use existing partitions" echo -n "Choice: " read ANSWER case ${ANSWER} in 1) choose_filesystem_type partition_disk # Don't ask which to use, since we already know. ROOTPART="${INSTALLDEV}s1" break ;; 2) run_fdisk use_partitions choose_filesystem_type break ;; 3) use_partitions choose_filesystem_type break ;; esac done else echo "" echo "For partitioning the disk, you have the following choices:" until [ ! : ] do echo "1) Auto-partition the disk (Destroys all disk contents)" echo "2) Manually partition the disk using fdisk" echo -n "Choice: " read ANSWER case ${ANSWER} in 1) partition_disk # Don't ask which to use, since we already know. ROOTPART="${INSTALLDEV}s1" break ;; 2) run_fdisk use_partitions break ;; esac done fi elif [ "${ARCH}" == "ppc" ]; then until [ ! : ] do FILESYSTEMTYPE="hfs" echo "Which (Apple_HFS) partition would you like to install into: " pdisk --list ${INSTALLDEV} 2> /dev/null slice="" until [[ "$slice" != "" && -b ${INSTALLDEV}s${slice} ]] do echo -n "Your choice: " read slice done ROOTPART="${INSTALLDEV}s${slice}" break done fi install_packages install_booter echo 'LANGUAGE=English' > ${TARGET_MOUNT}/var/log/CDIS.custom echo "Updating mkext cache" export TMPDIR=${TARGET_MOUNT}/private/tmp kextcache -K ${TARGET_MOUNT}/mach_kernel -a ${ARCH} -m ${TARGET_MOUNT}/System/Library/Extensions.mkext ${TARGET_MOUNT}/System/Library/Extensions 2>/dev/null export -n TMPDIR echo "Creating root user" # loop until password was entered the same twice while [ 1 ]; do ROOT_PW=`openssl passwd` if [ ${?} == "0" ]; then break fi done nicl -raw ${TARGET_MOUNT}/var/db/netinfo/local.nidb -create /users/root passwd ${ROOT_PW} echo -n "Set computer name (Bonjour hostname): " read BONJOUR configd echo "$BONJOUR" | chroot ${TARGET_MOUNT} scutil --set ComputerName echo "$BONJOUR" | tr A-Z a-z | sed -e 's/[^a-z0-9_-][^a-z0-9_-]*/-/g' | chroot ${TARGET_MOUNT} scutil --set LocalHostName echo "Configuring emacs" chroot ${TARGET_MOUNT} /usr/libexec/dumpemacs > /dev/null 2>&1 finishup } # Set the erase character properly # This is only for telnet consoles... #stty erase � # Ignore ^C #trap "" 2 main exit
Bug reporting
Please do not flood Apple with bug reports. It is more likely that Darwin bugs get addressed properly if bug reports are well-written and thorougly documented. Let's provide Apple with high-quality bug reports in their preferred format through their official channels, then it is most likely that they will be considered.