Skip to content

Instantly share code, notes, and snippets.

@T4cC0re
Created September 29, 2016 05:06
Show Gist options
  • Save T4cC0re/5724cb6d6f47be912571bcf53e5b2580 to your computer and use it in GitHub Desktop.
Save T4cC0re/5724cb6d6f47be912571bcf53e5b2580 to your computer and use it in GitHub Desktop.
SSH pi-flashrom v0.1 by T4cC0re - Flash images remotely via SSH/SCP
#!/usr/bin/env bash
# region SETTINGS
SPEED=3800; # safe speed for rPi. (<80sec for read, verify and download of 8MiB rom)
#SPEED=16000; # freaking fast! Should work on most rPis. (<30sec for read, verify and download of 8MiB rom)
#SPEED=32000; # insanely fast! Not guaranteed to work at all, but works for me. (~20sec for read, verify and download of 8MiB rom)
ASK=1; # Ask to flash before actually doing it
#ASK=0; # Don't ask.
# endregion
echo -e "SSH pi-flashrom v0.1 by T4cC0re\n";
COMMAND="$1";
HOST="$2";
FILE="$3";
shift 3;
ADDITIONAL_FLAGS="$@";
function confirm () {
if [ 1 -eq ${ASK} ]; then
read -r -p "$1 " response
case $response in
[yY][eE][sS]|[yY])
true
;;
*)
false
;;
esac
else
true
fi
}
function doCheck () {
ssh "${HOST}" "flashrom -p linux_spi:dev=/dev/spidev0.0,spispeed=${SPEED} ${ADDITIONAL_FLAGS}";
}
function doVerify () {
if [ ! -f "${FILE}" ]; then
echo "-> ERROR: NO FILE PRESENT!";
cleanup 1;
fi
TMP="$(ssh "${HOST}" "mktemp -d")";
echo "-> Created temporary folder '${TMP}'";
echo "-> Uploading ROM...";
scp "${FILE}" "${HOST}:${TMP}/verify.rom";
localVsRemoteMatch 'verify.rom';
echo "-> Verifying ROM (1/1)...";
flashrom_verify 'verify.rom';
cleanup 0;
}
function doFlash () {
confirm "-> Flash via host ${HOST}, using flags '${ADDITIONAL_FLAGS}'. [y/N]?" || exit 0;
if [ ! -f "${FILE}" ]; then
echo "-> ERROR: NO FILE PRESENT!";
cleanup 1;
fi
TMP="$(ssh "${HOST}" "mktemp -d")";
echo "-> Created temporary folder '${TMP}'";
echo "-> Uploading ROM...";
scp "${FILE}" "${HOST}:${TMP}/flash.rom";
localVsRemoteMatch 'flash.rom';
echo "-> Flashing ROM (1/2)...";
flashrom_flash 'flash.rom';
echo "-> Verifying ROM (2/2)...";
flashrom_verify 'flash.rom';
cleanup 0;
}
function doRead () {
TMP="$(ssh "${HOST}" "mktemp -d")";
echo "-> Created temporary folder '${TMP}'";
echo "-> Reading ROM (1/2)...";
flashrom_read 'read.rom';
echo "-> Verifying read ROM (2/2)...";
flashrom_verify 'read.rom';
echo "-> Downloading ROM...";
scp "${HOST}:${TMP}/read.rom" "${FILE}";
if [ -f "${FILE}" ]; then
localVsRemoteMatch 'read.rom';
else
echo "-> ERROR: NO FILE PRESENT!";
cleanup 1;
fi
cleanup 0;
}
# parameter 1: remote filename
function localVsRemoteMatch () {
REMOTE_HASH="$(ssh ${HOST} sha512sum "${TMP}/$1" | awk '{print $1}')";
HASH="$(sha512sum "${FILE}" | awk '{print $1}')";
if [ "${REMOTE_HASH}" = "${HASH}" ]; then
echo "-> Local hash matches remote hash!";
else
echo "-> ERROR: HASHES MISMATCH! Aborting!...";
cleanup 1;
fi
}
# parameter 1: exit-code
function cleanup () {
echo "-> Cleaning folder '${TMP}' from '${HOST}'...";
ssh "${HOST}" rm -rf "${TMP}";
exit $1;
}
# parameter 1: filename to flash
function flashrom_flash () {
flashrom_do w "$1";
}
# parameter 1: filename to verify
function flashrom_verify () {
flashrom_do v "$1";
}
# parameter 1: filename to read to
function flashrom_read () {
flashrom_do r "$1";
}
# parameter 1: operation (v,r,w)
# parameter 2: file
function flashrom_do () {
echo;
ssh "${HOST}" "flashrom -p linux_spi:dev=/dev/spidev0.0,spispeed=${SPEED} -$1 '${TMP}/$2' ${ADDITIONAL_FLAGS}";
FLASHROM_EXIT=$?;
echo;
if [ ${FLASHROM_EXIT} -ne 0 ]; then
echo "-> ERROR: FLASHROM ENCOUNTERED AN ERROR! ...";
cleanup 1;
fi
}
function usage () {
echo -e "usage:\n\
\t$0 [COMMAND] [HOST] [FILE] '[...FLASHROM FLAGS (OPT)]'\n\
e.g:\t$0 flash pi@10.10.10.10 my.rom '-c \"MX25L6406E/MX25L6408E\"'\n\
\n\
\tCommands:\n\
\t\t'read'\t\t- read rom to file\n\
\t\t'flash'\t\t- flash from file and verify\n\
\t\t'verify'\t- verify flash against file\n\
\t\t'check'\t\t- use to detect the flash chip\n";
}
case "${COMMAND}" in
"flash")
doFlash $@;
;;
"read")
doRead $@;
;;
"check")
doCheck $@;
;;
"verify")
doVerify $@;
;;
*)
echo "unknown command '${COMMAND}'";
usage;
;;
esac
@T4cC0re
Copy link
Author

