Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Save narainsagar/6faa045754878d0f11b3801aef15dd39 to your computer and use it in GitHub Desktop.
Save narainsagar/6faa045754878d0f11b3801aef15dd39 to your computer and use it in GitHub Desktop.
Create Bootable MacOS ISO from Apple's Free PKG

How to create a bootable installer for macOS

Task

Convert mac-os-el-capitan-pkg-to-iso.sh from using hdiutil and asr to using Linux utilities.

See https://gist.github.com/solderjs/22d08c4b582779485e0df11c5d84063a#file-mac-os-el-capitan-pkg-to-iso-sh

Steps

Important: You will need about 30GB of free disk space.

  1. Download OS X 1.11 El Capitan InstallMacOSX.dmg from Apple (7GB)
  2. Install hfsprogs, hfsplus, & hfsutils
  3. Install xar
  4. dmg2img and mount can be used to to mount InstallMacOSX.dmg
  5. xar can be used to extract InstallMacOSX.pkg (another 7GB)
  6. InstallMacOSX.pkg/InstallESD.dmg must be mounted to find BaseSystem.dmg
  7. BaseSystem.dmg must be copied to a larger read/write AFPS file system (another 8GB)
  8. Certain install files must be copied (see script).
  9. The new image must be converted to ISO. (another 8GB)

Resources

Mount dmg in Linux

apt install -y hfsprogs hfsplus hfsutils dmg2img build-essential libxml2-dev libssl1.0-dev zlib1g-dev

dmg2img InstallMacOSX.dmg #image is compressed, need to decompress

losetup -P -f InstallMacOSX.img #make block devices for each partition
mkdir -p /mnt/loop
mount /dev/loop0p2 /mnt/loop 

Install xar (pkg unzip) in Linux

sudo apt install -y build-essential autoconf
sudo apt install -y libxml2-dev libssl1.0-dev

Method 1

git clone git@github.com/mackyle/xar.git
pushd xar/xar
./autogen.sh
make -j
sudo make install

Method 2

wget https://storage.googleapis.com/google-code-archive-downloads/v2/code.google.com/xar/xar-1.5.2.tar.gz
tar -zxvf xar-1.5.2.tar.gz
pushd xar-1.5.2
./configure
make -j
sudo make install

Method 3:

See mackyle/xar#18

Here's what you need to do: In configure.ac, line 332 is:

AC_CHECK_LIB([crypto], [OpenSSL_add_all_ciphers], , [have_libcrypto="0"])

Replace it with:

AC_CHECK_LIB([crypto], [OPENSSL_init_crypto], , [have_libcrypto="0"])

Unpacking .pkg (via xar) in Linux

mkdir ./MacOSX && cd ./MacOSX
xar -xvf /mnt/loop/InstallMacOSX.pkg

How this works on MacOS

Watch Video: https://youtu.be/uNPp7IbmfsY

OS X Installer ISO Creator

Pre-reqs:

  1. Download OS X 1.11 El Capitan from Apple
  2. Install VirtualBox 6.1.4
  3. Install the VirtualBox Extension Pack
  4. Create a Virtual Machine named EXACTLY "OS X El Capitan"
    • change RAM to 4GB
    • change CPU cores to 2
  5. DO NOT start the virtual machine!!
# Clone this gist as 'mac-os-el-capitan-installer'
git clone https://gist.github.com/22d08c4b582779485e0df11c5d84063a.git ./mac-os-el-capitan-installer

# Move into the 'mac-os-el-capitan-installer' folder
pushd ./mac-os-el-capitan-installer

# Download the full El Capitan installer (free and legal, direct from Apple)
# and convert the downloaded pkg to an ISO
bash mac-os-el-capitan-pkg-to-iso.sh

# Add Apple-specific values and recommended VirtualBox settings
bash virtualbox-el-capitan.sh

Now it is okay to start the virtual machine and select the disk image.

ISO Properties

The empty image (included in this repo):

file ./empty.7900m.dmg
./empty.7900m.dmg: Apple Driver Map, blocksize 512, blockcount 16179200, devtype 0, devid 0, driver count 0, contains[@0x200]: Apple Partition Map, map block count 2, start block 1, block count 63, name Apple, type Apple_partition_map, valid, allocated, contains[@0x400]: Apple Partition Map, map block count 2, start block 64, block count 16179136, name disk image, type Apple_HFS, valid, allocated, readable, writable, mount at startup

The final image (all files copied over):

