Merge pull request #606 from dgarske/pqc_no_wolfcrypt_build

Fix --enable-pqc build with --disable-wolfcrypt
pull/590/head
Aidan Garske 2026-09-11 12:35:54 -07:00 committed by GitHub
commit 498a8e103a
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
4 changed files with 94 additions and 30 deletions

View File

@ -18,7 +18,10 @@ concurrency:
# prove each per-operation gate compiles and links (lib + server + unit tests).
# The (mldsa=no, mlkem=no) combo is intentionally absent: it is a configure
# error (no PQC algorithm) verified by the reject-no-pqc job below. Runtime
# make check on the full op set is covered by pqc-examples.yml.
# make check on the full op set is covered by pqc-examples.yml. The
# standalone-pqc job below covers PQC with --disable-wolfcrypt, and is the
# only PQC job that builds the examples and unit tests (every row above uses
# --disable-examples, so example/test compile breaks escape them).
jobs:
build:
if: github.event_name != 'pull_request' || github.event.pull_request.draft == false
@ -134,6 +137,48 @@ jobs:
config.log
retention-days: 5
standalone-pqc:
# PQC command marshaling is pure wire format, so it must build with
# --disable-wolfcrypt (embedded client driving a v1.85 TPM, no host
# crypto). Deliberately no setup-wolfssl step: this config links no
# wolfSSL at all, which is exactly what the job proves. Deliberately no
# --disable-examples: a plain `make` compiles examples/pqc/* and
# tests/unit.test, which is where the breakage showed up.
# Build-only -- no TPM is reachable over the SPI HAL on a runner.
if: github.event_name != 'pull_request' || github.event.pull_request.draft == false
runs-on: ubuntu-latest
timeout-minutes: 15
strategy:
fail-fast: false
matrix:
include:
- name: pqc-spi-nowolfcrypt
wolftpm_config: --enable-pqc --enable-spi --disable-wolfcrypt
- name: v185-nowolfcrypt
wolftpm_config: --enable-v185 --disable-wolfcrypt --disable-autodetect --disable-fwtpm
steps:
- name: Checkout wolfTPM
uses: actions/checkout@v4
- name: Build wolfTPM standalone (${{ matrix.name }})
run: |
./autogen.sh
./configure ${{ matrix.wolftpm_config }}
make -j"$(nproc)"
- name: Show resolved PQC options
run: grep -E "WOLFTPM_(V185|PQC|NO_ML|NO_HASH|MLDSA|MLKEM)" wolftpm/options.h || true
- name: Upload failure logs
if: failure()
uses: actions/upload-artifact@v4
with:
name: standalone-pqc-${{ matrix.name }}-logs
path: |
config.log
retention-days: 5
reject-no-pqc:
# --enable-pqc with both algorithms off must FAIL at configure with a clear
# message (no PQC algorithm). Verifies the guard, not just that it builds.

View File