T4cC0re commented Sep 29, 2016

Examples:
Read original bootrom:

[root@somepony coreboot]# pi-flashrom read pi@10.10.10.128 t420.rom '-c "MX25L6406E/MX25L6408E"'
SSH pi-flashrom v0.1 by T4cC0re

-> Created temporary folder '/tmp/tmp.nbAFoqr2K2'
-> Reading ROM (1/2)...

flashrom v0.9.9-r1954 on Linux 4.4.13-v7+ (armv7l)
flashrom is free software, get the source code at https://flashrom.org

Calibrating delay loop... OK.
Found Macronix flash chip "MX25L6406E/MX25L6408E" (8192 kB, SPI) on linux_spi.
Reading flash... done.

-> Verifying read ROM (2/2)...

flashrom v0.9.9-r1954 on Linux 4.4.13-v7+ (armv7l)
flashrom is free software, get the source code at https://flashrom.org

Calibrating delay loop... OK.
Found Macronix flash chip "MX25L6406E/MX25L6408E" (8192 kB, SPI) on linux_spi.
Reading old flash chip contents... done.
Verifying flash... VERIFIED.

-> Downloading ROM...
read.rom                                                                                                                                                                          100% 8192KB   2.4MB/s   00:03    
-> Local hash matches remote hash!
-> Cleaning folder '/tmp/tmp.nbAFoqr2K2' from 'pi@10.10.10.128'...

Flash coreboot:

[root@somepony coreboot]# pi-flashrom flash pi@10.10.10.128 build/coreboot.rom '-c "MX25L6406E/MX25L6408E"'
SSH pi-flashrom v0.1 by T4cC0re

-> Flash via host pi@10.10.10.128, using flags '-c "MX25L6406E/MX25L6408E"'. [y/N]? y
-> Created temporary folder '/tmp/tmp.o0LSDavx2n'
-> Uploading ROM...
coreboot.rom                                                        100% 8192KB   2.7MB/s   00:03    
-> Local hash matches remote hash!
-> Flashing ROM (1/2)...

flashrom v0.9.9-r1954 on Linux 4.4.13-v7+ (armv7l)
flashrom is free software, get the source code at https://flashrom.org

Calibrating delay loop... OK.
Found Macronix flash chip "MX25L6406E/MX25L6408E" (8192 kB, SPI) on linux_spi.
Reading old flash chip contents... done.
Erasing and writing flash chip... Erase/write done.
Verifying flash... VERIFIED.

-> Verifying ROM (2/2)...

flashrom v0.9.9-r1954 on Linux 4.4.13-v7+ (armv7l)
flashrom is free software, get the source code at https://flashrom.org

Calibrating delay loop... OK.
Found Macronix flash chip "MX25L6406E/MX25L6408E" (8192 kB, SPI) on linux_spi.
Reading old flash chip contents... done.
Verifying flash... VERIFIED.

-> Cleaning folder '/tmp/tmp.o0LSDavx2n' from 'pi@10.10.10.128'...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment