Skip to content

Commit e6a219a

Browse files
committed
Fixes for CI. Refactors for small stack and coding patterns. Adds SHA1 support. Copilot peer review fixes.
1 parent 992a56c commit e6a219a

File tree

14 files changed

+499
-221
lines changed

14 files changed

+499
-221
lines changed

.github/workflows/fwtpm-test.yml

Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,14 @@ jobs:
4646
wolfssl_config: --enable-wolftpm --enable-pkcallbacks --enable-keygen --disable-sha384
4747
build_only: true
4848

49+
# Build-only: fwTPM with SHA-1 disabled (verifies !NO_SHA gating
50+
# for SHA-1 PCR bank and RSA hash conversion)
51+
- name: fwtpm-no-sha1
52+
wolftpm_config: --enable-fwtpm --enable-swtpm
53+
wolfssl_config: --enable-wolftpm --enable-pkcallbacks --enable-keygen --disable-sha
54+
build_only: true
55+
extra_cflags: -DNO_SHA
56+
4957
# Build-only: fwTPM server only (no client library)
5058
- name: fwtpm-only
5159
wolftpm_config: --enable-fwtpm-only --enable-swtpm
@@ -329,3 +337,73 @@ jobs:
329337
/tmp/fwtpm_emu_build.log
330338
retention-days: 5
331339

340+
# ----------------------------------------------------------------
341+
# Valgrind memory-safety check
342+
# Runs the unit test under valgrind for three FWTPM_DECLARE_VAR
343+
# configurations (default, SMALL_STACK, NO_HEAP) so the
344+
# stack-vs-heap allocation paths are all exercised.
345+
# ----------------------------------------------------------------
346+
fwtpm-valgrind:
347+
runs-on: ubuntu-latest
348+
timeout-minutes: 30
349+
strategy:
350+
fail-fast: false
351+
matrix:
352+
include:
353+
- name: fwtpm-valgrind-default
354+
extra_cflags: ""
355+
- name: fwtpm-valgrind-smallstack
356+
extra_cflags: "-DWOLFTPM_SMALL_STACK"
357+
- name: fwtpm-valgrind-noheap
358+
extra_cflags: "-DWOLFTPM2_NO_HEAP"
359+
360+
steps:
361+
- name: Checkout wolfTPM
362+
uses: actions/checkout@v4
363+
364+
- name: Checkout wolfSSL
365+
uses: actions/checkout@v4
366+
with:
367+
repository: wolfssl/wolfssl
368+
path: wolfssl
369+
370+
- name: Install valgrind + tpm2-tools
371+
run: |
372+
sudo apt-get update
373+
sudo apt-get install -y valgrind tpm2-tools libtss2-tcti-mssim0
374+
375+
- name: Build wolfSSL
376+
working-directory: ./wolfssl
377+
run: |
378+
./autogen.sh
379+
./configure --enable-wolftpm --enable-pkcallbacks --enable-keygen \
380+
CFLAGS="-DWC_RSA_NO_PADDING -g -O1"
381+
make
382+
sudo make install
383+
sudo ldconfig
384+
385+
- name: Build wolfTPM (${{ matrix.name }})
386+
run: |
387+
./autogen.sh
388+
./configure --enable-fwtpm --enable-swtpm --enable-debug \
389+
CFLAGS="${{ matrix.extra_cflags }} -g -O1"
390+
make
391+
392+
- name: Run unit.test under valgrind
393+
run: |
394+
valgrind --error-exitcode=1 --leak-check=full \
395+
--errors-for-leak-kinds=definite \
396+
--show-leak-kinds=definite \
397+
./tests/unit.test
398+
399+
- name: Upload failure logs
400+
if: failure()
401+
uses: actions/upload-artifact@v4
402+
with:
403+
name: fwtpm-valgrind-logs-${{ matrix.name }}
404+
path: |
405+
/tmp/fwtpm_check_*.log
406+
test-suite.log
407+
tests/*.log
408+
config.log
409+
retention-days: 5

.github/workflows/sanitizer.yml

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,10 @@ jobs:
7171
7272
- name: Run tests (make check)
7373
env:
74-
WOLFSSL_PATH: /tmp/wolfssl-install
74+
# WOLFSSL_PATH must point at the wolfSSL *source tree* (with built
75+
# examples/server/server), not the install prefix — run_examples.sh
76+
# `pushd $WOLFSSL_PATH && ./examples/server/server ...` for TLS tests.
77+
WOLFSSL_PATH: ${{ github.workspace }}/wolfssl
7578
LD_LIBRARY_PATH: /tmp/wolfssl-install/lib
7679
ASAN_OPTIONS: ${{ matrix.asan_options }}
7780
UBSAN_OPTIONS: ${{ matrix.ubsan_options }}

CMakeLists.txt

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -446,9 +446,12 @@ else()
446446
endif()
447447
endif()
448448

449-
# Link wolftpm library to wolfSSL
449+
# Link wolftpm library to wolfSSL.
450+
# PRIVATE so the wolftpm_wolfssl_dep INTERFACE helper does not become part
451+
# of wolftpm's export set (it is build-tree-only). Downstream consumers of
452+
# wolftpm should `find_package(wolfssl)` themselves before find_package(wolftpm).
450453
if(BUILD_WOLFTPM_LIB)
451-
target_link_libraries(wolftpm PUBLIC wolftpm_wolfssl_dep)
454+
target_link_libraries(wolftpm PRIVATE wolftpm_wolfssl_dep)
452455
endif()
453456

454457
# fwTPM requires wolfCrypt
@@ -719,7 +722,11 @@ endif()
719722
include(GNUInstallDirs)
720723

721724
if(BUILD_WOLFTPM_LIB)
722-
install(TARGETS wolftpm wolftpm_wolfssl_dep
725+
# Note: wolftpm_wolfssl_dep is an INTERFACE helper used only at build
726+
# time to share wolfSSL include/link settings. It is intentionally NOT
727+
# installed/exported — downstream `find_package(wolftpm)` should only
728+
# see the real wolftpm target and discover wolfSSL via its own config.
729+
install(TARGETS wolftpm
723730
EXPORT wolftpm-targets
724731
LIBRARY DESTINATION lib
725732
ARCHIVE DESTINATION lib

configure.ac

Lines changed: 6 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -225,29 +225,16 @@ then
225225
AM_CFLAGS="$AM_CFLAGS -DWOLFTPM_LINUX_DEV"
226226
fi
227227

228-
# Native host defaults — auto-enable fwTPM and swTPM on Linux/BSD x86_64 / aarch64
229-
# so `make check` provides full coverage out of the box. Users can still
230-
# explicitly disable with --disable-fwtpm / --disable-swtpm.
228+
# Defaults: fwTPM and swTPM are opt-in via --enable-fwtpm / --enable-swtpm.
229+
# Auto-enabling them on Linux/BSD changed default behavior for downstream
230+
# builders (new optional dependencies, different `make check`), so keep the
231+
# safer opt-in default. CI scripts pass these flags explicitly.
231232
WOLFTPM_DEFAULT_FWTPM=no
232233
WOLFTPM_DEFAULT_SWTPM=no
233-
case $host_cpu in
234-
x86_64|amd64|aarch64)
235-
# Defensive exclusion: fwtpm_server uses POSIX sockets and is not
236-
# currently portable to Windows / Darwin. Auto-enable on Linux/BSD only.
237-
case $host_os in
238-
*mingw*|*cygwin*|*msys*|*darwin*|*win32*)
239-
;;
240-
*)
241-
WOLFTPM_DEFAULT_FWTPM=yes
242-
WOLFTPM_DEFAULT_SWTPM=yes
243-
;;
244-
esac
245-
;;
246-
esac
247234

248235
# SW TPM device Support
249236
AC_ARG_ENABLE([swtpm],
250-
[AS_HELP_STRING([--enable-swtpm],[Enable use of TPM through the SW socket driver (default: enabled on Linux x86_64/aarch64, disabled elsewhere)])],
237+
[AS_HELP_STRING([--enable-swtpm],[Enable use of TPM through the SW socket driver (default: disabled)])],
251238
[ ENABLED_SWTPM=$enableval ],
252239
[ ENABLED_SWTPM=$WOLFTPM_DEFAULT_SWTPM ]
253240
)
@@ -299,7 +286,7 @@ AC_SUBST([DISTCHECK_SWTPM_PORT_FLAG])
299286

300287
# Firmware TPM (fwTPM) - software TPM 2.0 simulator
301288
AC_ARG_ENABLE([fwtpm],
302-
[AS_HELP_STRING([--enable-fwtpm],[Enable firmware TPM (fwTPM) server (default: enabled on Linux x86_64/aarch64, disabled elsewhere)])],
289+
[AS_HELP_STRING([--enable-fwtpm],[Enable firmware TPM (fwTPM) server (default: disabled)])],
303290
[ ENABLED_FWTPM=$enableval ],
304291
[ ENABLED_FWTPM=$WOLFTPM_DEFAULT_FWTPM ]
305292
)

examples/tpm_test.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -174,7 +174,7 @@ static const byte kRsaKeyPubModulus[] = {
174174
0xAE, 0xF5, 0xFC, 0x5B, 0xE5, 0xFB, 0xA1, 0xBA, 0xD3
175175
};
176176

177-
static const word32 kRsaKeyPubExponent = 0x10001; /* {0x01, 0x00, 0x01} */
177+
static const word32 kRsaKeyPubExponent = WC_RSA_EXPONENT; /* 0x10001 */
178178

179179
static const byte kRsaKeyPrivQ[] = {
180180
0xD5, 0x38, 0x1B, 0xC3, 0x8F, 0xC5, 0x93, 0x0C, 0x47, 0x0B, 0x6F, 0x35, 0x92,

hal/tpm_io_fwtpm.c

Lines changed: 17 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -67,15 +67,30 @@ int FWTPM_TIS_ClientConnect(FWTPM_TIS_CLIENT_CTX* client)
6767
XMEMSET(client, 0, sizeof(FWTPM_TIS_CLIENT_CTX));
6868
client->shmFd = -1;
6969

70-
/* Open existing shared memory file */
71-
fd = open(FWTPM_TIS_SHM_PATH, O_RDWR | O_NOFOLLOW | O_CLOEXEC);
70+
/* Open existing shared memory file. O_NOFOLLOW and O_CLOEXEC are not
71+
* universally available across POSIX targets — guard at compile time
72+
* and fall back to fcntl(FD_CLOEXEC) for the close-on-exec semantics. */
73+
{
74+
int openFlags = O_RDWR;
75+
#ifdef O_NOFOLLOW
76+
openFlags |= O_NOFOLLOW;
77+
#endif
78+
#ifdef O_CLOEXEC
79+
openFlags |= O_CLOEXEC;
80+
#endif
81+
fd = open(FWTPM_TIS_SHM_PATH, openFlags);
82+
}
7283
if (fd < 0) {
7384
#ifdef DEBUG_WOLFTPM
7485
printf("fwTPM HAL: open(%s) failed: %d (%s)\n",
7586
FWTPM_TIS_SHM_PATH, errno, strerror(errno));
7687
#endif
7788
return TPM_RC_FAILURE;
7889
}
90+
#ifndef O_CLOEXEC
91+
/* Fallback for platforms without O_CLOEXEC */
92+
(void)fcntl(fd, F_SETFD, FD_CLOEXEC);
93+
#endif
7994

8095
/* Verify file is large enough before mapping */
8196
if (fstat(fd, &st) != 0 ||

scripts/tpm2_tools_test.sh

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1193,10 +1193,65 @@ if check_tool tpm2_certifycreation; then
11931193
-g sha256 -o "$TEST_TMPDIR/cc_sig.bin" \
11941194
--attestation "$TEST_TMPDIR/cc_attest.bin" \
11951195
-f plain -s rsassa
1196+
1197+
# Negative: tamper with the creation ticket and confirm the TPM rejects
1198+
# it with TPM_RC_TICKET (HMAC verification fails). Flip a byte in the
1199+
# middle of the ticket so headers/sizes stay valid.
1200+
cp "$TEST_TMPDIR/cc_creation.ticket" "$TEST_TMPDIR/cc_creation.ticket.bad"
1201+
# The TPMT_TK_CREATION layout starts with tag(2)+hierarchy(4); tamper
1202+
# at offset 16 which lands inside the digest body.
1203+
printf '\xAA' | dd of="$TEST_TMPDIR/cc_creation.ticket.bad" \
1204+
bs=1 count=1 seek=16 conv=notrunc 2>/dev/null
1205+
run_test_fail "certifycreation rejects tampered ticket (TPM_RC_TICKET)" \
1206+
tpm2_certifycreation -C "$TEST_TMPDIR/cc_sign.ctx" \
1207+
-c "$TEST_TMPDIR/cc_primary.ctx" \
1208+
-d "$TEST_TMPDIR/cc_creation.digest" \
1209+
-t "$TEST_TMPDIR/cc_creation.ticket.bad" \
1210+
-g sha256 -o "$TEST_TMPDIR/cc_sig_bad.bin" \
1211+
--attestation "$TEST_TMPDIR/cc_attest_bad.bin" \
1212+
-f plain -s rsassa
11961213
else
11971214
skip_test "certifycreation" "tpm2_certifycreation not available"
11981215
fi
11991216

1217+
# ----------------------------------------------------------------
1218+
hdr "Hash + Sign (TK_HASHCHECK ticket)"
1219+
# Generate a hash with ticket via TPM2_Hash, then sign the hashed digest
1220+
# using the ticket as proof the TPM produced the hash. Exercises the
1221+
# TK_HASHCHECK ticket generate→consume flow that PolicyAuthorize/Sign rely on.
1222+
flush_transient
1223+
1224+
run_test "createprimary for hash+sign" \
1225+
tpm2_createprimary -C o -c "$TEST_TMPDIR/hs_primary.ctx"
1226+
1227+
run_test "create signing key for hash+sign" \
1228+
tpm2_create -G rsa -C "$TEST_TMPDIR/hs_primary.ctx" \
1229+
-u "$TEST_TMPDIR/hs_sign.pub" -r "$TEST_TMPDIR/hs_sign.priv" \
1230+
-c "$TEST_TMPDIR/hs_sign.ctx"
1231+
1232+
echo -n "ticket-data-to-sign" > "$TEST_TMPDIR/hs_data.bin"
1233+
run_test "tpm2_hash with TK_HASHCHECK output" \
1234+
tpm2_hash -C o -g sha256 \
1235+
-o "$TEST_TMPDIR/hs_digest.bin" \
1236+
-t "$TEST_TMPDIR/hs_ticket.bin" \
1237+
"$TEST_TMPDIR/hs_data.bin"
1238+
1239+
run_test "tpm2_sign consumes TK_HASHCHECK ticket" \
1240+
tpm2_sign -c "$TEST_TMPDIR/hs_sign.ctx" \
1241+
-g sha256 -d -t "$TEST_TMPDIR/hs_ticket.bin" \
1242+
-o "$TEST_TMPDIR/hs_sig.bin" \
1243+
"$TEST_TMPDIR/hs_digest.bin"
1244+
1245+
# Negative: tamper ticket bytes; sign should reject (TPM_RC_TICKET).
1246+
cp "$TEST_TMPDIR/hs_ticket.bin" "$TEST_TMPDIR/hs_ticket.bad"
1247+
printf '\x55' | dd of="$TEST_TMPDIR/hs_ticket.bad" \
1248+
bs=1 count=1 seek=16 conv=notrunc 2>/dev/null
1249+
run_test_fail "tpm2_sign rejects tampered TK_HASHCHECK (TPM_RC_TICKET)" \
1250+
tpm2_sign -c "$TEST_TMPDIR/hs_sign.ctx" \
1251+
-g sha256 -d -t "$TEST_TMPDIR/hs_ticket.bad" \
1252+
-o "$TEST_TMPDIR/hs_sig_bad.bin" \
1253+
"$TEST_TMPDIR/hs_digest.bin"
1254+
12001255
# ----------------------------------------------------------------
12011256
hdr "Duplicate"
12021257
# Flush transient objects

0 commit comments

Comments
 (0)