@ -963,35 +963,45 @@ fi
if test "x$ENABLED_PQC_MODE" != "xno"
then
# Explicit opt-in: re-probe so we fail at configure time (with a
# clear hint about wolfSSL flags) rather than deep inside the compile
# with a cryptic error. Header existence alone is not enough -- the
# actual functions must be declared (gated by WOLFSSL_HAVE_MLDSA /
# HAVE_MLKEM in wolfssl/options.h). The probed symbol
# `wc_MlDsaKey_Init` is the canonical FIPS 204 entry point introduced
# by wolfSSL PR #10436 (post-v5.9.1-stable): wolfTPM consumes
# <wolfssl/wolfcrypt/wc_mldsa.h> directly, so older wolfSSL that
# only ships <wolfssl/wolfcrypt/dilithium.h> is not supported here.
AC_CHECK_DECL([wc_MlDsaKey_Init], [],
[AC_MSG_ERROR([--enable-v185/--enable-pqc requires wolfSSL built with --enable-mldsa (or alias --enable-dilithium) and --enable-experimental, ships post-v5.9.1-stable])],
[[#include <wolfssl/options.h>
#include <wolfssl/wolfcrypt/wc_mldsa.h>]])
AC_CHECK_DECL([wc_MlKemKey_Init], [],
[AC_MSG_ERROR([--enable-v185/--enable-pqc requires wolfSSL >= v5.8.0-stable built with --enable-mlkem --enable-experimental])],
[[#include <wolfssl/options.h>
#include <wolfssl/wolfcrypt/wc_mlkem.h>]])
# The PQC command set is pure marshaling, so it stands on its own with
# --disable-wolfcrypt (an embedded client driving a v1.85 TPM with no
# host-side crypto). Only probe wolfSSL when it is actually linked --
# otherwise no -I/-l is added and the probe would test headers this
# build never sees.
if test "x$ENABLED_WOLFCRYPT" = "xyes"
then
# Explicit opt-in: re-probe so we fail at configure time (with a
# clear hint about wolfSSL flags) rather than deep inside the compile
# with a cryptic error. Header existence alone is not enough -- the
# actual functions must be declared (gated by WOLFSSL_HAVE_MLDSA /
# HAVE_MLKEM in wolfssl/options.h). The probed symbol
# `wc_MlDsaKey_Init` is the canonical FIPS 204 entry point introduced
# by wolfSSL PR #10436 (post-v5.9.1-stable): wolfTPM consumes
# <wolfssl/wolfcrypt/wc_mldsa.h> directly, so older wolfSSL that
# only ships <wolfssl/wolfcrypt/dilithium.h> is not supported here.
AC_CHECK_DECL([wc_MlDsaKey_Init], [],
[AC_MSG_ERROR([--enable-v185/--enable-pqc requires wolfSSL built with --enable-mldsa (or alias --enable-dilithium) and --enable-experimental, ships post-v5.9.1-stable])],
[[#include <wolfssl/options.h>
#include <wolfssl/wolfcrypt/wc_mldsa.h>]])
AC_CHECK_DECL([wc_MlKemKey_Init], [],
[AC_MSG_ERROR([--enable-v185/--enable-pqc requires wolfSSL >= v5.8.0-stable built with --enable-mlkem --enable-experimental])],
[[#include <wolfssl/options.h>
#include <wolfssl/wolfcrypt/wc_mlkem.h>]])
AC_MSG_CHECKING([wolfSSL version >= v5.8.0 for PQC])
AC_COMPILE_IFELSE([AC_LANG_SOURCE([[
#include <wolfssl/version.h>
#if LIBWOLFSSL_VERSION_HEX < 0x05008000
#error "wolfSSL < v5.8.0"
#endif
int main(void) { return 0; }
]])],
[AC_MSG_RESULT([yes])],
[AC_MSG_RESULT([no])
AC_MSG_ERROR([wolfTPM PQC requires wolfSSL >= v5.8.0-stable. Please upgrade wolfSSL.])])
AC_MSG_CHECKING([wolfSSL version >= v5.8.0 for PQC])
AC_COMPILE_IFELSE([AC_LANG_SOURCE([[
#include <wolfssl/version.h>
#if LIBWOLFSSL_VERSION_HEX < 0x05008000
#error "wolfSSL < v5.8.0"
#endif
int main(void) { return 0; }
]])],
[AC_MSG_RESULT([yes])],
[AC_MSG_RESULT([no])
AC_MSG_ERROR([wolfTPM PQC requires wolfSSL >= v5.8.0-stable. Please upgrade wolfSSL.])])
else
AC_MSG_NOTICE([--disable-wolfcrypt: PQC is command marshaling only (no host-side ML-DSA/ML-KEM)])
fi
if test "x$ENABLED_PQC_MODE" = "xv185"
then

View File

@ -32,7 +32,7 @@
#include <wolftpm/tpm2_swtpm.h>
#include <wolftpm/tpm2_tis.h>
#include <wolftpm/tpm2_spdm.h>
#ifdef WOLFTPM_MLDSA_SIGN
#if defined(WOLFTPM_MLDSA_SIGN) && !defined(WOLFTPM2_NO_WOLFCRYPT)
#include <wolfssl/wolfcrypt/wc_mldsa.h>
#endif

View File

@ -279,6 +279,15 @@ typedef int64_t INT64;
#define NOT_COMPILED_IN -174 /* Feature not compiled in */
#define LENGTH_ONLY_E -202 /* Returning output length only */
/* wolfCrypt is not compiled in, so wolfssl/wolfcrypt/memory.h is not
* available. Mirror the upstream volatile byte wipe so callers can
* still zero secrets without the compiler eliding the store. */
static inline void wc_ForceZero(void* mem, size_t len)
{
volatile byte* z = (volatile byte*)mem;
while (len--) *z++ = 0;
}
#define ENCODING_TYPE_PEM CTC_FILETYPE_PEM
#define ENCODING_TYPE_ASN1 CTC_FILETYPE_ASN1