Skip to content

Add CI that builds and runs every example#598

Open
aidangarske wants to merge 104 commits into
wolfSSL:masterfrom
aidangarske:ci-matrix
Open

Add CI that builds and runs every example#598
aidangarske wants to merge 104 commits into
wolfSSL:masterfrom
aidangarske:ci-matrix

Conversation

@aidangarske

@aidangarske aidangarske commented Jul 15, 2026

Copy link
Copy Markdown
Member

Adds CI that builds and runs every example against wolfSSL master and the latest stable tag, asserting on real output — not just exit 0 — and fixes the example bugs that blocked those runs from going green.

CI

  • Manifest-driven harness (run_example.py + examples-manifest.yml): build → run → assert expected output.
  • Per-target workflows for environments that need special toolchains: ESP32, Android, RT1060, UEFI, SGX, PSA/mbedTLS, device sims (SE050, ATECC608, STSAFE, TROPIC01, STM32, PIC32MZ), DTLS multicast, Windows/MSVC, cross-arch (m32/aarch64/s390x), sanitizers/valgrind/cppcheck, config-matrix.
  • Nightly runs everything vs master + stable and triages failures into per-directory GitHub issues (retry-once, then flake-vs-real classification).
  • Every network fetch (git clone, download, docker pull) is wrapped in a retry so a transient blip does not fail a job.

Fixes

Each is its own commit:

  • Expired fixtures — regenerated CRL + certs that silently broke the CRL/verify examples.
  • Wrong exit codes — servers/examples that "passed" by returning a byte count or an unconditional -1; they now fail when they should.
  • Never-worked examples — PQ/ML-DSA/ML-KEM API ports, a client-cert-less resume, identical XTS key halves.
  • Toolchain drift — ESP-IDF 5.x ENC28J60 + PHY ports, RT1060 cross-build, UEFI freestanding, Android NDK/API-31, mynewt 64-bit.
  • Real bugs — a custom-IO double-free/use-after-free, DTLS resume-on-close_notify + record-spanning, TLS 1.3 early-data session-ticket handling.

Upstream wolfSSL bugs this CI surfaced

Examples are marked known-fail and gated per ref with fixed_on; drop the marker when each merges:

Copilot AI review requested due to automatic review settings July 15, 2026 00:38

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds a comprehensive GitHub Actions CI system to build and (where possible) run every example in this repository against wolfSSL master and the latest stable tag(s), using a manifest-driven matrix so failures are isolated to per-example jobs.

Changes:

  • Introduces manifest-driven CI workflows (host/emulated/cross) plus a nightly triage workflow that retries, classifies flakes vs real failures, and can file/update issues.
  • Adds Python harness/scripts to generate matrices, enforce “coverage” (no buildable example directory left unaccounted for), run examples with output assertions, and collect artifacts for triage.
  • Updates many examples/Makefiles/scripts/fixtures so they build/run reliably under CI (exit statuses, paths to certs, linking flags, regenerated CRL/certs, etc.).

Reviewed changes

Copilot reviewed 62 out of 64 changed files in this pull request and generated 5 comments.