file ./elcapitan.iso 
./elcapitan.iso: Apple Driver Map, blocksize 512, blockcount 16179200, devtype 0, devid 0, driver count 0, contains[@0x200]: Apple Partition Map, map block count 2, start block 1, block count 63, name Apple, type Apple_partition_map, valid, allocated, contains[@0x400]: Apple Partition Map, map block count 2, start block 64, block count 16179136, name disk image, type Apple_HFS, valid, allocated, readable, writable, mount at startup

El Capitan Checksums

  • InstallOSX.dmg
    • MD5 5040a59d785d7da609755244c4ed136c
    • SHA1 21e45136e34c6f805e0f1977e38d6ff029a9a1e2
    • SHA2 bca6d2b699fc03e7876be9c9185d45bf4574517033548a47cb0d0938c5732d59
  • elcapitan.iso
    • MD5 704e6246548b4c5670c49ab452f4b120
    • SHA1 5286ee4185e0814b77df368830ca8f8ef832f4c0
    • SHA2 6eeb5fa50411085564676bd446be82e579084f2a2c71f88fb9830c62c531f0eb
# set strict and verbose modes for bash
set -e
set -u
# Apple provides El Capitan, free of charge
# El Capitan can be upgraded all the way to Catalina, free of charge
# See "How to upgrade to OS X El Capitan"
# https://support.apple.com/en-us/HT206886
# Download legal, free copy of El Capitan from Apple
# (they also have Sierra, but that didn't boot for me)
# Go to https://support.apple.com/en-us/HT206886 and find the link "Download OS X El Capitan"
# (it changes every day)
# http://updates-http.cdn-apple.com/2019/cert/061-41424-20191024-218af9ec-cf50-4516-9011-228c78eda3d2/InstallMacOSX.dmg
if ! [ -f "InstallMacOSX.dmg" ]; then
echo "Error: Did not find 'InstallMacOSX.dmg'"
echo " 1. Go to https://support.apple.com/en-us/HT206886"
echo " 2. Click 'Download OS X El Capitan'"
echo " 3. Copy 'InstallMacOSX.dmg' to this folder"
exit 1
fi
if [ -f "elcapitan.iso" ]; then
echo "'elcapitan.iso' already exists"
exit 0
fi
# Much of this script came from the instructions here:
# https://techsviewer.com/install-macos-elcapitan-virtualbox-windows/
set -x
# Mount the Full Installer
hdiutil attach InstallMacOSX.dmg -noverify -nobrowse -mountpoint '/Volumes/Install OS X/'
pkgutil --expand '/Volumes/Install OS X/InstallMacOSX.pkg' './Install OS X/'
hdiutil detach '/Volumes/Install OS X'
# Mount DMG Installer to macOS
hdiutil attach './Install OS X/InstallMacOSX.pkg/InstallESD.dmg' -noverify -nobrowse -mountpoint '/Volumes/OS X Install ESD/'
# Create a DMG Disk
# (this exact file created by this command is included in the repo as 'empty.7900m.dmg.bz2')
hdiutil create -o /tmp/elcapitan -size 7900m -volname elcapitan -layout SPUD -fs HFS+J
# Mount Sierra.dmg disk to your macOS
hdiutil attach /tmp/elcapitan.dmg -noverify -mountpoint /Volumes/elcapitan
# Create macOS Sierra Installer Disk
asr restore -source '/Volumes/OS X Install ESD/BaseSystem.dmg' -target /Volumes/elcapitan -noprompt -noverify -erase
rm '/Volumes/OS X Base System/System/Installation/Packages'
cp -rp '/Volumes/OS X Install ESD/Packages' '/Volumes/OS X Base System/System/Installation/'
cp -rp '/Volumes/OS X Install ESD/BaseSystem.chunklist' '/Volumes/OS X Base System'
cp -rp '/Volumes/OS X Install ESD/BaseSystem.dmg' '/Volumes/OS X Base System'
hdiutil detach '/Volumes/OS X Base System'
hdiutil detach '/Volumes/OS X Install ESD'
# Convert DMG Disk to ISO File
hdiutil convert /tmp/elcapitan.dmg -format UDTO -o /tmp/elcapitan
# Move ISO File to Desktop
mv /tmp/elcapitan.cdr elcapitan.iso
# Cleanup
rm /tmp/elcapitan.dmg
rm -rf './Install OS X/'
hdiutil create: create a disk image image
Usage: hdiutil create <sizespec> <imagepath>
Size specifiers:
-size < ?? | ??b | ??k | ??m | ??g | ??t | ??p | ??e >
-sectors <count>
-megabytes <count>
Image options:
-library <MKDrivers>
-layout <layout> [GPTSPUD or per -fs]
MBRSPUD - Single partition - Master Boot Record Partition Map
SPUD - Single partition - Apple Partition Map
UNIVERSAL CD - CD/DVD
NONE - No partition map
GPTSPUD - Single partition - GUID Partition Map
SPCD - Single partition - CD/DVD
UNIVERSAL HD - Hard disk
ISOCD - Single partition - CD/DVD with ISO data
-partitionType <partitionType> [Apple_HFS or per -fs]
-align <sector alignment> [8 sectors]
-ov
Filesystem options:
-fs <filesystem>
UDF - Universal Disk Format (UDF)
MS-DOS FAT12 - MS-DOS (FAT12)
MS-DOS - MS-DOS (FAT)
MS-DOS FAT16 - MS-DOS (FAT16)
MS-DOS FAT32 - MS-DOS (FAT32)
HFS+ - Mac OS Extended
Case-sensitive HFS+ - Mac OS Extended (Case-sensitive)
Case-sensitive Journaled HFS+ - Mac OS Extended (Case-sensitive, Journaled)
Journaled HFS+ - Mac OS Extended (Journaled)
ExFAT - ExFAT
Case-sensitive APFS - APFS (Case-sensitive)
APFS - APFS
-volname <volumename> ["untitled"]
-stretch < ?? | ?b | ??k | ??m | ??g | ??t | ??p | ??e > (HFS+)
New Blank Image options:
-type <image type> [UDIF]
SPARSEBUNDLE - sparse bundle disk image
SPARSE - sparse disk image
UDIF - read/write disk image
UDTO - DVD/CD master
-[no]spotlight do (not) create a Spotlight™ index
Image from Folder options:
-srcfolder <source folder>
-[no]spotlight do (not) create a Spotlight™ index
-[no]anyowners do (not) attempt to preserve owners
-[no]skipunreadable do (not) skip unreadable objects [no]
-[no]atomic do (not) copy to temp location and then rename [yes]
-srcowners on|off|any|auto [auto]
on enable owners on source
off disable owners on source
any leave owners state on source unchanged
auto enable owners if source is a volume
-format <image type> [UDZO]
UDRO - read-only
UDCO - compressed (ADC)
UDZO - compressed
UDBZ - compressed (bzip2)
ULFO - compressed (lzfse)
ULMO - compressed (lzma)
UFBI - entire device
IPOD - iPod image
UDxx - UDIF stub
UDSB - sparsebundle
UDSP - sparse
UDRW - read/write
UDTO - DVD/CD master
DC42 - Disk Copy 4.2
RdWr - NDIF read/write
Rdxx - NDIF read-only
ROCo - NDIF compressed
Rken - NDIF compressed (KenCode)
UNIV - hybrid image (HFS+/ISO/UDF)
SPARSEBUNDLE - sparse bundle disk image
SPARSE - sparse disk image
UDIF - read/write disk image
UDTO - DVD/CD master
Image from Device options:
Note: Filesystem options (-fs, -volname, -stretch) ignored with -srcdevice
-srcdevice <source dev node, e.g. disk1, disk2s1>
-format <image type> [UDZO]
UDRO - read-only
UDCO - compressed (ADC)
UDZO - compressed
UDBZ - compressed (bzip2)
ULFO - compressed (lzfse)
ULMO - compressed (lzma)
UFBI - entire device
IPOD - iPod image
UDxx - UDIF stub
UDSB - sparsebundle
UDSP - sparse
UDRW - read/write
UDTO - DVD/CD master
DC42 - Disk Copy 4.2
RdWr - NDIF read/write
Rdxx - NDIF read-only
ROCo - NDIF compressed
Rken - NDIF compressed (KenCode)
-segmentSize < ?? | ??b | ??k | ??m | ??g | ??t | ??p | ??e >
(sectors, bytes, KiB, MiB, GiB, TiB, PiB, EiB)
Attach options:
-attach attach image after creation
Common options:
-encryption <crypto method>
AES-128 - 128-bit AES encryption (recommended)
AES-256 - 256-bit AES encryption (more secure, but slower)
-stdinpass
-agentpass
-certificate <path-to-cert-file>
-pubkey <public-key-hash>[,pkh2,...]
-imagekey <key>=<value>
-tgtimagekey <key>=<value>
-plist
-puppetstrings
-verbose
-debug
-quiet
pushd "C:\Program Files\Oracle\VirtualBox\"
VBoxManage modifyvm "OS X El Capitan" --cpuidset 00000001 000106e5 00100800 0098e3fd bfebfbff
VBoxManage setextradata "OS X El Capitan" "VBoxInternal/Devices/efi/0/Config/DmiSystemProduct" "iMac11,3"
VBoxManage setextradata "OS X El Capitan" "VBoxInternal/Devices/efi/0/Config/DmiSystemVersion" "1.0"
VBoxManage setextradata "OS X El Capitan" "VBoxInternal/Devices/efi/0/Config/DmiBoardProduct" "Iloveapple"
VBoxManage setextradata "OS X El Capitan" "VBoxInternal/Devices/smc/0/Config/DeviceKey" "ourhardworkbythesewordsguardedpleasedontsteal(c)AppleComputerInc"
VBoxManage setextradata "OS X El Capitan" "VBoxInternal/Devices/smc/0/Config/GetKeyFromRealSMC" 1
REM pick either of these, but not both
VBoxManage setextradata "OS X El Capitan" VBoxInternal2/EfiGopMode 3
REM VBoxManage setextradata "OS X El Capitan" "VBoxInternal2/EfiGraphicsResolution" "1920x1080"
VBoxManage modifyvm "OS X El Capitan" --memory 3072 --cpus 2 --vram 128
VBoxManage modifyvm "OS X El Capitan" --boot1 dvd --boot2 disk --boot3 none --boot4 none
VBoxManage modifyvm "OS X El Capitan" --usb on --usbxhci on
REM VBoxManage modifyvm "OS X El Capitan" --nic1 bridged --bridgeadapter1 en0
REM TODO mark hard drive as --nonrotational
# set strict and verbose modes for bash
set -e
set -u
set -x
###############################################
# VirtualBox Configuration for OS X and MacOS #
###############################################
# my_vm must EXACTLY match the name in the VirtualBox VM list
my_vm="OS X El Capitan"
# I believe that this sets the CPU ID to match that on an actual Apple motherboard
VBoxManage modifyvm "$my_vm" --cpuidset 00000001 000106e5 00100800 0098e3fd bfebfbff
# This is just the common product name. "MacBookPro11,3" is another valid option
VBoxManage setextradata "$my_vm" "VBoxInternal/Devices/efi/0/Config/DmiSystemProduct" "iMac11,3"
VBoxManage setextradata "$my_vm" "VBoxInternal/Devices/efi/0/Config/DmiSystemVersion" "1.0"
# This seems to be arbitrary
VBoxManage setextradata "$my_vm" "VBoxInternal/Devices/efi/0/Config/DmiBoardProduct" "Iloveapple"
# A special key Apple uses to determine if a product is genuine
VBoxManage setextradata "$my_vm" "VBoxInternal/Devices/smc/0/Config/DeviceKey" "ourhardworkbythesewordsguardedpleasedontsteal(c)AppleComputerInc"
VBoxManage setextradata "$my_vm" "VBoxInternal/Devices/smc/0/Config/GetKeyFromRealSMC" 1
#############################
# Set the Screen Resolution #
# (may require vbox guest) #
#############################
# You can pick either way of setting these settings, but NOT both
# (otherwise you have to shut down the VM and manually edit the .vbox XML file to remove it)
VBoxManage setextradata "$my_vm" VBoxInternal2/EfiGopMode 3
#VBoxManage setextradata "$my_vm" VBoxInternal2/EfiGopMode 4
# 0 640x480
# 1 800x600
# 2 1024x768
# 3 1280x1024
# 4 1440x900
# 5 1900x1200
#VBoxManage setextradata "$my_vm" "VBoxInternal2/EfiGraphicsResolution" "1920x1080"
# 1280×720 (HD)
# 1920×1080 (FHD)
# 2560×1440 (QHD)
# 2048×1080 (2K)
# 3840×2160 (4K)
# 5120×2880 (5K)
####################
# General Settings #
####################
VBoxManage modifyvm "$my_vm" --memory 4096 --cpus 2 --vram 128
VBoxManage modifyvm "$my_vm" --boot1 dvd --boot2 disk --boot3 none --boot4 none
VBoxManage modifyvm "$my_vm" --usb on --usbxhci on
#VBoxManage modifyvm "$my_vm" --nic1 bridged --bridgeadapter1 en0
# TODO mark hard drive as --nonrotational
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment