build: standardize v2 scripts to use HWDIRS as per v1
What changed, and why it matters
This commit is a build-script cleanup for Blockstream Jade firmware release tooling. It rewrites three shell scripts so they loop over a list of hardware directories (currently just 'jade2.0') instead of hard-coding that path, and adds 'set -e' to one script so it exits immediately on any error. The commit message explicitly says 'No functional changes.' There is no change to firmware code, cryptography, device behavior, or user-facing functionality, and no security issue is evident.
No security action required. Treat as normal build/maintenance refactoring. If desired, review the scripts for release-process correctness, but the diff itself introduces no vulnerability.
Security signals we found
No changes to cryptographic operations, key material, or signature verification logic
No changes to firmware source or binary behavior
No changes to network, USB, or Bluetooth attack surface
Commit message states 'No functional changes'
Adds 'set -e' in v2jadesign.sh, which is a defensive scripting improvement
Evidence from the diff
The diff modifies release/scripts/v2applysigs.sh, release/scripts/v2jadesign.sh, and release/scripts/v2sign.sh. In each script the hard-coded WORKING_DIR=’staging/${VER_DIR}/jade2.0’ is replaced by WORKING_DIR_PREFIX=’staging/${VER_DIR}’ plus an HWDIRS=’jade2.0’ list, and the existing signing/verification logic is wrapped in a ‘for hwdir in ${HWDIRS}’ loop. v2jadesign.sh also gains ‘set -e’. The commands executed, file paths used, key handling, signature verification, and digest comparisons remain identical for the single currently-supported hardware directory. This is a structural standardization with the v1 scripts and does not alter security properties.
Changed components
release/scripts/v2applysigs.shrelease/scripts/v2jadesign.shrelease/scripts/v2sign.shInspect captured patch +157 / −137
diff --git a/release/scripts/v2applysigs.sh b/release/scripts/v2applysigs.sh
index eb66a7b..5f0fba9 100755
--- a/release/scripts/v2applysigs.sh
+++ b/release/scripts/v2applysigs.sh
@@ -10,7 +10,8 @@ VER_DIR="${1}"
shift
SIGNER_KEY_LABELS="$@"
-WORKING_DIR="staging/${VER_DIR}/jade2.0"
+WORKING_DIR_PREFIX="staging/${VER_DIR}"
+HWDIRS="jade2.0"
BLEDIR="build_v2_prod"
NORADIODIR="build_v2_noradio_prod"
@@ -29,53 +30,58 @@ do
PUBKEYS="${PUBKEYS} ../../../scripts/${key_label}.pub"
done
-pushd "${WORKING_DIR}"
+for hwdir in ${HWDIRS}; do
+ WORKING_DIR="${WORKING_DIR_PREFIX}/${hwdir}"
-for build in ${BUILDS}
-do
- for binary in ${BINARIES}
+ pushd "${WORKING_DIR}"
+
+ for build in ${BUILDS}
do
- sig_files=""
- for key_label in ${SIGNER_KEY_LABELS}
+ for binary in ${BINARIES}
do
- sig_file="${FILE_PREFIX}_${build}_${binary}.${key_label}.sig"
- sig_files="${sig_files} ${sig_file}"
- done
+ sig_files=""
+ for key_label in ${SIGNER_KEY_LABELS}
+ do
+ sig_file="${FILE_PREFIX}_${build}_${binary}.${key_label}.sig"
+ sig_files="${sig_files} ${sig_file}"
+ done
- file_prefix="${FILE_PREFIX}_${build}_${binary}"
- infile="${file_prefix}.${FW_SUFFIX}"
- outfile="${file_prefix}_${SIGNED_SUFFIX}"
+ file_prefix="${FILE_PREFIX}_${build}_${binary}"
+ infile="${file_prefix}.${FW_SUFFIX}"
+ outfile="${file_prefix}_${SIGNED_SUFFIX}"
+
+ espsecure.py sign_data --version 2 --pub-key ${PUBKEYS} --signature ${sig_files} --output "${outfile}" "${infile}"
+ digests=""
+ for pubkey in ${PUBKEYS}
+ do
+ # Verify the signature
+ espsecure.py verify_signature --version 2 --keyfile "${pubkey}" "${outfile}"
+ # Capture the signature digest
+ digest=$(espsecure.py digest_sbv2_public_key --keyfile "${pubkey}" -o digest.bin >/dev/null && cat digest.bin | od -A n -t x1 | tr -d ' \n' && rm -f digest.bin)
+ digests="$digests $digest"
+ done
+ # Make sure the signature digests match
+ digests=$(echo ${digests} | tr ' ' '\n' | sort)
+ file_digests=$(espsecure.py signature_info_v2 "${outfile}" | grep "Public key digest for block " | cut -d\: -f2 | sed "s/ //g" | sort)
+ if [ "${digests}" != "${file_digests}" ]; then
+ echo "mismatched digests:"
+ echo "digests:"
+ echo ${digests}
+ echo "expected:"
+ echo ${file_digests}
+ exit 2
+ fi
+ done
- espsecure.py sign_data --version 2 --pub-key ${PUBKEYS} --signature ${sig_files} --output "${outfile}" "${infile}"
- digests=""
- for pubkey in ${PUBKEYS}
- do
- # Verify the signature
- espsecure.py verify_signature --version 2 --keyfile "${pubkey}" "${outfile}"
- # Capture the signature digest
- digest=$(espsecure.py digest_sbv2_public_key --keyfile "${pubkey}" -o digest.bin >/dev/null && cat digest.bin | od -A n -t x1 | tr -d ' \n' && rm -f digest.bin)
- digests="$digests $digest"
- done
- # Make sure the signature digests match
- digests=$(echo ${digests} | tr ' ' '\n' | sort)
- file_digests=$(espsecure.py signature_info_v2 "${outfile}" | grep "Public key digest for block " | cut -d\: -f2 | sed "s/ //g" | sort)
- if [ "${digests}" != "${file_digests}" ]; then
- echo "mismatched digests:"
- echo "digests:"
- echo ${digests}
- echo "expected:"
- echo ${file_digests}
- exit 2
- fi
done
+ sha256sum "${FILE_PREFIX}"_*_"${SIGNED_SUFFIX}"
-done
-sha256sum "${FILE_PREFIX}"_*_"${SIGNED_SUFFIX}"
+ # Copy main fw binaries that have been signed, consistent with v1
+ cp "${FILE_PREFIX}_ble_jade_${SIGNED_SUFFIX}" "${BLEDIR}/jade_${SIGNED_SUFFIX}"
+ cp "${FILE_PREFIX}_noradio_jade_${SIGNED_SUFFIX}" "${NORADIODIR}/jade_${SIGNED_SUFFIX}"
+ cp "${FILE_PREFIX}_ble_bootloader_${SIGNED_SUFFIX}" "${BLEDIR}/bootloader/bootloader_${SIGNED_SUFFIX}"
+ cp "${FILE_PREFIX}_noradio_bootloader_${SIGNED_SUFFIX}" "${NORADIODIR}/bootloader/bootloader_${SIGNED_SUFFIX}"
-# Copy main fw binaries that have been signed, consistent with v1
-cp "${FILE_PREFIX}_ble_jade_${SIGNED_SUFFIX}" "${BLEDIR}/jade_${SIGNED_SUFFIX}"
-cp "${FILE_PREFIX}_noradio_jade_${SIGNED_SUFFIX}" "${NORADIODIR}/jade_${SIGNED_SUFFIX}"
-cp "${FILE_PREFIX}_ble_bootloader_${SIGNED_SUFFIX}" "${BLEDIR}/bootloader/bootloader_${SIGNED_SUFFIX}"
-cp "${FILE_PREFIX}_noradio_bootloader_${SIGNED_SUFFIX}" "${NORADIODIR}/bootloader/bootloader_${SIGNED_SUFFIX}"
+ popd
-popd
+done
diff --git a/release/scripts/v2jadesign.sh b/release/scripts/v2jadesign.sh
index 13e5bab..e4e270f 100755
--- a/release/scripts/v2jadesign.sh
+++ b/release/scripts/v2jadesign.sh
@@ -1,5 +1,7 @@
#!/bin/bash
+set -e
+
function usage {
echo "Usage: ${0} <version/dir> <key_label> [--serialport PORT]"
}
@@ -32,7 +34,8 @@ if [ -z "${VER_DIR}" -o -z "${KEY_LABEL}" ]; then
exit 1
fi
-WORKING_DIR="staging/${VER_DIR}/jade2.0"
+WORKING_DIR_PREFIX="staging/${VER_DIR}"
+HWDIRS="jade2.0"
# Can log if required
LOGGING=""
@@ -61,71 +64,76 @@ HASH_OPTS="-sha256 -binary"
VERIFY_OPTS="-pubin -inkey ${PUBKEY} -pkeyopt digest:sha256 -pkeyopt rsa_padding_mode:pss"
JADE_SIGN_CMD="python ../../../../jade_bip85_rsa_sign.py ${JADE_SERIAL_ARG} ${LOGGING} ${CHECK_JADE_PUBKEY} --keylen ${KEYLEN} --index ${INDEX} --digest-files"
-pushd "${WORKING_DIR}"
+for hwdir in ${HWDIRS}; do
+ WORKING_DIR="${WORKING_DIR_PREFIX}/${hwdir}"
-# Verify bootloaders are same
-sha1=$(sha256sum "${BLEDIR}/bootloader/bootloader.bin" | cut -d\ -f1)
-sha2=$(sha256sum "${NORADIODIR}/bootloader/bootloader.bin" | cut -d\ -f1)
-if [ -z "${sha1}" -o -z "${sha2}" -o "${sha1}" != "${sha2}" ]
-then
- echo "Bootloaders missing or differ!"
- popd
- exit 2
-fi
+ pushd "${WORKING_DIR}"
-# Copy binaries that need signing
-cp "${BLEDIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_ble_bootloader.bin"
-cp "${BLEDIR}/jade.bin" "${FILE_PREFIX}_ble_jade.bin"
-cp "${NORADIODIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_noradio_bootloader.bin"
-cp "${NORADIODIR}/jade.bin" "${FILE_PREFIX}_noradio_jade.bin"
-
-# Hash the bootloaders and fws locally
-HASH_FILES=""
-for build in "ble" "noradio"
-do
- for program in "bootloader" "jade"
- do
- binary="${FILE_PREFIX}_${build}_${program}.bin"
- hash_file="${FILE_PREFIX}_${build}_${program}.hash"
- HASH_FILES="${HASH_FILES} ${hash_file}"
+ # Verify bootloaders are same
+ sha1=$(sha256sum "${BLEDIR}/bootloader/bootloader.bin" | cut -d\ -f1)
+ sha2=$(sha256sum "${NORADIODIR}/bootloader/bootloader.bin" | cut -d\ -f1)
+ if [ -z "${sha1}" -o -z "${sha2}" -o "${sha1}" != "${sha2}" ]
+ then
+ echo "Bootloaders missing or differ!"
+ popd
+ exit 2
+ fi
+
+ # Copy binaries that need signing
+ cp "${BLEDIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_ble_bootloader.bin"
+ cp "${BLEDIR}/jade.bin" "${FILE_PREFIX}_ble_jade.bin"
+ cp "${NORADIODIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_noradio_bootloader.bin"
+ cp "${NORADIODIR}/jade.bin" "${FILE_PREFIX}_noradio_jade.bin"
- openssl dgst ${HASH_OPTS} -out "${hash_file}" "${binary}"
+ # Hash the bootloaders and fws locally
+ HASH_FILES=""
+ for build in "ble" "noradio"
+ do
+ for program in "bootloader" "jade"
+ do
+ binary="${FILE_PREFIX}_${build}_${program}.bin"
+ hash_file="${FILE_PREFIX}_${build}_${program}.hash"
+ HASH_FILES="${HASH_FILES} ${hash_file}"
+
+ openssl dgst ${HASH_OPTS} -out "${hash_file}" "${binary}"
+ done
done
-done
-# Sign the hashes with jade
-echo "Please approve signing on your Jade device"
-${JADE_SIGN_CMD} ${HASH_FILES}
+ # Sign the hashes with jade
+ echo "Please approve signing on your Jade device"
+ ${JADE_SIGN_CMD} ${HASH_FILES}
-# Check signatures with labeled pubkey, and rename if good
-for build in "ble" "noradio"
-do
- for program in "bootloader" "jade"
+ # Check signatures with labeled pubkey, and rename if good
+ for build in "ble" "noradio"
do
- hash_file="${FILE_PREFIX}_${build}_${program}.hash"
- sig_file="${hash_file}.sig"
- openssl pkeyutl -verify ${VERIFY_OPTS} -sigfile "${sig_file}" -in "${hash_file}"
- if [ "${?}" -eq 0 ]
- then
- mv ${sig_file} "${FILE_PREFIX}_${build}_${program}.${SIG_SUFFIX}"
- rm "${hash_file}"
- else
- echo "Signature verification of ${sig_file} over ${hash_file} with ${PUBKEY} failed"
- fi
+ for program in "bootloader" "jade"
+ do
+ hash_file="${FILE_PREFIX}_${build}_${program}.hash"
+ sig_file="${hash_file}.sig"
+ openssl pkeyutl -verify ${VERIFY_OPTS} -sigfile "${sig_file}" -in "${hash_file}"
+ if [ "${?}" -eq 0 ]
+ then
+ mv ${sig_file} "${FILE_PREFIX}_${build}_${program}.${SIG_SUFFIX}"
+ rm "${hash_file}"
+ else
+ echo "Signature verification of ${sig_file} over ${hash_file} with ${PUBKEY} failed"
+ fi
+ done
done
-done
-sha256sum *."${SIG_SUFFIX}"
+ sha256sum *."${SIG_SUFFIX}"
-# Verify jade pubkey matches expected (if feched)
-if [ -n "${CHECK_JADE_PUBKEY}" ]
-then
- sha1=$(sha256sum "${PUBKEY}" | cut -d\ -f1)
- sha2=$(sha256sum "${JADE_PUBKEY_FILE}" | cut -d\ -f1)
- if [ -z "${sha1}" -o -z "${sha2}" -o "${sha1}" != "${sha2}" ]
+ # Verify jade pubkey matches expected (if feched)
+ if [ -n "${CHECK_JADE_PUBKEY}" ]
then
- echo "Error: Pubkey pem mismatch!"
+ sha1=$(sha256sum "${PUBKEY}" | cut -d\ -f1)
+ sha2=$(sha256sum "${JADE_PUBKEY_FILE}" | cut -d\ -f1)
+ if [ -z "${sha1}" -o -z "${sha2}" -o "${sha1}" != "${sha2}" ]
+ then
+ echo "Error: Pubkey pem mismatch!"
+ fi
fi
-fi
-popd
+ popd
+
+done
diff --git a/release/scripts/v2sign.sh b/release/scripts/v2sign.sh
index 44b9f3f..a1bceba 100755
--- a/release/scripts/v2sign.sh
+++ b/release/scripts/v2sign.sh
@@ -10,7 +10,8 @@ fi
VER_DIR="${1}"
KEY_LABEL="${2}"
-WORKING_DIR="staging/${VER_DIR}/jade2.0"
+WORKING_DIR_PREFIX="staging/${VER_DIR}"
+HWDIRS="jade2.0"
# Relative paths from where it will be referenced in fw dir
KEY="../../../scripts/${KEY_LABEL}.pem"
@@ -26,49 +27,54 @@ HASH_OPTS="-sha256 -binary"
SIGN_OPTS="-inkey ${KEY} -pkeyopt digest:sha256 -pkeyopt rsa_padding_mode:pss -pkeyopt rsa_pss_saltlen:32 -pkeyopt rsa_mgf1_md:sha256"
VERIFY_OPTS="-pubin -inkey ${PUBKEY} -pkeyopt digest:sha256 -pkeyopt rsa_padding_mode:pss"
-pushd "${WORKING_DIR}"
+for hwdir in ${HWDIRS}; do
+ WORKING_DIR="${WORKING_DIR_PREFIX}/${hwdir}"
-[ -f ${PUBKEY} ] || (echo "Public key file ${PUBKEY} not found" && exit 2)
-[ -f ${KEY} ] || (echo "Private key file ${KEY} not found" && exit 2)
+ pushd "${WORKING_DIR}"
-# Verify bootloaders are same
-sha1=$(sha256sum "${BLEDIR}/bootloader/bootloader.bin" | cut -d\ -f1)
-sha2=$(sha256sum "${NORADIODIR}/bootloader/bootloader.bin" | cut -d\ -f1)
-if [ -z "${sha1}" -o -z "${sha2}" -o "${sha1}" != "${sha2}" ]
-then
- echo "Bootloaders missing or differ!"
- popd
- exit 2
-fi
+ [ -f ${PUBKEY} ] || (echo "Public key file ${PUBKEY} not found" && exit 2)
+ [ -f ${KEY} ] || (echo "Private key file ${KEY} not found" && exit 2)
-# Copy binaries that need signing
-cp "${BLEDIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_ble_bootloader.bin"
-cp "${BLEDIR}/jade.bin" "${FILE_PREFIX}_ble_jade.bin"
-cp "${NORADIODIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_noradio_bootloader.bin"
-cp "${NORADIODIR}/jade.bin" "${FILE_PREFIX}_noradio_jade.bin"
+ # Verify bootloaders are same
+ sha1=$(sha256sum "${BLEDIR}/bootloader/bootloader.bin" | cut -d\ -f1)
+ sha2=$(sha256sum "${NORADIODIR}/bootloader/bootloader.bin" | cut -d\ -f1)
+ if [ -z "${sha1}" -o -z "${sha2}" -o "${sha1}" != "${sha2}" ]
+ then
+ echo "Bootloaders missing or differ!"
+ popd
+ exit 2
+ fi
-# Hash the bootloaders and fws locally
-for build in "ble" "noradio"
-do
- for program in "bootloader" "jade"
+ # Copy binaries that need signing
+ cp "${BLEDIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_ble_bootloader.bin"
+ cp "${BLEDIR}/jade.bin" "${FILE_PREFIX}_ble_jade.bin"
+ cp "${NORADIODIR}/bootloader/bootloader.bin" "${FILE_PREFIX}_noradio_bootloader.bin"
+ cp "${NORADIODIR}/jade.bin" "${FILE_PREFIX}_noradio_jade.bin"
+
+ # Hash the bootloaders and fws locally
+ for build in "ble" "noradio"
do
- filename_root="${FILE_PREFIX}_${build}_${program}"
- binary="${filename_root}.bin"
- hash_file="${filename_root}.hash"
- sig_file="${filename_root}.${SIG_SUFFIX}"
-
- openssl dgst ${HASH_OPTS} -out "${hash_file}" "${binary}"
- openssl pkeyutl -sign ${SIGN_OPTS} -in "${hash_file}" -out "${sig_file}"
- openssl pkeyutl -verify ${VERIFY_OPTS} -sigfile "${sig_file}" -in "${hash_file}"
- if [ "${?}" -eq 0 ]
- then
- rm "${hash_file}"
- else
- echo "Signature verification of ${sig_file} over ${hash_file} with ${PUBKEY} failed"
- fi
+ for program in "bootloader" "jade"
+ do
+ filename_root="${FILE_PREFIX}_${build}_${program}"
+ binary="${filename_root}.bin"
+ hash_file="${filename_root}.hash"
+ sig_file="${filename_root}.${SIG_SUFFIX}"
+
+ openssl dgst ${HASH_OPTS} -out "${hash_file}" "${binary}"
+ openssl pkeyutl -sign ${SIGN_OPTS} -in "${hash_file}" -out "${sig_file}"
+ openssl pkeyutl -verify ${VERIFY_OPTS} -sigfile "${sig_file}" -in "${hash_file}"
+ if [ "${?}" -eq 0 ]
+ then
+ rm "${hash_file}"
+ else
+ echo "Signature verification of ${sig_file} over ${hash_file} with ${PUBKEY} failed"
+ fi
+ done
done
-done
-sha256sum *."${SIG_SUFFIX}"
+ sha256sum *."${SIG_SUFFIX}"
+
+ popd
-popd
+done
Why this scored 15/100
Community notes
Notes can correct, qualify, or add evidence to the AI analysis. Every note shown here has been validated by a human moderator.
The AI analysis stands alone for now. Submit a note if you can add evidence or important context.