Show a summary per file
File Description
X9.146/Makefile Makefile header tweak for X9.146 examples
x509_acert/README.md Fix build/run instructions and cert paths
x509_acert/Makefile Make OpenSSL prefix optional; adjust lib paths
uefi-static/Makefile Make libgcc/gnu-efi paths less distro-specific
tls/server-tls13.c Ensure successful exit status after shutdown
tls/server-tls13-certauth-clienthello.c Ensure successful exit status after shutdown
tls/server-tls-posthsauth.c Ensure successful exit status after shutdown
tls/client-tls13-resume.c Load client cert/key and CA separately
tls/client-tls.c Load client cert/key and CA separately
staticmemory/memory-bucket-optimizer/tester/Makefile Add include/lib paths for wolfSSL
staticmemory/memory-bucket-optimizer/optimizer/Makefile Add include/lib paths for wolfSSL
staticmemory/Makefile Correct Makefile title/comment
signature/sigtest/Makefile Make OpenSSL path optional and clearer
SGX_Linux/sgx_t.mk Update SGX C++ runtime library name
scripts/run-all-examples.sh Add local manifest-driven runner script
psa/Makefile Fix include path and guard empty PSA_INCLUDE
pq/stateful_hash_sig/xmss_example.c Remove redundant include
pq/stateful_hash_sig/lms_example.c Remove redundant include
pq/ml_kem/README.md Switch build instructions to make
pq/ml_kem/ml_kem.c Update include/header usage; simplify main signature
pq/ml_kem/Makefile Add Makefile for ML-KEM example
pq/ml_dsa/ml_dsa.c Update to FIPS 204 ctx APIs; fix exit code
pq/ml_dsa/Makefile Fix clean target artifacts list
pkcs7/scripts/runall.sh Fix ordering + ensure failures exit non-zero
pkcs7/scripts/openssl-verify.sh Gate on runall, add failure accounting, improve checks
pkcs7/Makefile Correct Makefile title and zlib comment
pkcs11/Makefile Correct Makefile title/comment
pk/srp/Makefile Fix WOLFSSL_INSTALL_DIR prefix
pk/enc-through-sign-rsa/rsa-public-decrypt-app.c Normalize return code from length-returning API
embedded/Makefile Adjust linux-specific target list handling
ecc/ecc-params.c Handle negative lengths; normalize exit status
ebpf/tls-uprobe-trace/Makefile Add wolfSSL include/lib flags
dtls/server-dtls-rw-threads.c Fix cert paths for CI execution
dtls/client-dtls-rw-threads.c Fix cert paths for CI execution
custom-io-callbacks/file-server/file-server.c Fix server return codes / cleanup flow
custom-io-callbacks/file-server/check.sh Make server/client orchestration bounded and reliable
custom-io-callbacks/file-client/file-client.c Fix client return codes
crypto/keywrap/Makefile Add Makefile for keywrap example
crypto/aes-modes/aes-xts.c Fix XTS key halves to be distinct
certvfy/Makefile Add include/lib flags for wolfSSL
certs/crl/regenerate-crl.sh Add script to regenerate CRL fixture
certs/crl/crl.pem Update CRL fixture to unexpired version
certmanager/README.md Fix example invocation name
certmanager/certverify.c Ensure successful exit status
certmanager/certloadverifybuffer.c Update embedded cert fixtures
certgen/Makefile Add Makefile header/comment
certgen/csr_w_ed25519_example.c Normalize return code from length-returning API
can-bus/Makefile Add include/lib flags for wolfSSL
can-bus/generate_ssl.sh Cap CN length to X.509 limits
btle/common/btle-sim.c Ignore SIGPIPE to avoid FIFO-close crashes
.gitignore Ignore new binaries/pycache; fix typo
.github/workflows/nightly.yml Add scheduled nightly orchestration
.github/workflows/examples.yml Add host-tier matrix workflow + coverage gate
.github/workflows/emulated.yml Add emulated-tier workflow (TPM/SGX/CAN/UEFI)
.github/workflows/cross-build.yml Add cross-build workflow (ESP32/Pico/etc.)
.github/workflows/ci-triage.yml Add triage workflow for nightly results
.github/workflows/_resolve-wolfssl.yml Add reusable wolfSSL ref resolution workflow
.github/scripts/run_example.py Add example harness (build/run/assert/output/artifacts)
.github/scripts/manifest.py Add manifest loader + matrix generator + coverage checker
.github/scripts/issue_store.py Add issue identity/body/state machine + scrubbing
.github/scripts/ci_triage.py Add triage logic (retry, classify, issues, AI advisory)
.github/examples-manifest.yml Add source-of-truth manifest for CI coverage/matrix
.github/actions/setup-wolfssl/action.yml Add composite action to build/cache/install wolfSSL

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread custom-io-callbacks/file-server/file-server.c
Comment thread custom-io-callbacks/file-server/file-server.c Outdated
Comment thread custom-io-callbacks/file-server/file-server.c
Comment thread custom-io-callbacks/file-client/file-client.c
Comment thread .github/examples-manifest.yml Outdated
Comment thread uefi-library/src/driver.c
(key, heap, devId))
WRAP_VOID(wc_MlDsaKey_Free, (wc_MlDsaKey* key), (key))
WRAP_FUNC(int, wc_MlDsaKey_SetParams, (wc_MlDsaKey* key, byte level), (key, level))
WRAP_FUNC(int, wc_MlDsaKey_MakeKey, (wc_MlDsaKey* key, WC_RNG* rng), (key, rng))

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

the context-less sign and verify are only available under WOLFSSL_MLDSA_NO_CTX according to /git/wolfssl/wolfssl/wolfcrypt/wc_mldsa.h

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! Switched to wc_MlDsaKey_SignCtx/VerifyCtx with an empty context, those are always compiled in.

Comment thread uefi-library/src/test_app.c Outdated

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI says these values aren't big enough for RSA 2048, and the check will always fail due to input validation

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Bumped to n[256]/d[256]/p[128]/q[128] so the components fit.

wolfssl_ref: ${{ fromJson(needs.resolve.outputs.refs_json) }}
include:
# uefi-static clones wolfSSL itself; `all` is wolfcrypt.efi
- example: uefi-static

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

uefi-static is not being run. Seems it needs to be one layer up to be part of the matrix:

Comment thread .github/workflows/emulated.yml Outdated
- uses: actions/upload-artifact@v4
if: always()
with:
name: results-tpm-${{ matrix.simulator }}-attempt${{ github.run_attempt }}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI says there should be another ref here, maybe {{ matrix.ref_slug }}?

