Last active
September 29, 2023 10:22
-
-
Save iwalfy/eb137b0b705683aa427ed29311ed1b30 to your computer and use it in GitHub Desktop.
Simple script to extract PNG image assets from Apple's EFI Firmwares using UEFIExtract and binwalk
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env bash | |
# | |
# Simple script to extract PNG assets from Apple's Mac EFI Firmware | |
# Works for all firmwares 2005-2021 | |
# | |
# Requirements: pkgutil (for pkg firmwares), binwalk, find | |
# | |
# (c) Mikhail Lebedinets, 2023 | |
# | |
set -e | |
TEMP_DIR="firmware_extract_$RANDOM" | |
usage() { | |
echo "Usage: $0 <firmware dump/installaer package> <output images directory>" | |
} | |
if [ $# -lt 2 ]; then | |
usage | |
exit 1 | |
fi | |
input_file="$1" | |
output_dir="$2" | |
if [ ! -f "$input_file" ]; then | |
echo "!!! Error: Firmware file does not exists" | |
exit 1 | |
fi | |
if [ ! -d "$output_dir" ]; then | |
echo "-> Output directory created" | |
mkdir "$output_dir" | |
fi | |
mkdir "$TEMP_DIR" | |
uefi_extract_path=$(whereis UEFIExtract | awk '{print $2}') | |
if [ ! "$uefi_extract_path" ]; then | |
echo "-> UEFIExtract not found in your PATH" | |
echo "--> Downloading latest UEFIExtract..." | |
wget "https://github.com/LongSoft/UEFITool/releases/download/A67/UEFIExtract_NE_A67_universal_mac.zip" -O "$TEMP_DIR/UEFIExtract.zip" | |
uefi_extract_path="$TEMP_DIR/UEFIExtract" | |
echo "---> Unzipping..." | |
unzip -j "$TEMP_DIR/UEFIExtract.zip" -d "$TEMP_DIR" | |
chmod +x "$uefi_extract_path" | |
fi | |
firmware_file="$input_file" | |
if [[ $input_file == *.pkg ]]; then | |
echo "-> Detected package installer" | |
echo "--> Extracting package..." | |
pkg_contents="$TEMP_DIR/pkg_contents" | |
pkgutil --expand "$input_file" "$pkg_contents" | |
firmware_file=$(find "$pkg_contents" -type f -regex ".*\.scap") | |
if [ $(echo "$firmware_file" | wc -l) -gt 1 ]; then | |
echo "!!! This package has more than one image. You should extract required manually" | |
echo "$firmware_file" | |
exit 3 | |
fi | |
if [ ! "$firmware_file" ]; then | |
echo "-> Firmware file not found (trying to find in Payload)" | |
tar -xvf $(find "$pkg_contents" -type f -name "Payload") -C "$pkg_contents" | |
firmware_file=$(find "$pkg_contents" -type f -regex ".*\.scap") | |
fi | |
if [ "$firmware_file" ]; then | |
echo "-> Firmware file found ($firmware_file)" | |
else | |
echo "!!! Error: Failed to find firmware file in package" | |
exit 2 | |
fi | |
fi | |
unpack_dir="$TEMP_DIR/unpack" | |
mkdir "$unpack_dir" | |
echo "-> Extracting firmware..." | |
$uefi_extract_path "$firmware_file" dump | |
mv "$firmware_file.dump" "$unpack_dir" | |
last_path=$(realpath) | |
cd "$unpack_dir" | |
echo -n "-> Appending all parts to single binary..." | |
find . -type f -exec sh -c 'dd if="$1" status=none >> data.bin; printf "."' sh {} . \; | |
echo | |
echo "-> Extracting images..." | |
binwalk --dd="png image:png:" data.bin | |
cd "$last_path" | |
echo "--> Moving images to output directory..." | |
find "$unpack_dir" -type f -regex ".*\.png" -exec sh -c 'mv "$1" "$2/$RANDOM$RANDOM.png"' sh {} "$output_dir" \; | |
if [ -z "$(ls -A $output_dir)" ]; then | |
echo "!!! Extract finished but this firmware probably have no PNG images inside (maybe update?)" | |
exit 4 | |
fi | |
echo "-> Deleting temp directory" | |
rm -rf "$TEMP_DIR" |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment