mirror of https://github.com/wolfSSL/wolfBoot.git
Add support for wolfHSM cert chain verification on TC3xx
parent
23cf367c38
commit
d689656a71
|
@ -10,6 +10,7 @@ This example demonstrates using wolfBoot on the Infineon AURIX TC3xx family of m
|
|||
- [Flash Partitioning](#flash-partitioning)
|
||||
- [Standard wolfBoot images](#standard-wolfboot-images)
|
||||
- [ELF files](#elf-files)
|
||||
- [Cert Chain Verification](#cert-chain-verification)
|
||||
- [Configuration and the wolfBoot AURIX tool (wbaurixtool.sh)](#configuration-and-the-wolfboot-aurix-tool-wbaurixtoolsh)
|
||||
- [Building and running the wolfBoot demo](#building-and-running-the-wolfboot-demo)
|
||||
- [Prerequisites](#prerequisites)
|
||||
|
@ -23,6 +24,9 @@ This example demonstrates using wolfBoot on the Infineon AURIX TC3xx family of m
|
|||
- [Load and run the wolfBoot demo in TRACE32](#load-and-run-the-wolfboot-demo-in-trace32)
|
||||
- [wolfHSM Compatibility](#wolfhsm-compatibility)
|
||||
- [Building wolfBoot with wolfHSM](#building-wolfboot-with-wolfhsm)
|
||||
- [Building wolfBoot with wolfHSM and cert chain verification](#building-wolfboot-with-wolfhsm-and-cert-chain-verification)
|
||||
- [Custom Certificate Chain](#custom-certificate-chain)
|
||||
- [Dummy Certificate Chain](#dummy-certificate-chain)
|
||||
- [Building: Command Sequence](#building-command-sequence)
|
||||
- [Troubleshooting](#troubleshooting)
|
||||
- [WSL "bad interpreter" error](#wsl-bad-interpreter-error)
|
||||
|
@ -95,6 +99,10 @@ Different linker script templates are used to configure the memory layout via `w
|
|||
- [test-app (standard wolfBoot images)](test-app/Lcf_Gnu_Tricore_Tc.lsl.in)
|
||||
- [test-app (ELF files)](test-app/Lcf_Gnu_Tricore_elf.lsl.in)
|
||||
|
||||
### Cert Chain Verification
|
||||
|
||||
wolfBoot on AURIX supports verifying firmware images using certificate chains. For more information on how this wolfBoot feature works, refer to [Signing.md](../../docs/Signing.md), [firmware_update.md](../docs/firmware_update.md), and [wolfBoot-wolfHSM](../../IDE/AURIX/wolfBoot-wolfHSM). Currently this feature can only be used in conjunction with wolfHSM. Instructions for using this feature are detailed below in the [Building wolfBoot with wolfHSM](#building-wolfboot-with-wolfhsm) section.
|
||||
|
||||
## Configuration and the wolfBoot AURIX tool (wbaurixtool.sh)
|
||||
|
||||
wolfBoot relies extensively on its build system in order to properly set configuration macros, linker addresses, and other target-specific items. Because wolfBoot on AURIX uses the AURIX studio IDE to build, changing things like the signature algorithm would require manually editing IDE settings, linker scripts, etc. which is error prone and tedious. The `wbaurixtool.sh` script provides a single tool that automates the generation of all configurable items required for building wolfBoot and the test application on AURIX given the chosen signature and hashing algorithms, including managing all configuration macros, linker scripts, as well as handling the actual key generation and image signing process. `wbaurixtool.sh` can also generate wolfHSM NVM images containing the generated image signing key when used in conjunction with wolfHSM.
|
||||
|
@ -320,6 +328,27 @@ IDE/AURIX/wolfHSM-infineon-tc3xx/
|
|||
3. Provide the `--hsm` global option to the `wbaurixtool.sh` script when invoking it so that the wolfHSM projects are used instead of the standard wolfBoot projects
|
||||
4. If using the default build options in [wolfBoot-tc3xx-wolfHSM](./wolfBoot-tc3xx-wolfHSM/), wolfBoot will expect the public key for image verification to be stored at a specific keyId for the wolfBoot client ID. You can use [whnvmtool](https://github.com/wolfSSL/wolfHSM/tree/main/tools/whnvmtool) to generate a loadable NVM image that contains the required keys automatically via `wbaurixtool.sh` through the `nvm` subcommand. This generates an NVM image containing the generated image signing key based on the [wolfBoot-wolfHSM-keys.nvminit](../../tools/scripts/tc3xx/wolfBoot-wolfHSM-keys.nvminit) configuration file, which can then be loaded to the device via a flash programming tool. Before using the `nvm` subcommand of `wbaurixtool.sh`, first compile `whnvmtool` by running `make` in the `lib/wolfHSM/tools/whnvmtool` directory. See the `whnvmtool` documentation and the documentation included in your wolfHSM AURIX release for more details. Note: if you want to use the standard wolfBoot keystore functionality in conjunction with wolfHSM for testing purposes (doesn't require pre-loading keys on the HSM) you can configure wolfBoot to send the keys to the HSM on-the-fly as ephemeral keys. To do this, ensure `WOLFBOOT_USE_WOLFHSM_PUBKEY_ID` is **NOT** defined, and add the `--localkeys` argument to then `./wbaurixtool.sh keygen` command, which invokes the `keygen` tool without the default `--nolocalkeys` option.
|
||||
|
||||
### Building wolfBoot with wolfHSM and cert chain verification
|
||||
|
||||
wolfBoot with wolfHSM supports certificate chain verification for firmware images. This feature allows wolfBoot to verify that firmware images are signed with certificates that can be traced back to a trusted root certificate authority through a certificate chain.
|
||||
|
||||
The `wbaurixtool.sh` script provides two options for applicable commands that enable automation of configuring the build for certificate chain verification:
|
||||
|
||||
- `--certchain <file>`: Use a user-provided certificate chain file
|
||||
- `--dummy-certchain`: Use a "dummy" certificate chain that is created from the key pair generated by the wolfBoot keytools for development/testing purposes.
|
||||
|
||||
Both options require the `--hsm` global option and can be used with the `keygen`, `sign`, `macros`, `lcf`, and `nvm` subcommands.
|
||||
|
||||
### Custom Certificate Chain
|
||||
|
||||
If you want to use a custom certificate chain for verification, you can provide the `--certchain <certchain file>` option to the `macros`, `lcf`, and `sign` subcommands. This ensures that your certificate chain will be included in the generated firmware image and that wolfBoot will verify the chain on boot, then verify the signature of the firmware image using the public key corresponding to the leaf certificate in the chain. Note that the user is responsible for properly constructing the certificate chain and ensuring that the leaf certificate is bound to the firmware signing key pair, as well as properly provisioning the HSM with the root CA certificate at the expected NVM object ID specified by the HAL.
|
||||
|
||||
### Dummy Certificate Chain
|
||||
|
||||
If you just want to test out the certificate verifcation functionality, `wbaurixtool.sh` can generate and use a dummy certificate chain by providing the `--dummy-certchain` option to the `keygen`, `sign`, `macros`, `lcf`, and `nvm` subcommands. This will cause the keygen step to generate a dummy root CA at `test-dummy-ca/root-ca.der`, well as a dummy certificate chain at `test-dummy-ca/raw-chain.der` using the specified algorithm. The generated chain consists of a single intermediate as well as a leaf (signing) certificate whose identity is bound to the generated firmware signing key pair. The subsequent commands will then ensure this generated chain is used by wolfBoot. Additionally, the `nvm` subcommand will create an NVM image containing the generated root CA that can be loaded into HSM NVM.
|
||||
|
||||
**Note: The `--dummy-certchain` option is intended for development and testing. For production use, generate and use your own certificate chain.**
|
||||
|
||||
## Building: Command Sequence
|
||||
|
||||
The following pseudo command sequence shows a brief overview of the commands needed to build wolfBoot on AURIX (optionally with wolfHSM). The signature and hashing algorithms used in the example are ECC 256 and SHA 256 and specified explicitly for clarity. Note that these algorithms are the default, so do not need to be explicitly specified. Optional arguments are shown in square brackets (e.g. if targeting wolfHSM, the `--hsm` option must be provided as a global option to `wbaurixtool.sh`).
|
||||
|
|
File diff suppressed because one or more lines are too long
|
@ -8,3 +8,4 @@
|
|||
@ML_DSA_IMAGE_SIGNATURE_SIZE@
|
||||
@WOLFBOOT_ELF@
|
||||
@WOLFBOOT_ELF_FLASH_SCATTER@
|
||||
@WOLFBOOT_CERT_CHAIN_VERIFY@
|
|
@ -26,5 +26,6 @@
|
|||
#define WOLFHSM_CFG_H_
|
||||
|
||||
#define WOLFHSM_CFG_DMA
|
||||
#define WOLFHSM_CFG_CERTIFICATE_MANAGER
|
||||
|
||||
#endif /* WOLFHSM_CFG_H_ */
|
||||
|
|
File diff suppressed because one or more lines are too long
|
@ -665,6 +665,9 @@ const int hsmClientKeyIdPubKey = 0xFF;
|
|||
const int hsmClientDevIdCrypt = WH_DEV_ID;
|
||||
const int hsmClientKeyIdCrypt = 0xFF;
|
||||
#endif
|
||||
#ifdef WOLFBOOT_CERT_CHAIN_VERIFY
|
||||
const whNvmId hsmClientNvmIdCertRootCA = 1;
|
||||
#endif
|
||||
|
||||
|
||||
static int _cancelCb(uint16_t cancelSeq)
|
||||
|
|
|
@ -928,7 +928,7 @@ ifneq ($(CERT_CHAIN_VERIFY),)
|
|||
KEYGEN_OPTIONS += --der
|
||||
ifneq ($(CERT_CHAIN_GEN),)
|
||||
# Use dummy cert chain file if not provided (needs to be generated when keys are generated)
|
||||
CERT_CHAIN_FILE = test-dummy-ca/raw_chain.der
|
||||
CERT_CHAIN_FILE = test-dummy-ca/raw-chain.der
|
||||
|
||||
# Set appropriate cert gen options based on sigalg
|
||||
ifeq ($(SIGN),ECC256)
|
||||
|
|
12
src/image.c
12
src/image.c
|
@ -2038,10 +2038,20 @@ int wolfBoot_verify_authenticity(struct wolfBoot_image *img)
|
|||
wolfBoot_printf("Found certificate chain (%d bytes)\n",
|
||||
cert_chain_size);
|
||||
|
||||
/* Verify certificate chain using wolfHSM's verification API */
|
||||
/* Verify certificate chain using wolfHSM's verification API. Use DMA if
|
||||
* available in the wolfHSM configuration */
|
||||
#if defined(WOLFHSM_CFG_DMA)
|
||||
wolfBoot_printf(
|
||||
"verifying cert chain and caching leaf pubkey (using DMA)\n");
|
||||
hsm_ret = wh_Client_CertVerifyDmaAndCacheLeafPubKey(
|
||||
&hsmClientCtx, cert_chain, cert_chain_size,
|
||||
hsmClientNvmIdCertRootCA, &g_certLeafKeyId, &cert_verify_result);
|
||||
#else
|
||||
wolfBoot_printf("verifying cert chain and caching leaf pubkey\n");
|
||||
hsm_ret = wh_Client_CertVerifyAndCacheLeafPubKey(
|
||||
&hsmClientCtx, cert_chain, cert_chain_size,
|
||||
hsmClientNvmIdCertRootCA, &g_certLeafKeyId, &cert_verify_result);
|
||||
#endif
|
||||
|
||||
/* Error or verification failure results in standard auth check failure
|
||||
* path */
|
||||
|
|
|
@ -176,7 +176,7 @@ echo "Extracting public key from leaf certificate..."
|
|||
extract_public_key "${OUTPUT_DIR}/temp/leaf.crt.pem" "${OUTPUT_DIR}/temp/leaf_pubkey.pem" "${OUTPUT_DIR}/leaf-pubkey.der"
|
||||
|
||||
# Create raw DER format certificate chain
|
||||
cat ${OUTPUT_DIR}/intermediate-cert.der ${OUTPUT_DIR}/leaf-cert.der > ${OUTPUT_DIR}/raw_chain.der
|
||||
cat ${OUTPUT_DIR}/intermediate-cert.der ${OUTPUT_DIR}/leaf-cert.der > ${OUTPUT_DIR}/raw-chain.der
|
||||
|
||||
##################################
|
||||
# GENERATE C ARRAYS FOR EMBEDDING
|
||||
|
@ -223,7 +223,7 @@ echo "/* Certificates */" >> "${HEADER_FILE}"
|
|||
append_cert_array "${OUTPUT_DIR}/root-cert.der" "ROOT_CERT" "Root CA Certificate (DER format)"
|
||||
append_cert_array "${OUTPUT_DIR}/intermediate-cert.der" "INTERMEDIATE_CERT" "Intermediate CA Certificate (DER format)"
|
||||
append_cert_array "${OUTPUT_DIR}/leaf-cert.der" "LEAF_CERT" "Leaf/Server Certificate (DER format)"
|
||||
append_cert_array "${OUTPUT_DIR}/raw_chain.der" "RAW_CERT_CHAIN" "Raw Certificate Chain (Intermediate+Leaf) (DER format)"
|
||||
append_cert_array "${OUTPUT_DIR}/raw-chain.der" "RAW_CERT_CHAIN" "Raw Certificate Chain (Intermediate+Leaf) (DER format)"
|
||||
# Add leaf certificate public key
|
||||
append_cert_array "${OUTPUT_DIR}/leaf-pubkey.der" "LEAF_PUBKEY" "Leaf Certificate Public Key (DER format)"
|
||||
|
||||
|
@ -257,7 +257,7 @@ echo " Intermediate certificate: ${OUTPUT_DIR}/intermediate-cert.der"
|
|||
echo " Intermediate key: ${OUTPUT_DIR}/intermediate-prvkey.der"
|
||||
echo " Leaf certificate: ${OUTPUT_DIR}/leaf-cert.der"
|
||||
echo " Leaf key: ${OUTPUT_DIR}/leaf-prvkey.der"
|
||||
echo " Raw chain: ${OUTPUT_DIR}/raw_chain.der"
|
||||
echo " Raw chain: ${OUTPUT_DIR}/raw-chain.der"
|
||||
echo " Leaf public key: ${OUTPUT_DIR}/leaf-pubkey.der"
|
||||
echo ""
|
||||
echo "C Header file:"
|
||||
|
|
|
@ -27,8 +27,10 @@ PRVKEY_DER="$WOLFBOOT_DIR/priv.der"
|
|||
PUBKEY_DER="$WOLFBOOT_DIR/priv_pub.der"
|
||||
TARGET_H="$WOLFBOOT_DIR/include/target.h"
|
||||
NVM_CONFIG="$WOLFBOOT_DIR/tools/scripts/tc3xx/wolfBoot-wolfHSM-keys.nvminit"
|
||||
NVM_CONFIG_DUMMY_CERTCHAIN="$WOLFBOOT_DIR/tools/scripts/tc3xx/wolfBoot-wolfHSM-dummy-certchain.nvminit"
|
||||
NVM_BIN="whNvmImage.bin"
|
||||
NVM_HEX="whNvmImage.hex"
|
||||
DUMMY_CERT_CHAIN="$WOLFBOOT_DIR/test-dummy-ca/raw-chain.der"
|
||||
|
||||
# Tool paths (relative to project root)
|
||||
SQUASHELF="$WOLFBOOT_DIR/tools/squashelf/squashelf"
|
||||
|
@ -93,30 +95,11 @@ declare -A ML_DSA_HEADER_SIZES=(
|
|||
[5]=12288
|
||||
)
|
||||
|
||||
# Get the header size based on the selected public key algorithm
|
||||
get_header_size() {
|
||||
local algo="$1"
|
||||
local pq_params="$2"
|
||||
|
||||
case "$algo" in
|
||||
"ml_dsa")
|
||||
# Default to level 2 for ML-DSA if no params specified
|
||||
echo "${ML_DSA_HEADER_SIZES[${pq_params:-2}]}"
|
||||
;;
|
||||
"ecc256") echo "256" ;;
|
||||
"ecc384"|"ecc521"|"rsa2048"|"rsa3072") echo "512" ;;
|
||||
"rsa4096") echo "1024" ;;
|
||||
"ed25519") echo "256" ;;
|
||||
"ed448") echo "512" ;;
|
||||
"lms"|"xmss") echo "0" ;; # currently not supported
|
||||
"none") echo "256" ;;
|
||||
*) echo "256" ;; # Default
|
||||
esac
|
||||
}
|
||||
|
||||
# Add to command options structure
|
||||
declare -A COMMON_OPTS=(
|
||||
[sign_pq_params]=""
|
||||
[certchain_file]=""
|
||||
[dummy_certchain]=""
|
||||
)
|
||||
|
||||
# Add LCF_OPTS to command options structure
|
||||
|
@ -130,6 +113,80 @@ declare -A TARGET_OPTS=(
|
|||
[use_elf_format]=""
|
||||
)
|
||||
|
||||
# Add NVM_OPTS to command options structure
|
||||
declare -A NVM_OPTS=(
|
||||
[dummy_certchain]=""
|
||||
)
|
||||
|
||||
# Get the effective certificate chain file path
|
||||
get_effective_certchain_file() {
|
||||
if [[ -n "${COMMON_OPTS[dummy_certchain]}" ]]; then
|
||||
echo "$DUMMY_CERT_CHAIN"
|
||||
elif [[ -n "${COMMON_OPTS[certchain_file]}" ]]; then
|
||||
echo "${COMMON_OPTS[certchain_file]}"
|
||||
else
|
||||
echo ""
|
||||
fi
|
||||
}
|
||||
|
||||
# Get the header size based on the selected public key algorithm
|
||||
get_header_size() {
|
||||
local algo="$1"
|
||||
local pq_params="$2"
|
||||
local certchain_file="$3"
|
||||
|
||||
# Get base header size for the algorithm
|
||||
local base_size
|
||||
case "$algo" in
|
||||
"ml_dsa")
|
||||
# Default to level 2 for ML-DSA if no params specified
|
||||
base_size="${ML_DSA_HEADER_SIZES[${pq_params:-2}]}"
|
||||
;;
|
||||
"ecc256") base_size="256" ;;
|
||||
"ecc384"|"ecc521"|"rsa2048"|"rsa3072") base_size="512" ;;
|
||||
"rsa4096") base_size="1024" ;;
|
||||
"ed25519") base_size="256" ;;
|
||||
"ed448") base_size="512" ;;
|
||||
"lms"|"xmss") base_size="0" ;; # currently not supported
|
||||
"none") base_size="256" ;;
|
||||
*) base_size="256" ;; # Default
|
||||
esac
|
||||
|
||||
# If no certificate chain, return base size
|
||||
if [[ -z "$certchain_file" ]]; then
|
||||
echo "$base_size"
|
||||
return
|
||||
fi
|
||||
|
||||
# Check if certificate chain file exists and get its size
|
||||
if [[ ! -f "$certchain_file" ]]; then
|
||||
echo "Error: Certificate chain file not found: $certchain_file" >&2
|
||||
echo "$base_size"
|
||||
return
|
||||
fi
|
||||
|
||||
local cert_size
|
||||
cert_size=$(stat -c%s "$certchain_file" 2>/dev/null || stat -f%z "$certchain_file" 2>/dev/null)
|
||||
if [[ $? -ne 0 ]]; then
|
||||
echo "Error: Cannot get certificate chain file size: $certchain_file" >&2
|
||||
echo "$base_size"
|
||||
return
|
||||
fi
|
||||
|
||||
# Calculate total required space
|
||||
# cert_size + 4 bytes (TLV header) + 8 bytes (max alignment padding)
|
||||
local cert_overhead=$((cert_size + 12))
|
||||
local total_required=$((base_size + cert_overhead))
|
||||
|
||||
# Round up to next power of 2 (matching C code behavior)
|
||||
local final_size=$base_size
|
||||
while [[ $final_size -lt $total_required ]]; do
|
||||
final_size=$((final_size * 2))
|
||||
done
|
||||
|
||||
echo "$final_size"
|
||||
}
|
||||
|
||||
# Helper function to display usage
|
||||
usage() {
|
||||
echo "Usage: $0 [global-options] COMMAND [command-options] [COMMAND [command-options]]"
|
||||
|
@ -142,11 +199,14 @@ usage() {
|
|||
echo " keygen"
|
||||
echo " --sign-algo ALGO Signing algorithm (default: ecc256)"
|
||||
echo " --localkeys Use local keys (only valid with --hsm)"
|
||||
echo " --dummy-certchain Generate dummy certificate chain after key generation"
|
||||
echo ""
|
||||
echo " sign"
|
||||
echo " --sign-algo ALGO Signing algorithm (inherits from keygen if not specified)"
|
||||
echo " --hash-algo ALGO Hash algorithm (default: sha256)"
|
||||
echo " --debug Use debug build (default: release)"
|
||||
echo " --certchain FILE Certificate chain file to include in header"
|
||||
echo " --dummy-certchain Use dummy certificate chain in header"
|
||||
echo ""
|
||||
echo " target"
|
||||
echo " No additional options"
|
||||
|
@ -157,12 +217,16 @@ usage() {
|
|||
echo " macros"
|
||||
echo " --sign-algo ALGO Signing algorithm (inherits from keygen/sign if not specified)"
|
||||
echo " --hash-algo ALGO Hash algorithm (inherits from sign if not specified)"
|
||||
echo " --certchain FILE Certificate chain file to include in header"
|
||||
echo " --dummy-certchain Use dummy certificate chain in header"
|
||||
echo ""
|
||||
echo " nvm"
|
||||
echo " No additional options"
|
||||
echo " --dummy-certchain Use dummy certificate chain configuration"
|
||||
echo ""
|
||||
echo " lcf"
|
||||
echo " --sign-algo ALGO Signing algorithm (inherits from keygen/sign if not specified)"
|
||||
echo " --certchain FILE Certificate chain file to include in header"
|
||||
echo " --dummy-certchain Use dummy certificate chain in header"
|
||||
echo ""
|
||||
echo "Examples:"
|
||||
echo " $0 keygen --sign-algo ecc256"
|
||||
|
@ -174,28 +238,29 @@ usage() {
|
|||
echo " $0 macros"
|
||||
echo " $0 nvm"
|
||||
echo " $0 lcf"
|
||||
echo " $0 sign --certchain /path/to/cert_chain.pem"
|
||||
echo " $0 macros --certchain /path/to/cert_chain.pem lcf --certchain /path/to/cert_chain.pem"
|
||||
echo " $0 keygen --sign-algo ecc256 --dummy-certchain"
|
||||
echo " $0 sign --dummy-certchain"
|
||||
echo " $0 keygen --sign-algo ecc256 --dummy-certchain sign --dummy-certchain"
|
||||
echo " $0 nvm --dummy-certchain"
|
||||
exit 1
|
||||
}
|
||||
|
||||
# Function to generate keys
|
||||
do_keygen() {
|
||||
local sign_algo="${KEYGEN_OPTS[sign_algo]:-$DEFAULT_SIGN_ALGO}"
|
||||
local pq_params="${COMMON_OPTS[sign_pq_params]}"
|
||||
local header_size
|
||||
|
||||
# Get header size for current algorithm
|
||||
header_size=$(get_header_size "$sign_algo" "$pq_params")
|
||||
|
||||
echo "Generating keys with algorithm: $sign_algo"
|
||||
|
||||
# Set environment variables for keygen tool
|
||||
export IMAGE_HEADER_SIZE="$header_size"
|
||||
if [ "$sign_algo" = "ml_dsa" ]; then
|
||||
export ML_DSA_LEVEL="${pq_params:-2}" # Default to level 2 if not specified
|
||||
fi
|
||||
|
||||
(cd $WOLFBOOT_DIR && tools/keytools/keygen --"$sign_algo" -g $(basename $PRVKEY_DER) --exportpubkey \
|
||||
${KEYGEN_OPTS[nolocalkeys]:+--nolocalkeys} --der)
|
||||
|
||||
# Generate dummy certificate chain if requested
|
||||
if [[ -n "${COMMON_OPTS[dummy_certchain]}" ]]; then
|
||||
echo "Generating dummy certificate chain with algorithm: $sign_algo"
|
||||
(cd $WOLFBOOT_DIR && tools/scripts/sim-gen-dummy-chain.sh --algo "$sign_algo" --leaf priv.der)
|
||||
fi
|
||||
}
|
||||
|
||||
# Function to sign binaries
|
||||
|
@ -218,7 +283,7 @@ do_sign() {
|
|||
fi
|
||||
|
||||
# Get header size for current algorithm
|
||||
header_size=$(get_header_size "$sign_algo" "$pq_params")
|
||||
header_size=$(get_header_size "$sign_algo" "$pq_params" "$(get_effective_certchain_file)")
|
||||
|
||||
# Set IMAGE_HEADER_SIZE environment variable for sign tool
|
||||
export IMAGE_HEADER_SIZE="$header_size"
|
||||
|
@ -226,9 +291,17 @@ do_sign() {
|
|||
echo "Signing binaries with $sign_algo and ${SIGN_OPTS[hash_algo]}"
|
||||
echo "Using header size: $header_size"
|
||||
|
||||
# Build cert-chain argument if specified
|
||||
local cert_chain_arg=""
|
||||
if [[ -n "${COMMON_OPTS[certchain_file]}" ]]; then
|
||||
cert_chain_arg="--cert-chain ${COMMON_OPTS[certchain_file]}"
|
||||
elif [[ -n "${COMMON_OPTS[dummy_certchain]}" ]]; then
|
||||
cert_chain_arg="--cert-chain $DUMMY_CERT_CHAIN"
|
||||
fi
|
||||
|
||||
# Sign for both partition 1 and 2
|
||||
../../keytools/sign --"$sign_algo" --"${SIGN_OPTS[hash_algo]}" "$bin_path" "$PRVKEY_DER" 1
|
||||
../../keytools/sign --"$sign_algo" --"${SIGN_OPTS[hash_algo]}" "$bin_path" "$PRVKEY_DER" 2
|
||||
../../keytools/sign --"$sign_algo" --"${SIGN_OPTS[hash_algo]}" $cert_chain_arg "$bin_path" "$PRVKEY_DER" 1
|
||||
../../keytools/sign --"$sign_algo" --"${SIGN_OPTS[hash_algo]}" $cert_chain_arg "$bin_path" "$PRVKEY_DER" 2
|
||||
}
|
||||
|
||||
# Function to generate target header
|
||||
|
@ -303,7 +376,8 @@ do_gen_macros() {
|
|||
local pq_params="${COMMON_OPTS[sign_pq_params]}"
|
||||
|
||||
# Get header size using the new function
|
||||
local image_header_size=$(get_header_size "$sign_algo" "$pq_params")
|
||||
local image_header_size=$(get_header_size "$sign_algo" "$pq_params" "$(get_effective_certchain_file)")
|
||||
echo "generating macros with header size = $image_header_size"
|
||||
|
||||
local use_huge_stack=""
|
||||
local use_wolfhsm_pubkey_id=""
|
||||
|
@ -312,6 +386,7 @@ do_gen_macros() {
|
|||
local ml_dsa_level=""
|
||||
local use_wolfboot_elf=""
|
||||
local use_wolfboot_elf_flash_scattered=""
|
||||
local use_wolfboot_cert_chain_verify=""
|
||||
|
||||
# Map algorithms to their macro names
|
||||
local sign_macro="${SIGN_ALGO_MAP[${sign_algo,,}]:-}"
|
||||
|
@ -326,6 +401,13 @@ do_gen_macros() {
|
|||
exit 1
|
||||
fi
|
||||
|
||||
# Validate certificate chain usage
|
||||
if [[ -n "${COMMON_OPTS[certchain_file]}" ]]; then
|
||||
use_wolfboot_cert_chain_verify="-DWOLFBOOT_CERT_CHAIN_VERIFY"
|
||||
elif [[ -n "${COMMON_OPTS[dummy_certchain]}" ]]; then
|
||||
use_wolfboot_cert_chain_verify="-DWOLFBOOT_CERT_CHAIN_VERIFY"
|
||||
fi
|
||||
|
||||
# Set huge stack for RSA4096
|
||||
if [[ "${sign_algo,,}" == "rsa4096" ]]; then
|
||||
use_huge_stack="-DWOLFBOOT_HUGE_STACK"
|
||||
|
@ -373,6 +455,7 @@ do_gen_macros() {
|
|||
-e "s/@WOLFBOOT_USE_WOLFHSM_PUBKEY_ID@/$use_wolfhsm_pubkey_id/g" \
|
||||
-e "s/@WOLFBOOT_ELF@/$use_wolfboot_elf/g" \
|
||||
-e "s/@WOLFBOOT_ELF_FLASH_SCATTER@/$use_wolfboot_elf_flash_scattered/g" \
|
||||
-e "s/@WOLFBOOT_CERT_CHAIN_VERIFY@/$use_wolfboot_cert_chain_verify/g" \
|
||||
"$macros_in" > "$macros_out"
|
||||
|
||||
# Remove empty lines from the output file, as they cause compiler errors
|
||||
|
@ -381,9 +464,16 @@ do_gen_macros() {
|
|||
|
||||
# Function to generate a wolfHSM NVM image
|
||||
do_gen_nvm() {
|
||||
local nvm_config_file="$NVM_CONFIG"
|
||||
|
||||
# Use dummy cert chain config if specified
|
||||
if [[ -n "${COMMON_OPTS[dummy_certchain]}" ]]; then
|
||||
nvm_config_file="$NVM_CONFIG_DUMMY_CERTCHAIN"
|
||||
fi
|
||||
|
||||
echo "Generating HSM NVM image"
|
||||
echo "Running: $WHNVMTOOL --image=$NVM_BIN --size=0x10000 --invert-erased-byte $NVM_CONFIG"
|
||||
"$WHNVMTOOL" --image="$NVM_BIN" --size=0x10000 --invert-erased-byte "$NVM_CONFIG"
|
||||
echo "Running: $WHNVMTOOL --image=$NVM_BIN --size=0x10000 --invert-erased-byte $nvm_config_file"
|
||||
"$WHNVMTOOL" --image="$NVM_BIN" --size=0x10000 --invert-erased-byte "$nvm_config_file"
|
||||
|
||||
echo "Converting to Intel HEX format"
|
||||
echo "Running: objcopy -I binary -O ihex --change-address 0xAFC00000 $NVM_BIN $NVM_HEX"
|
||||
|
@ -412,7 +502,7 @@ do_gen_lcf() {
|
|||
local lcf_template="$base_dir/$app_dir/$template_name"
|
||||
local lcf_output="$base_dir/$app_dir/Lcf_Gnuc_Tricore_Tc.lsl"
|
||||
|
||||
header_size=$(get_header_size "$sign_algo" "$pq_params")
|
||||
header_size=$(get_header_size "$sign_algo" "$pq_params" "$(get_effective_certchain_file)")
|
||||
|
||||
echo "Generating LCF file with header_size=$header_size"
|
||||
sed -e "s/@LCF_WOLFBOOT_HEADER_OFFSET@/$header_size/g" \
|
||||
|
@ -479,7 +569,7 @@ while [[ $# -gt 0 ]]; do
|
|||
;;
|
||||
nvm)
|
||||
OPERATIONS+=("nvm")
|
||||
CURRENT_OPTS=""
|
||||
CURRENT_OPTS="NVM_OPTS"
|
||||
shift
|
||||
;;
|
||||
lcf)
|
||||
|
@ -546,6 +636,26 @@ while [[ $# -gt 0 ]]; do
|
|||
COMMON_OPTS[sign_pq_params]="$2"
|
||||
shift 2
|
||||
;;
|
||||
--certchain)
|
||||
if [[ -z "$CURRENT_OPTS" ]]; then
|
||||
echo "Error: --certchain must follow a command"
|
||||
exit 1
|
||||
fi
|
||||
if [[ -z "$HSM" ]]; then
|
||||
echo "Error: --certchain can only be used with --hsm global option"
|
||||
exit 1
|
||||
fi
|
||||
COMMON_OPTS[certchain_file]="$2"
|
||||
shift 2
|
||||
;;
|
||||
--dummy-certchain)
|
||||
if [[ -z "$CURRENT_OPTS" ]]; then
|
||||
echo "Error: --dummy-certchain must follow a command"
|
||||
exit 1
|
||||
fi
|
||||
COMMON_OPTS[dummy_certchain]="1"
|
||||
shift
|
||||
;;
|
||||
*)
|
||||
echo "Unknown option for ${CURRENT_OPTS:-global options}: $1"
|
||||
usage
|
||||
|
@ -559,6 +669,12 @@ if [ ${#OPERATIONS[@]} -eq 0 ]; then
|
|||
usage
|
||||
fi
|
||||
|
||||
# Validate that --certchain and --dummy-certchain are not both specified
|
||||
if [[ -n "${COMMON_OPTS[certchain_file]}" && -n "${COMMON_OPTS[dummy_certchain]}" ]]; then
|
||||
echo "Error: Cannot specify both --certchain and --dummy-certchain"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
# Execute requested operations in order
|
||||
for op in "${OPERATIONS[@]}"; do
|
||||
case $op in
|
||||
|
|
|
@ -0,0 +1,2 @@
|
|||
# NVM config file for wolfHSM whnvmtool to create NVM image based on generated keys
|
||||
obj 1 0xFFFF 0x0000 "cert CA" ../../../test-dummy-ca/root-cert.der
|
Loading…
Reference in New Issue