same with the --results above

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added -${{ matrix.wolfssl_ref }} to the --results file and the artifact name.

Comment thread .github/workflows/analysis.yml Outdated
steps:
- id: pick
run: |
case "${{ github.event_name }}" in

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Apparently, the github.event_name is owned by the caller flow, and would be schedule in this case, which would not trigger this action.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems this is still not fixed

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Keys off inputs.caller_run_id now, set by nightly.yml:104, not github.event_name.

name: CMake

on:
push:

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Lots of on: push and on: pull_request added. Questions:

  1. Does this trigger 2x runs?
  2. Can we reduce this? At minimum, add draft == false

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ya it would run twice if on the same fork I added smoke test on draft and also filters for tests if that examples dir wasn't touched it wont run it on the pr.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I made it push branches: [master] only so a fork PR fires once. Added draft == false and paths filters.

Comment thread .github/workflows/lint.yml Outdated
steps:
- uses: actions/checkout@v5
- uses: ./.github/actions/apt-update
- name: Install shellcheck + cppcheck + actionlint

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

lint.sh does not actually use spellcheck

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added codespell over the repo text.

Comment thread .github/scripts/se050-run.sh Outdated
out=$("$WORK/wolfcrypt_test" 2>&1) || true
kill "$simpid" 2>/dev/null || true
printf '%s\n' "$out" | tail -40
printf '%s' "$out" | grep -qiE "Ran wolfCrypt test|Test complete|error test passed" \

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI says this grep will always print success

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Now fails on nonzero rc or missing string (se050-run.sh:97), and the demo returns the test result.

@padelsbach

Copy link
Copy Markdown
Contributor

General comment: I'd argue the build+test scripts should not live in the CI dir, and should not be shell scripts. make check for each applicable example would be more canonical and perhaps closer to the end-user environment. (And it's how Provider runs CI as well.)

Ofc, keep the ones that don't fit that model (eg Android)

Comment thread .github/workflows/analysis.yml Outdated
steps:
- id: pick
run: |
case "${{ github.event_name }}" in

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Seems this is still not fixed

Comment thread .github/scripts/lint.sh
makefail=""
for mk in $(find . -name Makefile -not -path './.git/*' -not -path '*/wolfssl/*' | sort); do
d=$(dirname "$mk")
make -n -C "$d" >/dev/null 2>&1 || makefail="$makefail $d"

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI sayas this will clone the repo into the tree, and will pollute the lint

Comment thread .github/examples-manifest.yml Outdated
path: ecc
profile: ecc
run:
- exec: [./ecc-key-decode]

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this stuff lives in the example-specific makefiles now, no need to duplicate it here.

In fact, I don't see any make check calls from .github

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

run_example.py calls make check per dir now (mode: check) and the duplicated exec/expect is gone. 46 dirs...

Comment thread .github/examples-manifest.yml Outdated
path: crypto/aes-modes
profile: crypto
setup:
- [sh, -c, "printf 'wolfssl-examples aes-modes CI input\\n' > in.txt"]

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think we need to create the inputs in the makefiles too. Eg in.txt, mem.log.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Moved input creation into the check targets, each one is self-contained now.

Comment thread pkcs7/Makefile
authEnvelopedDataKEKRI.der compressedData.der \
smime-created.p7s

check: signedData-stream

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this check is not sufficient to catch a failure. From the .c:

    printf("read %d bytes from file\n", encryptedSz);

    decryptedSz = signedData_verify(encrypted, encryptedSz,
                                    cert, certSz, key, keySz,
                                    decrypted, decryptedSz);

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Greps 'Successfully verified SignedData bundle' now, which only prints on a passing verify.

Comment thread pk/rsa/Makefile
clean:
rm -f $(TARGETS)

check: rsa-nb

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this also does not check the verify result

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a 'RSA non-block verify successful' print after the XMEMCMP and grep that.

Comment thread ecc/Makefile
./ecc-key-decode | grep -q "Success"
./ecc-params | grep -q "Gy: 32"
./ecc-sign | grep -q "Firmware Signature 9: Ret 0"
./ecc-stack | grep -q "stack used ="

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI says that ecc-stack does not return non-zero on make key failure, and this would pass

.PHONY: all clean check

check: memory_bucket_optimizer
./memory_bucket_optimizer mem.log | grep -q 'Optimization Summary:'

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI says this will always pass.

Can you review the Makefiles to make sure they check for actual failure?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Every check runs under -eo pipefail now, and fixed four grep/SIGPIPE bugs that hid real failures.

path: tpm
tier: emulated
profile: all
# emulated.yml runs it against wolfTPM's own fwTPM simulator on :2321

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

AI says this should have a run: field to actually exercise the test. Or should it be build-only?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

good finds, fixing these now

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants