This document describes how wolfBoot configures wolfCrypt: the layout of
include/user_settings.h and include/user_settings/, the
WOLFBOOT_NEEDS_* marker convention, the contract between the build
system (options.mk) and these headers, and how to read, modify, or
extend the configuration when adding a new feature.
Audience. Developers adding or modifying wolfBoot features that touch wolfCrypt. If you only consume wolfBoot via a
.configfile or an IDE project, you do not need to read this document — the high-levelWOLFBOOT_*flags work the same way they always have.
- Overview & Goals
- Architecture
- The NEEDS_* Marker Convention
- Marker Reference
- Fragment Reference
cascade.hDetailfinalize.hDetail- Adding a New Feature
- Reading an Existing Configuration
- Relationship to options.mk
- Alternative Build Paths (CMake, IDE, Zephyr)
- Compatibility Notes
wolfBoot pulls in wolfCrypt as a submodule and configures it via
-DWOLFSSL_USER_SETTINGS, which directs wolfSSL to load
include/user_settings.h. Historically that file was a single 781-line
header that mixed system defines, every SIGN family's curve/size config,
every wolfBoot feature's wolfCrypt requirements, and a long block of
"strip the rest" disables — all interconnected by deeply nested negated
#ifdef chains. Adding a new feature meant editing every chain that
needed to opt out of a default disable.
The current scheme replaces that with a shim + fragments + one reconciliation header layout where:
include/user_settings.his a 73-line shim that does nothing but#includefragment headers in a fixed order.- Each high-level wolfBoot feature owns a fragment header that declares
only its own wolfCrypt configuration. Fragments compose by
#define-only contributions; they never#undefand never test each other's internal state. WOLFBOOT_NEEDS_*markers are the single contract between fragments and the final reconciliation. Each marker is a positive intent ("this build needs RNG") andfinalize.htranslates the absence of a marker into the corresponding wolfCrypt negative flag (WC_NO_RNG).
The benefits, listed concretely:
- An IDE or CMake user can build wolfBoot by setting only the
high-level
WOLFBOOT_*flags. The cascade and reconciliation that used to live inoptions.mknow lives incascade.hand runs from the preprocessor. - Adding a feature no longer requires editing the disable sites in
finalize.h. The new fragment declares its needs once, and every affected disable picks up the change automatically. - The full set of "what does this configuration disable?" is one grep
away (
grep WOLFBOOT_NEEDS_ include/user_settings/finalize.h); the full set of "what does my feature need?" is one fragment file away.
include/user_settings.h is the canonical entry point that wolfSSL
loads when -DWOLFSSL_USER_SETTINGS is set. It contains no wolfCrypt
configuration of its own, just an ordered series of #includes.
/* include/user_settings.h (excerpt) */
#ifdef WOLFBOOT_PKCS11_APP
# include "test-app/wcs/user_settings.h"
#else
#include <target.h>
#include "user_settings/cascade.h"
#include "user_settings/base.h"
#include "user_settings/sign_dispatch.h"
#include "user_settings/hash_dispatch.h"
#include "user_settings/encrypt.h"
#include "user_settings/trustzone.h"
#include "user_settings/tpm.h"
#include "user_settings/wolfhsm.h"
#include "user_settings/cert_chain.h"
#include "user_settings/renesas.h"
#include "user_settings/platform.h"
#include "user_settings/test_bench.h"
#include "user_settings/finalize.h"
#endifThe WOLFBOOT_PKCS11_APP branch is a pre-existing redirect for the
PKCS#11 test app, which has its own user_settings.h shipped alongside
its build harness; it is not part of the production wolfBoot path.
Fragment headers live in include/user_settings/. Each is a small,
self-contained .h file that contributes wolfCrypt configuration when
its activation flag (a WOLFBOOT_* or wolfCrypt-side flag) is set, and
expands to nothing otherwise. The 22 fragments are grouped by concern:
| Group | Files |
|---|---|
| Foundation | cascade.h, base.h, finalize.h |
| SIGN dispatch + families | sign_dispatch.h, sign_ecc.h, sign_rsa.h, sign_ed25519.h, sign_ed448.h, sign_ml_dsa.h, sign_lms.h, sign_xmss.h |
| HASH dispatch + families | hash_dispatch.h, hash_sha384.h, hash_sha3.h |
| Feature blocks | encrypt.h, trustzone.h, tpm.h, wolfhsm.h, cert_chain.h |
| Platform / hardware | renesas.h, platform.h |
| Test/Bench | test_bench.h |
Each fragment is described in detail in Section 5.
The order in user_settings.h is not arbitrary. It is the contract
that lets fragments stay decoupled. The phases:
-
cascade.hruns first. It derives implied flags (WOLFBOOT_TPMfromWOLFBOOT_TPM_VERIFY/MEASURED_BOOT/etc.,WOLFBOOT_TPM_PARMENCfromTPM_KEYSTORE/TPM_SEAL,WOLFBOOT_NEEDS_RSAfrom any RSA SIGN flag) and declares all theWOLFBOOT_NEEDS_*markers that come purely from feature-flag testing. Every fragment downstream sees the derived flags as if they were emitted byoptions.mk. -
base.hsets the always-on foundation: alignment, threading, stdlib types,WC_NO_HARDEN(wolfBoot does verify-only public crypto). It also definesWOLFCRYPT_ONLY(skipped only when wolfHSM server + cert-chain verify needs the SSL layer). -
sign_dispatch.hconditionally includes the appropriatesign_*.hfragment(s) based onWOLFBOOT_SIGN_*andWOLFBOOT_SIGN_SECONDARY_*. Hybrid signatures (primary + secondary) include two SIGN fragments.sign_rsa.his included unconditionally; its#elsebranch definesNO_RSAwhen no RSA flag is set. -
hash_dispatch.hconditionally includes the appropriatehash_*.hfragment based onWOLFBOOT_HASH_*. SHA-256 is the foundation default and has no fragment. -
Feature fragments (
encrypt.h,trustzone.h,tpm.h,wolfhsm.h,cert_chain.h,renesas.h,platform.h,test_bench.h) each contribute their own positive defines and declare additionalWOLFBOOT_NEEDS_*markers when needed. Order among these is currently insensitive — fragments don't read each other's contributions — but the established order is preserved for readability. -
finalize.hruns last. It tests everyWOLFBOOT_NEEDS_*marker and applies the corresponding wolfCrypt negative flag (NO_*,WC_NO_*) when the marker is absent. It then defines the always-on global "off" block and the memory model.
Two rules for fragment authors:
- Fragments only
#define, never#undef. All the negative-flag decisions belong tofinalize.h. - Fragments declare
WOLFBOOT_NEEDS_*markers; they don't test for the absence of features. If your fragment needs to know whether another feature is present, that's a sign the cascade header should derive a marker that both fragments can read.
wolfCrypt has two flavors of feature flags:
| Flavor | Examples | Default |
|---|---|---|
| Positive (opt-in) | HAVE_ECC, WOLFSSL_AES_CFB, HAVE_HASHDRBG, WOLFSSL_SHA384 |
off; you set them when you want the capability |
| Negative (opt-out) | NO_AES, NO_HMAC, WC_NO_RNG, NO_ASN, NO_KDF, NO_CMAC, NO_PWDBASED |
on; you set them to strip a capability for code-size |
Positive flags compose trivially. If tpm.h says #define WOLFSSL_AES_CFB and trustzone.h also says #define WOLFSSL_AES_CFB,
the second is harmless under an #ifndef guard. Multiple fragments can
each declare the same positive flag with no coordination.
Negative flags don't compose. If base.h defines NO_AES and a
later fragment needs AES, the fragment has to either #undef NO_AES
(scattering AES-truth across N fragments and requiring strict include
ordering) or the NO_AES definition itself has to be conditional on
every feature that needs AES — exactly the negated-AND chain pattern
that the old user_settings.h was riddled with.
WOLFBOOT_NEEDS_* markers thread the needle: fragments stay purely
additive (each declares positive intent), and finalize.h is the
single place that translates positive intent into negative flags.
A fragment declares its needs:
/* include/user_settings/tpm.h */
#if defined(WOLFBOOT_TPM) && !defined(WOLFBOOT_TZ_FWTPM)
# ifdef WOLFBOOT_TPM_PARMENC
# define WOLFSSL_AES_CFB /* positive flag, set directly */
# define WOLFSSL_PUBLIC_MP /* positive flag, set directly */
/* RNG and HASHDRBG are needed too, but those translate to
* negatives in finalize.h, so we declare markers: */
# endif
#endif
/* (NEEDS_RNG and NEEDS_HASHDRBG for PARMENC are declared in
* cascade.h — see Section 6.) */In practice most WOLFBOOT_NEEDS_* markers are declared in
cascade.h, because the conditions that imply them are pure tests of
high-level feature flags. Fragments may also declare additional
markers when they have an internal sub-condition (the prime example is
test_bench.h declaring WOLFBOOT_NEEDS_HASHDRBG only on the
LPC55S69 sub-path).
finalize.h reconciles:
/* include/user_settings/finalize.h */
#ifndef WOLFBOOT_NEEDS_RNG
# define WC_NO_RNG
#endif
#ifndef WOLFBOOT_NEEDS_AES
# define NO_AES
#endif
/* ... etc ... */- Idempotent. Every marker
#defineis#ifndef-guarded, so multiple fragments declaring the same marker is safe. - Order-independent among feature fragments. A fragment that
declares
WOLFBOOT_NEEDS_RNGdoes not care which other fragments declare it too.finalize.honly checks "was the marker defined by anyone?". - Cheap. Pure preprocessor; no runtime or code-size cost.
- Searchable. Every disable in
finalize.his a#ifndef WOLFBOOT_NEEDS_*block. Every opt-in is a#define WOLFBOOT_NEEDS_*line. Both are greppable.
Markers are declared by cascade.h (and a few by individual fragments)
and tested by finalize.h. The table below is the canonical
vocabulary; every marker is pure preprocessor and has no runtime cost.
| Marker | Without it, finalize.h sets | Declared when | Where declared |
|---|---|---|---|
WOLFBOOT_NEEDS_RSA |
NO_RSA |
Any WOLFBOOT_SIGN_RSA* / RSAPSS* / SECONDARY_RSA* flag, or WOLFCRYPT_SECURE_MODE && !PKCS11_SMALL |
cascade.h |
WOLFBOOT_NEEDS_RNG |
WC_NO_RNG |
WOLFBOOT_TPM_PARMENC, WOLFCRYPT_SECURE_MODE, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK, WOLFBOOT_ENABLE_WOLFHSM_SERVER, WOLFBOOT_ENABLE_WOLFHSM_CLIENT && WOLFBOOT_SIGN_ML_DSA |
cascade.h |
WOLFBOOT_NEEDS_HASHDRBG |
WC_NO_HASHDRBG (else: defines HAVE_HASHDRBG) |
WOLFBOOT_TPM_PARMENC, WOLFCRYPT_SECURE_MODE, (WOLFCRYPT_TEST‖WOLFCRYPT_BENCHMARK) && (LPC55S69_*HWACCEL) |
cascade.h |
WOLFBOOT_NEEDS_AES |
NO_AES |
ENCRYPT_WITH_AES128, ENCRYPT_WITH_AES256, WOLFBOOT_TPM_PARMENC, WOLFCRYPT_SECURE_MODE, SECURE_PKCS11, WOLFCRYPT_TZ_PSA, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK |
cascade.h |
WOLFBOOT_NEEDS_AES_CBC |
NO_AES_CBC |
WOLFBOOT_TPM_PARMENC, WOLFCRYPT_SECURE_MODE, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK |
cascade.h |
WOLFBOOT_NEEDS_HMAC |
NO_HMAC |
WOLFBOOT_TPM, WOLFCRYPT_SECURE_MODE, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK |
cascade.h |
WOLFBOOT_NEEDS_DEV_RANDOM |
NO_DEV_RANDOM |
WOLFBOOT_TPM, WOLFCRYPT_SECURE_MODE, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK |
cascade.h |
WOLFBOOT_NEEDS_ECC_KEY_EXPORT |
NO_ECC_KEY_EXPORT |
WOLFBOOT_TPM, WOLFCRYPT_SECURE_MODE, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK, WOLFBOOT_ENABLE_WOLFHSM_CLIENT, WOLFBOOT_ENABLE_WOLFHSM_SERVER |
cascade.h |
WOLFBOOT_NEEDS_ASN |
NO_ASN |
WOLFBOOT_NEEDS_RSA, WOLFBOOT_TPM, WOLFCRYPT_SECURE_MODE, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK, WOLFBOOT_ENABLE_WOLFHSM_CLIENT, WOLFBOOT_ENABLE_WOLFHSM_SERVER |
cascade.h |
WOLFBOOT_NEEDS_BASE64 |
NO_CODING (else: defines WOLFSSL_BASE64_ENCODE) |
WOLFBOOT_TPM_SEAL && WOLFBOOT_ATA_DISK_LOCK, WOLFBOOT_ENABLE_WOLFHSM_CLIENT, WOLFBOOT_ENABLE_WOLFHSM_SERVER |
cascade.h |
WOLFBOOT_NEEDS_CMAC |
NO_CMAC |
WOLFCRYPT_TZ_PSA, WOLFBOOT_TZ_FWTPM |
cascade.h |
WOLFBOOT_NEEDS_KDF |
NO_KDF |
WOLFCRYPT_TZ_PSA, WOLFBOOT_TZ_FWTPM |
cascade.h |
WOLFBOOT_NEEDS_MALLOC |
NO_WOLFSSL_MEMORY, WOLFSSL_NO_MALLOC (in the !SMALL_STACK branch of memory model) |
SECURE_PKCS11, WOLFCRYPT_TZ_PSA, WOLFBOOT_ENABLE_WOLFHSM_SERVER, WOLFCRYPT_TEST, WOLFCRYPT_BENCHMARK |
cascade.h |
Two markers have a bipolar reconciliation: NEEDS_HASHDRBG and
NEEDS_BASE64 switch between the positive flag (HAVE_HASHDRBG /
WOLFSSL_BASE64_ENCODE) when present and the negative flag
(WC_NO_HASHDRBG / NO_CODING) when absent. The rest are unipolar:
absent ⇒ define the negative flag, present ⇒ skip the negative flag
(the positive flag is set elsewhere by the relevant fragment).
Each fragment is documented with: purpose, activation gate, markers it declares, positive defines it sets, and any notes.
Purpose. Foundation defines that every wolfBoot build needs regardless of features.
Activation. Always (unconditional).
Sets:
WOLFSSL_GENERAL_ALIGNMENT 4,SINGLE_THREADED,WOLFSSL_USER_MUTEXWOLFCRYPT_ONLY(only when not(WOLFHSM_SERVER && CERT_CHAIN_VERIFY))SIZEOF_LONG_LONG 8,HAVE_EMPTY_AGGREGATES 0,HAVE_ANONYMOUS_INLINE_AGGREGATES 0CTYPE_USER,XTOUPPER/XTOLOWER(unlessWOLFSSL_ARMASM)WC_NO_HARDENifUSE_FAST_MATH(verify-only crypto needs no timing-resistance hardening)
Notes. The WOLFCRYPT_ONLY carve-out for the wolfHSM-server
cert-chain mode lives here for now. A future cleanup could move that to
cert_chain.h via a WOLFBOOT_NEEDS_TLS_LAYER marker.
Purpose. Single source of truth for feature-flag → derived-flag
cascades and for WOLFBOOT_NEEDS_* markers that come purely from
feature-flag tests.
See Section 6 for full content.
Purpose. Conditionally include the right sign_*.h fragment(s).
Each branch tests the SIGN family activation flags and pulls in the
matching fragment. sign_rsa.h is included unconditionally because
its #else branch defines NO_RSA when no RSA flag is set; that
fallback must run regardless of the active SIGN.
Activation. WOLFBOOT_SIGN_ED25519 || WOLFBOOT_SIGN_SECONDARY_ED25519.
Sets:
HAVE_ED25519,ED25519_SMALL,USE_SLOW_SHA512,WOLFSSL_SHA512NO_ED25519_SIGN,NO_ED25519_EXPORTwhen notWOLFBOOT_ENABLE_WOLFHSM_SERVER(HSM server is the only build that also signs with ED25519).
Activation. WOLFBOOT_SIGN_ED448 || WOLFBOOT_SIGN_SECONDARY_ED448.
Sets:
HAVE_ED448,HAVE_ED448_VERIFY,ED448_SMALLWOLFSSL_SHA3,WOLFSSL_SHAKE256,WOLFSSL_SHA512NO_ED448_SIGN,NO_ED448_EXPORTwhen notWOLFHSM_SERVER.
Activation. Any WOLFBOOT_SIGN_ECC{256,384,521},
WOLFBOOT_SIGN_SECONDARY_ECC*, WOLFCRYPT_SECURE_MODE,
WOLFCRYPT_TEST, or WOLFCRYPT_BENCHMARK.
Sets:
HAVE_ECC,ECC_TIMING_RESISTANT,ECC_USER_CURVES,WOLFSSL_PUBLIC_MP- Per-curve:
HAVE_ECC256,HAVE_ECC384/WOLFSSL_SP_384,HAVE_ECC521/WOLFSSL_SP_521 FP_MAX_BITSper the largest active curveWOLFSSL_SP_NO_*for unselected curves (when SP math is in use)- SP math:
WOLFSSL_SP_MATH,WOLFSSL_SP_SMALL,WOLFSSL_HAVE_SP_ECC - Verify-only carve-outs (
NO_ECC_SIGN,NO_ECC_DHE,NO_ECC_EXPORT,NO_ECC_KEY_EXPORT) when no TPM/SECURE_MODE/TEST/BENCH/HSM is in use - Sign-and-verify defines (
HAVE_ECC_SIGN,HAVE_ECC_VERIFY,HAVE_ECC_KEY_EXPORT/IMPORT,WOLFSSL_KEY_GEN) under SECURE_MODE/ TEST/BENCH/HSM - Freescale LTC bindings under
FREESCALE_USE_LTC
Notes. The internal carve-outs for verify-only vs sign-capable are the most complex piece of any SIGN fragment. They are kept inline (rather than collapsed via NEEDS markers) because the conditions are ECC-specific and don't fit the global marker vocabulary cleanly. The fragment is self-contained.
Activation. Always included by sign_dispatch.h. Inside the file,
the outer #if tests the same RSA / RSAPSS / SECONDARY / SECURE_MODE
condition as sign_dispatch.h would; the #else defines NO_RSA.
Sets when RSA is active:
WC_RSA_BLINDING,WC_RSA_DIRECT,RSA_LOW_MEM,WC_ASN_HASH_SHA256WC_RSA_PSSfor any RSAPSS flag- Verify-only carve-outs (
WOLFSSL_RSA_VERIFY_INLINE,WOLFSSL_RSA_VERIFY_ONLY,WOLFSSL_RSA_PUBLIC_ONLY,WC_NO_RSA_OAEP,NO_RSA_BOUNDS_CHECK) when not under TPM / SECURE_MODE / TEST / BENCH / HSM - Per-size:
FP_MAX_BITS,SP_INT_BITS,RSA_MIN_SIZE,RSA_MAX_SIZE,WOLFSSL_SP_<size>,WOLFSSL_SP_NO_<other_sizes> - SP math:
WOLFSSL_HAVE_SP_RSA,WOLFSSL_SP,WOLFSSL_SP_SMALL,WOLFSSL_SP_MATH - Under
WOLFCRYPT_SECURE_MODE: re-#definesFP_MAX_BITSand SP size flags to span 2048-4096 (the secure side may serve any RSA size)
Sets when RSA is not active: NO_RSA.
Notes. This is the only SIGN fragment included unconditionally,
because the NO_RSA fallback must still run for ECC/Ed25519/etc.
configurations to avoid linking the RSA code path.
Activation. WOLFBOOT_SIGN_ML_DSA || WOLFBOOT_SIGN_SECONDARY_ML_DSA.
Sets:
HAVE_DILITHIUM,WOLFSSL_WC_DILITHIUM,WOLFSSL_EXPERIMENTAL_SETTINGS- Verify-only and small-mem variants:
WOLFSSL_DILITHIUM_VERIFY_ONLY,WOLFSSL_DILITHIUM_NO_LARGE_CODE,WOLFSSL_DILITHIUM_SMALL,WOLFSSL_DILITHIUM_VERIFY_SMALL_MEM,WOLFSSL_DILITHIUM_VERIFY_NO_MALLOC WOLFSSL_DILITHIUM_NO_ASN1when not WOLFHSM client/server (HSM needs ASN.1 for ML-DSA keys traveling over the comm channel)WOLFSSL_SHA3,WOLFSSL_SHAKE256,WOLFSSL_SHAKE128,WOLFSSL_SP_NO_DYN_STACK
Activation. WOLFBOOT_SIGN_LMS.
Sets:
WOLFSSL_HAVE_LMS,WOLFSSL_WC_LMS,WOLFSSL_WC_LMS_SMALL,WOLFSSL_LMS_VERIFY_ONLYWOLFSSL_LMS_MAX_LEVELS LMS_LEVELS,WOLFSSL_LMS_MAX_HEIGHT LMS_HEIGHT,LMS_IMAGE_SIGNATURE_SIZE IMAGE_SIGNATURE_SIZE
Notes. The user-set parameter values (LMS_LEVELS, LMS_HEIGHT,
LMS_WINTERNITZ, IMAGE_SIGNATURE_SIZE) are still passed by
options.mk from the .config file. This fragment maps those into
the WOLFSSL_LMS_* flags wolfCrypt expects.
Activation. WOLFBOOT_SIGN_XMSS.
Sets:
WOLFSSL_HAVE_XMSS,WOLFSSL_WC_XMSS,WOLFSSL_WC_XMSS_SMALL,WOLFSSL_XMSS_VERIFY_ONLY,WOLFSSL_XMSS_MAX_HEIGHT 32XMSS_IMAGE_SIGNATURE_SIZE IMAGE_SIGNATURE_SIZE
Purpose. Conditionally include the right hash_*.h fragment.
SHA-256 is the foundation default and has no fragment.
Activation. WOLFBOOT_HASH_SHA384.
Sets: WOLFSSL_SHA384. Defines NO_SHA256 when no other consumer
(no RSA, no TPM, no secure-mode, no test/bench) needs SHA-256. Adds
WOLFSSL_SHA512/WOLFSSL_NOSHA512_224/WOLFSSL_NOSHA512_256 if
not already set (SHA-384 is the truncation of SHA-512).
Activation. WOLFBOOT_HASH_SHA3_384.
Sets: WOLFSSL_SHA3. Defines NO_SHA256 under the same
"no-other-consumer" condition.
Activation. Always included; bodies gate internally on
EXT_ENCRYPTED and SECURE_PKCS11.
Sets:
EXT_ENCRYPTEDbranch:HAVE_PWDBASEDSECURE_PKCS11branch: full PKCS#11 token support (HAVE_PWDBASED,HAVE_PBKDF2,WOLFPKCS11_*,HAVE_AESCTR,WOLFSSL_AES_GCM,GCM_TABLE_4BIT,WOLFSSL_AES_128,HAVE_SCRYPT,HAVE_AESGCM,HAVE_PKCS8)- Always:
HAVE_PKCS11_STATIC
Notes. The NO_PWDBASED fallback (when HAVE_PWDBASED is not set)
lives in finalize.h, not here, because it must run after
trustzone.h and tpm.h have had a chance to opt in.
Activation. Bodies gate on WOLFCRYPT_SECURE_MODE,
WOLFCRYPT_TZ_PSA, and WOLFBOOT_TZ_FWTPM.
Sets under WOLFCRYPT_SECURE_MODE:
- Custom RNG seed callback (
hal_trng_get_entropy→CUSTOM_RAND_GENERATE_SEED) WOLFSSL_AES_CFB
Sets under WOLFCRYPT_TZ_PSA: broad PSA cipher / hash / AEAD /
PRF support — WOLFSSL_AES_COUNTER, WOLFSSL_AES_GCM, HAVE_AESGCM,
HAVE_AESCCM, HAVE_AES_ECB, WOLFSSL_AES_CFB, WOLFSSL_AES_OFB,
HAVE_CHACHA, HAVE_POLY1305, WOLFSSL_CMAC,
WOLFSSL_ECDSA_DETERMINISTIC_K, WOLFSSL_HAVE_PRF, HAVE_HKDF,
HAVE_PBKDF2, HAVE_PWDBASED, WOLFSSL_KEY_GEN, WC_RSA_PSS,
WOLFSSL_PSS_SALT_LEN_DISCOVER, WOLFSSL_RSA_OAEP,
HAVE_ECC_KEY_EXPORT, HAVE_ECC_KEY_IMPORT. Also forces NO_DES3.
Sets under WOLFBOOT_TZ_FWTPM: WOLFSSL_AES_CFB, WOLFSSL_SHA384.
Notes. WOLFBOOT_NEEDS_CMAC and WOLFBOOT_NEEDS_KDF for
WOLFCRYPT_TZ_PSA/WOLFBOOT_TZ_FWTPM are declared in cascade.h,
not here.
Activation. WOLFBOOT_TPM && !WOLFBOOT_TZ_FWTPM. (FWTPM uses a
firmware-TPM in the secure world and has its own configuration in
trustzone.h.) WOLFBOOT_TPM_PARMENC is derived in cascade.h.
Sets:
WOLFTPM2_NO_HEAP- Small-stack budget when
WOLFTPM_SMALL_STACK:MAX_COMMAND_SIZE 1024,MAX_RESPONSE_SIZE 1350,WOLFTPM2_MAX_BUFFER 1500,MAX_SESSION_NUM 2,MAX_DIGEST_BUFFER 973 WOLFBOOT_TPM_PARMENCbranch:WOLFSSL_AES_CFB,WOLFSSL_PUBLIC_MP,CUSTOM_RAND_GENERATE_SEEDstub,WC_RNG_SEED_CBWOLFTPM_MMIObranch:WOLFTPM_ADV_IO,XTPM_WAIT()HASH_COUNT 3- TPM
printfredirect whenDEBUG_WOLFTPMand notARCH_SIM
Activation. WOLFBOOT_ENABLE_WOLFHSM_CLIENT || WOLFBOOT_ENABLE_WOLFHSM_SERVER.
Sets:
WOLF_CRYPTO_CBHAVE_ANONYMOUS_INLINE_AGGREGATES 1(overrides the0default inbase.h)WOLFSSL_KEY_GEN
Activation. WOLFBOOT_ENABLE_WOLFHSM_SERVER && WOLFBOOT_CERT_CHAIN_VERIFY. This is the only build mode that links
the wolfSSL TLS-layer cert manager (server side).
Sets: NO_TLS, NO_OLD_TLS, WOLFSSL_NO_TLS12,
WOLFSSL_USER_IO, WOLFSSL_SP_MUL_D, WOLFSSL_PEM_TO_DER,
WOLFSSL_ALLOW_NO_SUITES.
Notes. The companion WOLFCRYPT_ONLY carve-out (which un-defines
WOLFCRYPT_ONLY in this mode) still lives in base.h as part of the
foundation.
Activation. WOLFBOOT_RENESAS_TSIP || WOLFBOOT_RENESAS_RSIP || WOLFBOOT_RENESAS_SCEPROTECT.
Sets: WOLFBOOT_SMALL_STACK, WOLF_CRYPTO_CB,
WOLF_CRYPTO_CB_ONLY_ECC, WOLF_CRYPTO_CB_ONLY_RSA,
WOLFSSL_NO_SW_MATH, MAX_CRYPTO_DEVID_CALLBACKS 2,
WC_NO_DEFAULT_DEVID, WOLFSSL_AES_SMALL_TABLES. Per-flavor
(TSIP / RSIP / SCEPROTECT): adds the corresponding wolfCrypt
Renesas port flags and key-storage addresses.
Activation. Multiple internal gates.
Sets:
WOLFSSL_HAVE_SP_ECC || WOLFSSL_HAVE_SP_RSA(set by SIGN fragments): SP math word-size selection per arch (WOLFSSL_SP_ARM64_ASM,WOLFSSL_SP_X86_64_ASM,SP_WORD_SIZE,HAVE___UINT128_T,ULLONG_MAX)__QNX__:WOLFSSL_HAVE_MIN,WOLFSSL_HAVE_MAXWOLFSSL_STM32_PKA:HAVE_UINTPTR_T
Activation. Bodies gate on WOLFCRYPT_TEST and
WOLFCRYPT_BENCHMARK.
Sets when WOLFCRYPT_TEST: NO_CRYPT_TEST_EXTENDED,
USE_CERT_BUFFERS_256, undefines NO_CRYPT_TEST. NO_CRYPT_TEST is
defined when test mode is not active.
Sets when WOLFCRYPT_BENCHMARK: BENCH_EMBEDDED, undefines
NO_CRYPT_BENCHMARK. NO_CRYPT_BENCHMARK is defined when bench mode
is not active.
Sets when either is active: NO_WRITE_TEMP_FILES,
WOLFSSL_LOG_PRINTF, static memory pool, WOLFSSL_SP_MUL_D,
WOLFSSL_USER_CURRTIME, XTIME my_time, HAVE_AESGCM, GCM_TABLE,
plus the LPC55S69 vs custom-RNG split (LPC55S69 path enables
HAVE_AES_ECB/AES_OFB/AES_CFB/AES_COUNTER and SHA-256/384/512;
non-LPC path defines WC_NO_HASHDRBG and a my_rng_seed_gen custom
RNG).
Purpose. Single reconciliation point. See Section 7.
cascade.h runs first and consists of three sections:
Lift Make-side feature implications into header-side cascades so an
IDE-only build (which sets only the high-level flags) sees the same
derived flags that options.mk would emit.
/* Any TPM-using feature implies WOLFBOOT_TPM. */
#if defined(WOLFBOOT_TPM_VERIFY) || defined(WOLFBOOT_MEASURED_BOOT) || \
defined(WOLFBOOT_TPM_KEYSTORE) || defined(WOLFBOOT_TPM_SEAL)
# ifndef WOLFBOOT_TPM
# define WOLFBOOT_TPM
# endif
#endif
/* TPM keystore and seal both require TPM session parameter encryption. */
#if defined(WOLFBOOT_TPM_KEYSTORE) || defined(WOLFBOOT_TPM_SEAL)
# ifndef WOLFBOOT_TPM_PARMENC
# define WOLFBOOT_TPM_PARMENC
# endif
#endifTested by cascade.h's own WOLFBOOT_NEEDS_ASN block, set on any
RSA SIGN flag (primary or secondary, RSA or RSAPSS) or
WOLFCRYPT_SECURE_MODE && !PKCS11_SMALL. Mirrored in
sign_dispatch.h's own gate for including sign_rsa.h's positive
configuration.
The full positive-intent vocabulary, declared from feature-flag tests. See the Marker Reference for the conditions per marker.
The cascade.h structure is intentionally one-pass: every block tests
already-known flags (high-level WOLFBOOT_* or WOLFCRYPT_* flags
plus the derived WOLFBOOT_TPM and WOLFBOOT_TPM_PARMENC) and emits
markers. No fragment downstream needs to read another fragment's
internal state.
finalize.h runs last and contains four sections:
Each negative wolfCrypt flag is gated by the absence of the matching
WOLFBOOT_NEEDS_* marker. Two markers are bipolar:
/* HASHDRBG: positive when needed, WC_NO_HASHDRBG otherwise. */
#ifdef WOLFBOOT_NEEDS_HASHDRBG
# ifndef HAVE_HASHDRBG
# define HAVE_HASHDRBG
# endif
#else
# ifndef WC_NO_HASHDRBG
# define WC_NO_HASHDRBG
# endif
#endif
/* BASE64 / NO_CODING. */
#ifdef WOLFBOOT_NEEDS_BASE64
# define WOLFSSL_BASE64_ENCODE
#else
# define NO_CODING
#endifThe rest are unipolar:
#ifndef WOLFBOOT_NEEDS_RNG
# define WC_NO_RNG
#endif
#ifndef WOLFBOOT_NEEDS_AES
# define NO_AES
#endif
/* ... */HAVE_PWDBASED does not have a NEEDS marker because no fragment outside
encrypt.h / trustzone.h opts in. finalize.h simply checks
#ifndef HAVE_PWDBASED: #define NO_PWDBASED.
A flat list of wolfCrypt features that wolfBoot never uses, regardless of configuration:
NO_DH, WOLFSSL_NO_PEM, NO_ASN_TIME, NO_RC4, NO_SHA, NO_DSA, NO_MD4,
NO_RABBIT, NO_MD5, NO_SIG_WRAPPER, NO_CERT, NO_SESSION_CACHE, NO_HC128,
NO_DES3 (if not already set), NO_WRITEV, NO_FILESYSTEM (unless
WOLFBOOT_PARTITION_FILENAME), NO_MAIN_DRIVER, NO_OLD_RNGNAME,
NO_WOLFSSL_DIR, WOLFSSL_NO_SOCK, WOLFSSL_IGNORE_FILE_WARN,
NO_ERROR_STRINGS, NO_PKCS12, NO_PKCS8, NO_CHECK_PRIVATE_KEY
If a future feature ever needs one of these to be skipped (e.g. some
new TLS-using mode wants NO_PEM skipped), the entry should move
under a new NEEDS marker.
Outside of explicit WOLFCRYPT_TEST/WOLFCRYPT_BENCHMARK mode,
BENCH_EMBEDDED is set as a small-target sizing hint. Test/bench mode
sets it itself in test_bench.h and overrides this default.
Two-branch policy:
WOLFBOOT_SMALL_STACKsetsWOLFSSL_SMALL_STACK. Errors out if combined withWOLFBOOT_HUGE_STACK.- else: when SP math is in use, sets
WOLFSSL_SP_NO_MALLOCandWOLFSSL_SP_NO_DYN_STACK. Then, unlessWOLFBOOT_NEEDS_MALLOCis set, definesNO_WOLFSSL_MEMORYandWOLFSSL_NO_MALLOCfor a pure-stack wolfCrypt with no heap.WOLFBOOT_NEEDS_MALLOCis declared bycascade.hforSECURE_PKCS11,WOLFCRYPT_TZ_PSA,WOLFBOOT_ENABLE_WOLFHSM_SERVER, and test/bench.
This cookbook walks through adding a hypothetical
WOLFBOOT_NEW_FEAT=1 feature that needs RNG, AES and ASN.1 parsing. Replace the
names with your actual feature throughout.
In options.mk, add:
ifeq ($(WOLFBOOT_NEW_FEAT),1)
CFLAGS+=-D"WOLFBOOT_ENABLE_NEW_FEAT"
# Add any object files / library paths the feature needs
WOLFCRYPT_OBJS+=...
endifCreate include/user_settings/new_feat.h:
#ifndef _WOLFBOOT_USER_SETTINGS_NEW_FEAT_H_
#define _WOLFBOOT_USER_SETTINGS_NEW_FEAT_H_
#ifdef WOLFBOOT_ENABLE_NEW_FEAT
/* Positive flags this feature needs directly. */
# define WOLF_CRYPTO_CB
# define WOLFSSL_KEY_GEN
/* anything else specific to this feature... */
#endif
#endifIn include/user_settings.h, add it among the feature fragments:
#include "user_settings/wolfhsm.h"
#include "user_settings/new_feat.h" /* <-- add */
#include "user_settings/cert_chain.h"If the feature needs RNG, AES, and ASN.1, add to cascade.h's
declarations:
/* NEEDS_RNG: ... */
#if defined(WOLFBOOT_TPM_PARMENC) || \
defined(WOLFCRYPT_SECURE_MODE) || \
defined(WOLFCRYPT_TEST) || \
defined(WOLFCRYPT_BENCHMARK) || \
defined(WOLFBOOT_ENABLE_WOLFHSM_SERVER) || \
(defined(WOLFBOOT_ENABLE_WOLFHSM_CLIENT) && \
defined(WOLFBOOT_SIGN_ML_DSA)) || \
defined(WOLFBOOT_ENABLE_NEW_FEAT) /* <-- add */
# ifndef WOLFBOOT_NEEDS_RNG
# define WOLFBOOT_NEEDS_RNG
# endif
#endif…and the same for WOLFBOOT_NEEDS_AES and WOLFBOOT_NEEDS_ASN.
You do not need to touch finalize.h here — its #ifndef WOLFBOOT_NEEDS_* blocks already do the right thing once the markers
are declared.
Skip this step if the wolfCrypt capabilities your feature needs are already covered by an existing marker (Step 4 above). This step applies only when your feature needs a wolfCrypt capability that is currently disabled by a negative flag without a NEEDS_ marker* — a case that requires extending the marker vocabulary.
Recall the polarity rules from Section 3.1:
-
Positive flags (
HAVE_*,WOLFSSL_*) compose trivially. If your feature wantsHAVE_PKCS7orWOLFSSL_AES_OFB, just#defineit in your fragment header. Done. No NEEDS marker needed. -
Negative flags (
NO_*,WC_NO_*) don't compose. If your feature wants Diffie-Hellman, butNO_DHis currently defined unconditionally infinalize.h's always-on disables block, then#define HAVE_DHfrom your fragment is not enough —NO_DHwill still be defined later (sincefinalize.hruns last) and wolfCrypt will strip DH regardless ofHAVE_DH. You need to makeNO_DHconditional, which means adding aWOLFBOOT_NEEDS_DHmarker to the vocabulary.
The tell that you're in this case: you #define HAVE_X in your
fragment, build, and either (a) the build fails with the assertion
error: "user_settings: NEEDS_* marker required; see docs/wolfssl-config.md"
raised by the #error directive in finalize.h's always-on block, or
(b) the build succeeds but the wolfCrypt feature is still stripped
from the binary because finalize.h later defines NO_X and that
wins. Most always-on disables in finalize.h are guarded by an
assertion that catches the polarity-mismatch at compile time and
points the developer at this section. A handful of disables (the ones
without a canonical positive form, like NO_ASN_TIME, or the
environment ones, like NO_FILESYSTEM) have no assertion; for those
you'll only see case (b).
Imagine the new feature WOLFBOOT_NEW_FEAT needs Diffie-Hellman.
NO_DH lives in finalize.h's always-on block today.
1. Identify and confirm the polarity. Grep for the disable:
grep -nE 'NO_DH|HAVE_DH' include/user_settings/*.hVerify it's set unconditionally in finalize.h's always-on block,
not in a fragment. (If a fragment sets it, the rules from Section 2.3
say fragments shouldn't #undef, so the right fix is still to lift
it into finalize.h under a NEEDS marker.)
2. Declare the marker in cascade.h. Add a new WOLFBOOT_NEEDS_DH
block alongside the existing markers:
/* NEEDS_DH: features that use Diffie-Hellman key exchange. */
#if defined(WOLFBOOT_ENABLE_NEW_FEAT)
# ifndef WOLFBOOT_NEEDS_DH
# define WOLFBOOT_NEEDS_DH
# endif
#endifIf your feature can't be expressed in cascade.h alone (for example, it has an internal sub-condition that depends on other fragment state), declare the marker from your fragment header instead. Either location works; cascade.h is preferred when the trigger is a clean test of high-level feature flags.
3. Lift the disable in finalize.h. Move the #define NO_DH
line out of the always-on disables block and into the NEEDS-gated
section:
/* In finalize.h's NEEDS_* reconciliation section, alongside the
* existing #ifndef WOLFBOOT_NEEDS_* blocks: */
#ifndef WOLFBOOT_NEEDS_DH
# define NO_DH
#endifDelete the now-redundant #define NO_DH from finalize.h's always-on
list.
4. Set the matching positive flag in your fragment. Some wolfCrypt features only get linked in when both the negative is not set and a positive flag is set. For DH:
/* In include/user_settings/new_feat.h */
#ifdef WOLFBOOT_ENABLE_NEW_FEAT
# define HAVE_DH
/* and any DH-specific tuning your feature needs... */
#endifYou'll know whether a positive flag is needed by checking wolfCrypt's
wolfssl/wolfcrypt/settings.h for how the feature is gated. Some
features (like NO_AES) gate purely on the negative flag — clearing
the negative is sufficient. Others (like DH) require both: clearing
NO_DH and setting HAVE_DH.
5. Update Section 4 of this document. Add a row to the marker reference table for the new marker, listing the disable it gates, the conditions that declare it, and where it's declared. Also extend any other relevant sections (the cascade.h walkthrough in Section 6, the fragment reference in Section 5 if applicable).
6. Verify byte-identity for unaffected configs. This is critical
when extending the vocabulary. Build a representative set of canary
configs without WOLFBOOT_NEW_FEAT set (e.g. sim.config,
sim-tpm-seal.config, stm32h5-tz-psa.config) before and after your
changes. The binaries should be byte-identical when debug info and
build-id are stripped — none of them declare WOLFBOOT_NEEDS_DH, so
NO_DH still gets defined, and the resulting wolfCrypt is the same
as before. If a canary config diverges, you've either set the marker
too aggressively in cascade.h or moved more than just the one
#define NO_DH line out of the always-on block.
-
Don't
#undef NO_Xfrom a fragment. This breaks the fragment-author rule from Section 2.3 (fragments only#define). It also makes the disable harder to find when reading the code: someone grepping forNO_DHinfinalize.hwould be misled. Use a marker instead. -
Don't gate the marker on a flag that only your fragment knows about unless the flag is unique to your feature. If
WOLFBOOT_TPMneeds DH too (hypothetically), the marker should mention TPM in its trigger list — declared in cascade.h — not be set indirectly through your fragment's internal logic. -
Don't add the marker only to fragments without also lifting the disable in
finalize.h. The marker is inert on its own; it becomes effective whenfinalize.hreads it. Both halves of the edit must land together.
Build a config that exercises the new feature. Confirm the build links and the binary size is sensible.
To understand what wolfCrypt config a given .config produces:
The most exhaustive view:
cp config/examples/<name>.config .config
make clean
make CFLAGS_EXTRA='-E -dM' wolfboot.elf 2>&1 | grep -E '^#define (WOLFSSL_|HAVE_|NO_|WC_NO_|WOLFBOOT_)' | sortThis shows every #define that wolfCrypt sees, including everything
emitted by options.mk, cascade.h, the active fragments, and
finalize.h.
For a more focused view of just the WOLFBOOT_NEEDS_* markers (which
features are opting in) and the resulting NO_*/WC_NO_* flags
(which features wolfCrypt strips):
make CFLAGS_EXTRA='-E -dM' wolfboot.elf 2>&1 \
| grep -E '^#define (WOLFBOOT_NEEDS_|NO_|WC_NO_)' | sortFor a specific flag like NO_AES:
- Search
include/user_settings/for the flag. Anything infinalize.his gated by a NEEDS marker; anything in a fragment is set by that fragment unconditionally (within its own activation gate). - If it's gated by
WOLFBOOT_NEEDS_X, find where the marker is declared (almost alwayscascade.h). The condition list shows exactly which features opt in. - If the flag is set in
options.mk(rare for purely-wolfCrypt flags after the refactor), grepoptions.mkfor the flag.
After the refactor, options.mk and include/user_settings/ have a
clear division of labor.
- WOLFCRYPT_OBJS selection. The linker input set. This is the only
surface the preprocessor cannot generate, because
makechooses which.ofiles end up on the link line. - High-level
WOLFBOOT_*flag emission. Any flag a user sets in.configbecomes a-Dflag here. - Tool invocation.
KEYGEN_OPTIONS,SIGN_OPTIONS, keytool arguments,whnvmtoolsetup, etc. - Mutual-exclusion errors.
$(error WOLFCRYPT_TZ_PKCS11 and TZ_PSA cannot both be set)-style checks at config time. - Math backend selection. SPMATH vs SPMATHALL vs USE_FAST_MATH —
this affects both
MATH_OBJSand-Dflags. Today still inarch.mk:4-17. - Architecture-specific assembly objects.
arch.mkselectssp_arm64.ovssp_c64.oetc. - Parameter values.
LMS_LEVELS,LMS_HEIGHT,XMSS_PARAMS,IMAGE_SIGNATURE_SIZE,ML_DSA_LEVEL,MEASURED_PCR_A— these come from the user's.configand reach the headers as-Ds.
- Every wolfCrypt-side
#definethat's purely a configuration choice rather than an input. Anything a wolfBoot maintainer would set "because TPM+PARMENC needsWOLFSSL_AES_CFB" is here. - Every
WOLFBOOT_NEEDS_*marker. - Every
WOLFCRYPT_*andNO_*/WC_NO_*decision. - Cascades (
WOLFBOOT_TPM_VERIFY → WOLFBOOT_TPM, etc.) so an IDE/CMake/Zephyr build does not need a separate Make pass.
The Phase 5 trim removed wolfCrypt-side -D flags from
LMS_EXTRA / XMSS_EXTRA (the WOLFSSL_HAVE_LMS,
WOLFSSL_LMS_MAX_LEVELS, etc. now live in sign_lms.h/sign_xmss.h).
The user-set parameter values (LMS_LEVELS, etc.) stay.
Other CFLAGS in options.mk (-DWOLFTPM_SMALL_STACK,
-DWOLF_CRYPTO_CB, -DWOLFHSM_CFG_ENABLE_CLIENT, etc.) could in
principle be moved into the matching fragments. They are left in
options.mk for now because: (a) they are mostly side-effect free
(positive-flag duplication is harmless under #ifndef), and (b) some
of them are also consumed by non-wolfCrypt code (wolfBoot's own
sources include the wolfHSM client, for example), where the Make-side
emission keeps them visible to those compilation units.
The header-only configuration scheme means alternative build paths need only:
- Set the high-level
WOLFBOOT_*flags (e.g.WOLFBOOT_SIGN_ECC256,WOLFBOOT_HASH_SHA256,WOLFBOOT_TPM_KEYSTORE). - Pass
-DWOLFSSL_USER_SETTINGSto the compiler. - Add
include/to the include path. - Compile the right
WOLFCRYPT_OBJSset (the linker input).
Steps 1-3 produce the correct wolfCrypt configuration via the cascade and fragments. Step 4 is the only one that still needs build-system involvement, because it's a linker concern.
CMakeLists.txt already sets -DWOLFSSL_USER_SETTINGS and adds
include/ to the include path. cmake/config_defaults.cmake and
lib/CMakeLists.txt contain a copy of the WOLFCRYPT_OBJS selection
logic; that piece is independent of this refactor and could be
trimmed in a future cleanup.
The Renesas IDE projects under IDE/Renesas/e2studio/ ship their own
hand-maintained copy of user_settings.h today. The refactor does
not touch those — they continue to work as before. New IDE projects
should adopt the shim pattern: have the IDE define the high-level
WOLFBOOT_* flags in its preprocessor settings and let the project
include include/user_settings.h (the shim) directly. The IDE then
gets the same configuration the Make build does.
zephyr/Kconfig maps user choices in the Zephyr menuconfig to -D
flags via CONFIG_WOLFBOOT_SIGN_ALG / CONFIG_WOLFBOOT_SIGN_HASH.
Those -Ds feed the cascade and fragments unchanged. No Zephyr-side
modifications are needed for this refactor.
No change. The .config flags (SIGN, HASH, WOLFBOOT_TPM_*,
WOLFHSM_*, etc.) work the same way they always have. options.mk
translates them into the same -D flags as before; the headers now
do more of the work that options.mk used to do, but the user-facing
flags are unchanged.
Backwards-compatible. Every public flag (WOLFBOOT_SIGN_*,
WOLFBOOT_HASH_*, WOLFBOOT_TPM, WOLFBOOT_ENABLE_WOLFHSM_*, etc.)
still works as before. The WOLFBOOT_NEEDS_* namespace is internal
and should not be defined by users; it is reserved for cascade /
fragment internals.
If you maintain your own user_settings.h (an IDE or downstream
fork), the file you copied previously was 781 lines. The new shim is
73 lines, but it produces the same wolfCrypt configuration when the
same WOLFBOOT_* flags are set. Two options:
- Adopt the shim. Replace your copy with the shim and pull the
fragment headers from
include/user_settings/. Keep your owntarget.hfor board-specific addresses. Future maintenance benefits from any fragment improvements. - Keep your copy. The old monolithic file still produces the same binary if it sees the same input flags. There is no upgrade pressure on existing IDE projects until they need a feature added after the refactor landed.
include/
├── user_settings.h # 73-line shim
└── user_settings/
├── base.h # foundation defines
├── cascade.h # feature-flag cascades + NEEDS markers
│
├── sign_dispatch.h # SIGN family dispatch
├── sign_ecc.h
├── sign_rsa.h
├── sign_ed25519.h
├── sign_ed448.h
├── sign_ml_dsa.h
├── sign_lms.h
├── sign_xmss.h
│
├── hash_dispatch.h # HASH family dispatch
├── hash_sha384.h
├── hash_sha3.h
│
├── encrypt.h # EXT_ENCRYPTED, SECURE_PKCS11
├── trustzone.h # SECURE_MODE, TZ_PSA, TZ_FWTPM
├── tpm.h # WOLFBOOT_TPM
├── wolfhsm.h # WOLFHSM client/server
├── cert_chain.h # CERT_CHAIN_VERIFY (server side)
├── renesas.h # TSIP / RSIP / SCEPROTECT
├── platform.h # SP-math word size, QNX, STM32 PKA
├── test_bench.h # WOLFCRYPT_TEST / BENCHMARK
│
└── finalize.h # NEEDS_* reconciliation + global "off"
- Fragment. A header file in
include/user_settings/that contributes wolfCrypt configuration for one wolfBoot concern (a SIGN family, a feature block, etc.). - Shim.
include/user_settings.h. The file wolfSSL loads via-DWOLFSSL_USER_SETTINGS. Contains only#includes. - Cascade. A preprocessor implication that derives one flag from
another (e.g.
WOLFBOOT_TPM_VERIFY → WOLFBOOT_TPM). Lives incascade.h. - NEEDS marker. A
WOLFBOOT_NEEDS_*macro declared by a fragment or bycascade.hto express positive intent.finalize.hreads the absence of a marker and applies the corresponding wolfCrypt negative flag. - Positive flag. A wolfCrypt feature flag that is off by default
and turned on by
#define-ing it (HAVE_*,WOLFSSL_*). - Negative flag. A wolfCrypt feature flag that is on by default
and turned off by
#define-ing it (NO_*,WC_NO_*). - Reconciliation. The process by which
finalize.htranslates the set of declared NEEDS markers into the corresponding negative flags.