Skip to content

Commit c92a922

Browse files
committed
Added uefi-library: wolfCrypt as UEFI driver
1 parent 8e47edb commit c92a922

19 files changed

Lines changed: 5610 additions & 3 deletions

.gitignore

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@
66
*.ko
77
*.obj
88
*.elf
9+
*.efi
910

1011
# Libraries
1112
*.lib
@@ -407,3 +408,6 @@ kernel/bsdkm/x86
407408
stsafe/stsafe_test
408409
stsafe/wolfssl_stsafe_test
409410
stsafe/wolfssl_stsafe_full_test
411+
412+
# uefi-library generated filesystem content
413+
uefi-library/efifs

README.md

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -381,11 +381,22 @@ details.
381381

382382
<br />
383383

384-
#### UEFI (wolfCrypt UEFI application Example)
384+
#### uefi-static (wolfCrypt UEFI application Example)
385385

386386
This directory contains an example UEFI application that runs wolfcrypt test.
387387

388-
Please see the [uefi/README.md](uefi/README.md) for further usage and
388+
Please see the [uefi-static/README.md](uefi-static/README.md) for further usage and
389+
details.
390+
391+
392+
<br />
393+
394+
#### uefi-library (wolfCrypt UEFI boot module and test app)
395+
396+
This directory contains a UEFI wolfCrypt protocol driver (`libwolfcrypt.efi`)
397+
and a companion test application (`test.efi`). Examples run on qemu.
398+
399+
Please see the [uefi-library/README.md](uefi-library/README.md) for further usage and
389400
details.
390401

391402

@@ -406,4 +417,3 @@ To generate your own cert text, see the [DER to C script](https://github.com/wol
406417

407418
Please contact wolfSSL at support@wolfssl.com with any questions, bug fixes,
408419
or suggested feature additions.
409-

uefi-library/Makefile

Lines changed: 348 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,348 @@
1+
uC = gcc
2+
LD = ld
3+
OBJCOPY = objcopy
4+
SIZE = size
5+
6+
# Path to the wolfssl source tree (sibling of wolfssl-examples by default)
7+
WOLFSSL_PATH ?= $(abspath $(CURDIR)/../../wolfssl)
8+
9+
# QEMU configuration
10+
QEMU_CPU ?= qemu64
11+
# Use a named Intel CPU model so CPUID leaf 0 reports "GenuineIntel".
12+
# wolfSSL's cpuid_flag() only sets AES-NI when the vendor is Intel or AMD;
13+
# the generic "qemu64" model reports "TCGTCGTCGTCG" and fails that check
14+
# even when +aes is passed. "Broadwell" includes AES-NI and PCLMULQDQ by
15+
# default and works with both KVM and TCG (accel=kvm:tcg falls back cleanly).
16+
QEMU_CPU_HW ?= host,migratable=off
17+
QEMU_ACCEL ?=
18+
19+
# -----------------------------------------------------------------------
20+
# x86_64 paths / flags common to all 64-bit variants
21+
# -----------------------------------------------------------------------
22+
GNU_EFI_LIB_PATH ?= /usr/lib
23+
GNU_EFI_CRT0_X64 := $(GNU_EFI_LIB_PATH)/crt0-efi-x86_64.o
24+
GNU_EFI_LSCRIPT_X64 := $(GNU_EFI_LIB_PATH)/elf_x86_64_efi.lds
25+
EFI_DRIVER_TARGET_X64 := efi-bsdrv-x86_64
26+
EFI_APP_TARGET_X64 := efi-app-x86_64
27+
28+
LIBGCC_X64 := $(shell $(CC) -print-libgcc-file-name)
29+
30+
# -----------------------------------------------------------------------
31+
# i386 paths / flags
32+
# -----------------------------------------------------------------------
33+
GNU_EFI_LIB_PATH32 ?= /usr/lib32
34+
GNU_EFI_CRT0_I32 := $(GNU_EFI_LIB_PATH32)/crt0-efi-ia32.o
35+
GNU_EFI_LSCRIPT_I32 := $(GNU_EFI_LIB_PATH32)/elf_ia32_efi.lds
36+
EFI_DRIVER_TARGET_I32 := efi-bsdrv-ia32
37+
EFI_APP_TARGET_I32 := efi-app-ia32
38+
LIBGCC_I32 := /usr/lib/gcc-cross/i686-linux-gnu/14/libgcc.a
39+
40+
# -----------------------------------------------------------------------
41+
# Common CFLAGS (base)
42+
# -----------------------------------------------------------------------
43+
CFLAGS_COMMON := \
44+
-fpic -ffreestanding -fno-stack-protector -fno-stack-check \
45+
-fshort-wchar -mno-red-zone -maccumulate-outgoing-args \
46+
-DUEFI -DGNUEFI -DWOLFSSL_USER_SETTINGS -DNEED_DYNAMIC_TYPE_FIX_UEFI \
47+
-I. -I/usr/include/efi -I/usr/include/efi/x86_64 \
48+
-I$(WOLFSSL_PATH) \
49+
-DTARGET_X86_64_EFI
50+
51+
CFLAGS_HW := $(CFLAGS_COMMON) -maes -mpclmul -DUEFI_HW_ACCEL
52+
53+
CFLAGS_NOHW := $(CFLAGS_COMMON)
54+
55+
CFLAGS_I32 := \
56+
-m32 -fpic -ffreestanding -fno-stack-protector -fno-stack-check \
57+
-fshort-wchar -mno-red-zone -maccumulate-outgoing-args \
58+
-fno-asynchronous-unwind-tables -fno-unwind-tables \
59+
-DUEFI -DGNUEFI -DWOLFSSL_USER_SETTINGS -DNEED_DYNAMIC_TYPE_FIX_UEFI \
60+
-I. -I/usr/include/efi -I/usr/include/efi/ia32 \
61+
-I$(WOLFSSL_PATH) \
62+
-DTARGET_IA32_EFI -DEFI_FUNCTION_WRAPPER -DTARGET_IA32_EFI
63+
64+
# -----------------------------------------------------------------------
65+
# wolfcrypt object list
66+
# -----------------------------------------------------------------------
67+
OBJS_WOLFCRYPT := \
68+
$(WOLFSSL_PATH)/wolfcrypt/src/aes.o \
69+
$(WOLFSSL_PATH)/wolfcrypt/src/asn.o \
70+
$(WOLFSSL_PATH)/wolfcrypt/src/coding.o \
71+
$(WOLFSSL_PATH)/wolfcrypt/src/logging.o \
72+
$(WOLFSSL_PATH)/wolfcrypt/src/cpuid.o \
73+
$(WOLFSSL_PATH)/wolfcrypt/src/memory.o \
74+
$(WOLFSSL_PATH)/wolfcrypt/src/rsa.o \
75+
$(WOLFSSL_PATH)/wolfcrypt/src/dilithium.o \
76+
$(WOLFSSL_PATH)/wolfcrypt/src/falcon.o \
77+
$(WOLFSSL_PATH)/wolfcrypt/src/dh.o \
78+
$(WOLFSSL_PATH)/wolfcrypt/src/kdf.o \
79+
$(WOLFSSL_PATH)/wolfcrypt/src/ecc.o \
80+
$(WOLFSSL_PATH)/wolfcrypt/src/misc.o \
81+
$(WOLFSSL_PATH)/wolfcrypt/src/sha.o \
82+
$(WOLFSSL_PATH)/wolfcrypt/src/sha256.o \
83+
$(WOLFSSL_PATH)/wolfcrypt/src/sha512.o \
84+
$(WOLFSSL_PATH)/wolfcrypt/src/sha3.o \
85+
$(WOLFSSL_PATH)/wolfcrypt/src/hash.o \
86+
$(WOLFSSL_PATH)/wolfcrypt/src/hmac.o \
87+
$(WOLFSSL_PATH)/wolfcrypt/src/cmac.o \
88+
$(WOLFSSL_PATH)/wolfcrypt/src/pwdbased.o \
89+
$(WOLFSSL_PATH)/wolfcrypt/src/pkcs7.o \
90+
$(WOLFSSL_PATH)/wolfcrypt/src/pkcs12.o \
91+
$(WOLFSSL_PATH)/wolfcrypt/src/wolfmath.o \
92+
$(WOLFSSL_PATH)/wolfcrypt/src/tfm.o \
93+
$(WOLFSSL_PATH)/wolfcrypt/src/wc_encrypt.o \
94+
$(WOLFSSL_PATH)/wolfcrypt/src/error.o \
95+
$(WOLFSSL_PATH)/wolfcrypt/src/random.o \
96+
$(WOLFSSL_PATH)/wolfcrypt/src/wc_port.o \
97+
$(WOLFSSL_PATH)/wolfcrypt/src/wc_mlkem.o \
98+
$(WOLFSSL_PATH)/wolfcrypt/src/wc_mlkem_poly.o \
99+
$(WOLFSSL_PATH)/wolfcrypt/src/chacha.o \
100+
$(WOLFSSL_PATH)/wolfcrypt/src/chacha20_poly1305.o \
101+
$(WOLFSSL_PATH)/wolfcrypt/src/poly1305.o \
102+
$(WOLFSSL_PATH)/wolfcrypt/src/curve25519.o \
103+
$(WOLFSSL_PATH)/wolfcrypt/src/ed25519.o \
104+
$(WOLFSSL_PATH)/wolfcrypt/src/fe_operations.o \
105+
$(WOLFSSL_PATH)/wolfcrypt/src/ge_operations.o \
106+
src/driver.o \
107+
src/utility_wolf.o
108+
109+
# AES-NI assembly objects (hw variant only)
110+
OBJS_HW := \
111+
$(WOLFSSL_PATH)/wolfcrypt/src/aes_asm.o \
112+
$(WOLFSSL_PATH)/wolfcrypt/src/aes_gcm_asm.o
113+
114+
# Test app objects
115+
OBJS_TEST := \
116+
src/test_app.o
117+
118+
# -----------------------------------------------------------------------
119+
# LDFLAGS helpers
120+
# -----------------------------------------------------------------------
121+
LDFLAGS_X64 = -shared -Bsymbolic -L$(GNU_EFI_LIB_PATH) -T$(GNU_EFI_LSCRIPT_X64)
122+
LD_GROUP_X64 = --start-group $(GNU_EFI_CRT0_X64) $(OBJS_WOLFCRYPT) --end-group -lgnuefi -lefi $(LIBGCC_X64)
123+
LD_GROUP_X64_HW = --start-group $(GNU_EFI_CRT0_X64) $(OBJS_WOLFCRYPT) $(OBJS_HW) --end-group -lgnuefi -lefi $(LIBGCC_X64)
124+
LD_GROUP_X64_TEST = --start-group $(GNU_EFI_CRT0_X64) $(OBJS_TEST) --end-group -lgnuefi -lefi $(LIBGCC_X64)
125+
126+
LDFLAGS_I32 = -shared -Bsymbolic -L$(GNU_EFI_LIB_PATH32) -m elf_i386 -T$(GNU_EFI_LSCRIPT_I32)
127+
LD_GROUP_I32 = --start-group $(GNU_EFI_CRT0_I32) $(OBJS_WOLFCRYPT) --end-group \
128+
$(GNU_EFI_LIB_PATH32)/libgnuefi.a $(GNU_EFI_LIB_PATH32)/libefi.a $(LIBGCC_I32)
129+
LD_GROUP_I32_TEST = --start-group $(GNU_EFI_CRT0_I32) $(OBJS_TEST) --end-group \
130+
$(GNU_EFI_LIB_PATH32)/libgnuefi.a $(GNU_EFI_LIB_PATH32)/libefi.a $(LIBGCC_I32)
131+
132+
EFI_EH_FRAME ?= -j .eh_frame
133+
EFI_REMOVE_EH ?=
134+
135+
# -----------------------------------------------------------------------
136+
# Main targets
137+
# -----------------------------------------------------------------------
138+
.PHONY: all clean
139+
140+
all: run-fallback-nohw
141+
142+
143+
144+
# -----------------------------------------------------------------------
145+
# Pattern rules
146+
# -----------------------------------------------------------------------
147+
%.o: %.c
148+
$(CC) $(CFLAGS) -c -o $@ $<
149+
150+
%.o: %.S
151+
$(CC) $(CFLAGS) -c -o $@ $<
152+
153+
# sha3.o must always have SHAKE128/256 enabled
154+
$(WOLFSSL_PATH)/wolfcrypt/src/sha3.o: $(WOLFSSL_PATH)/wolfcrypt/src/sha3.c
155+
$(CC) $(CFLAGS) -DWOLFSSL_SHAKE128 -DWOLFSSL_SHAKE256 \
156+
-UWOLFSSL_NO_SHAKE128 -UWOLFSSL_NO_SHAKE256 -c -o $@ $<
157+
158+
# AES-NI assembly: compile without -DWOLFSSL_USER_SETTINGS to prevent user_settings.h
159+
# from pulling in EFI C headers that the assembler cannot parse. Only define the
160+
# macros the .S file actually needs: WOLFSSL_X86_64_BUILD triggers the x86_64 path.
161+
CFLAGS_ASM := -ffreestanding -fno-stack-protector -fpic -mno-red-zone \
162+
-DWOLFSSL_X86_64_BUILD -maes -mpclmul
163+
164+
$(WOLFSSL_PATH)/wolfcrypt/src/aes_asm.o: $(WOLFSSL_PATH)/wolfcrypt/src/aes_asm.S
165+
$(CC) $(CFLAGS_ASM) -c -o $@ $<
166+
167+
$(WOLFSSL_PATH)/wolfcrypt/src/aes_gcm_asm.o: $(WOLFSSL_PATH)/wolfcrypt/src/aes_gcm_asm.S
168+
$(CC) $(CFLAGS_ASM) -c -o $@ $<
169+
170+
# -----------------------------------------------------------------------
171+
# EFI image rules
172+
# -----------------------------------------------------------------------
173+
libwolfcrypt.elf: $(OBJS_WOLFCRYPT) $(EXTRA_OBJS)
174+
$(LD) $(LDFLAGS) --defsym=EFI_SUBSYSTEM=11 -o $@ $(LD_GROUPS)
175+
176+
libwolfcrypt.efi: libwolfcrypt.elf
177+
@echo Creating $@
178+
$(OBJCOPY) -j .rodata -j .text -j .sdata -j .data \
179+
-j .dynamic -j .dynsym -j .rel \
180+
-j .rela -j .reloc $(EFI_EH_FRAME) \
181+
--target=$(EFI_DRV_TGT) --subsystem=11 $(EFI_REMOVE_EH) $^ $@
182+
@echo Size:
183+
$(SIZE) $@
184+
185+
test.elf: $(OBJS_TEST) $(EXTRA_TEST_OBJS)
186+
$(LD) $(LDFLAGS) --defsym=EFI_SUBSYSTEM=10 -o $@ $(LD_GROUPS_TEST)
187+
188+
test.efi: test.elf
189+
@echo Creating $@
190+
$(OBJCOPY) -j .rodata -j .text -j .sdata -j .data \
191+
-j .dynamic -j .dynsym -j .rel \
192+
-j .rela -j .reloc $(EFI_EH_FRAME) \
193+
--target=$(EFI_APP_TGT) --subsystem=10 $(EFI_REMOVE_EH) $^ $@
194+
@echo Size:
195+
$(SIZE) $@
196+
197+
# -----------------------------------------------------------------------
198+
# install
199+
# -----------------------------------------------------------------------
200+
install: libwolfcrypt.efi test.efi
201+
mkdir -p efifs
202+
cp libwolfcrypt.efi efifs/
203+
cp test.efi efifs/
204+
cp startup-single.nsh efifs/startup.nsh
205+
cp NvVars efifs/ 2>/dev/null || true
206+
207+
install-dual: libwolfcrypt.efi libwolfcrypt-nohw.efi test.efi
208+
mkdir -p efifs
209+
cp libwolfcrypt.efi efifs/
210+
cp libwolfcrypt-nohw.efi efifs/
211+
cp test.efi efifs/
212+
cp startup.nsh efifs/
213+
cp NvVars efifs/ 2>/dev/null || true
214+
215+
# -----------------------------------------------------------------------
216+
# lib — x86_64 with AES-NI (hw)
217+
# -----------------------------------------------------------------------
218+
.PHONY: lib
219+
lib:
220+
@$(MAKE) CFLAGS="$(CFLAGS_HW)" LDFLAGS="$(LDFLAGS_X64)" \
221+
LD_GROUPS="$(LD_GROUP_X64_HW)" LD_GROUPS_TEST="$(LD_GROUP_X64_TEST)" \
222+
EXTRA_OBJS="$(OBJS_HW)" EXTRA_TEST_OBJS="$(GNU_EFI_CRT0_X64)" \
223+
EFI_DRV_TGT="$(EFI_DRIVER_TARGET_X64)" EFI_APP_TGT="$(EFI_APP_TARGET_X64)" \
224+
libwolfcrypt.efi test.efi install
225+
226+
# -----------------------------------------------------------------------
227+
# lib-nohw — x86_64 software-only
228+
# -----------------------------------------------------------------------
229+
.PHONY: lib-nohw
230+
lib-nohw: CFLAGS = $(CFLAGS_NOHW)
231+
lib-nohw: LDFLAGS = $(LDFLAGS_X64)
232+
lib-nohw: LD_GROUPS = $(LD_GROUP_X64)
233+
lib-nohw: LD_GROUPS_TEST = $(LD_GROUP_X64_TEST)
234+
lib-nohw: EXTRA_TEST_OBJS = $(GNU_EFI_CRT0_X64)
235+
lib-nohw: EFI_DRV_TGT = $(EFI_DRIVER_TARGET_X64)
236+
lib-nohw: EFI_APP_TGT = $(EFI_APP_TARGET_X64)
237+
lib-nohw: libwolfcrypt.efi test.efi install
238+
239+
# -----------------------------------------------------------------------
240+
# lib32 — i386, software-only
241+
# -----------------------------------------------------------------------
242+
.PHONY: lib32
243+
lib32: CFLAGS = $(CFLAGS_I32)
244+
lib32: LDFLAGS = $(LDFLAGS_I32)
245+
lib32: LD_GROUPS = $(LD_GROUP_I32)
246+
lib32: LD_GROUPS_TEST = $(LD_GROUP_I32_TEST)
247+
lib32: EXTRA_TEST_OBJS =
248+
lib32: EFI_DRV_TGT = $(EFI_DRIVER_TARGET_I32)
249+
lib32: EFI_APP_TGT = $(EFI_APP_TARGET_I32)
250+
lib32: EFI_EH_FRAME =
251+
lib32: EFI_REMOVE_EH = --remove-section .eh_frame
252+
lib32: libwolfcrypt.efi test.efi install
253+
254+
# -----------------------------------------------------------------------
255+
# lib32-nohw — alias for lib32 (i386 has no hw accel)
256+
# -----------------------------------------------------------------------
257+
.PHONY: lib32-nohw
258+
lib32-nohw: lib32
259+
260+
# -----------------------------------------------------------------------
261+
# run targets
262+
# -----------------------------------------------------------------------
263+
.PHONY: run
264+
run: lib
265+
qemu-system-x86_64 -machine q35,accel=kvm -m 512 -net none -serial stdio \
266+
-display none -cpu $(QEMU_CPU_HW) \
267+
-bios /usr/share/ovmf/OVMF.fd \
268+
-drive format=raw,file=fat:rw:./efifs \
269+
-object rng-random,id=rng0,filename=/dev/urandom \
270+
-device virtio-rng-pci,rng=rng0
271+
272+
.PHONY: run-nohw
273+
run-nohw: lib-nohw
274+
qemu-system-x86_64 -machine q35,accel=kvm -m 512 -net none -serial stdio \
275+
-display none -cpu $(QEMU_CPU) \
276+
-bios /usr/share/ovmf/OVMF.fd \
277+
-drive format=raw,file=fat:rw:./efifs \
278+
-object rng-random,id=rng0,filename=/dev/urandom \
279+
-device virtio-rng-pci,rng=rng0
280+
281+
.PHONY: run32
282+
run32: lib32
283+
qemu-system-i386 -m 512 -machine q35,accel=kvm -net none -serial stdio \
284+
-display none -cpu $(QEMU_CPU_HW) \
285+
-drive if=pflash,format=raw,readonly=on,file=/usr/share/OVMF/OVMF32_CODE_4M.fd \
286+
-drive format=raw,file=fat:rw:./efifs
287+
288+
.PHONY: run32-nohw
289+
run32-nohw: lib32-nohw
290+
qemu-system-i386 -m 512 -machine q35,accel=kvm -net none -serial stdio \
291+
-display none -cpu qemu32 \
292+
-drive if=pflash,format=raw,readonly=on,file=/usr/share/OVMF/OVMF32_CODE_4M.fd \
293+
-drive format=raw,file=fat:rw:./efifs
294+
295+
# -----------------------------------------------------------------------
296+
# run-fallback-nohw
297+
# Build hw + nohw drivers, install both; run QEMU without AES-NI so the
298+
# hw driver exits EFI_UNSUPPORTED and startup.nsh loads the nohw driver.
299+
# -----------------------------------------------------------------------
300+
.PHONY: run-fallback-nohw
301+
run-fallback-nohw:
302+
@echo "=== Building hw driver (with AES-NI) ==="
303+
@$(MAKE) CFLAGS="$(CFLAGS_HW)" LDFLAGS="$(LDFLAGS_X64)" \
304+
LD_GROUPS="$(LD_GROUP_X64_HW)" LD_GROUPS_TEST="$(LD_GROUP_X64_TEST)" \
305+
EXTRA_OBJS="$(OBJS_HW)" EXTRA_TEST_OBJS="$(GNU_EFI_CRT0_X64)" \
306+
EFI_DRV_TGT="$(EFI_DRIVER_TARGET_X64)" EFI_APP_TGT="$(EFI_APP_TARGET_X64)" \
307+
libwolfcrypt.efi test.efi
308+
@echo "=== Saving hw driver ==="
309+
@cp libwolfcrypt.efi libwolfcrypt-hw-tmp.efi
310+
@echo "=== Cleaning objects ==="
311+
@$(MAKE) clean-objs
312+
@echo "=== Building nohw driver ==="
313+
@$(MAKE) CFLAGS="$(CFLAGS_NOHW)" LDFLAGS="$(LDFLAGS_X64)" \
314+
LD_GROUPS="$(LD_GROUP_X64)" LD_GROUPS_TEST="$(LD_GROUP_X64_TEST)" \
315+
EXTRA_TEST_OBJS="$(GNU_EFI_CRT0_X64)" \
316+
EFI_DRV_TGT="$(EFI_DRIVER_TARGET_X64)" EFI_APP_TGT="$(EFI_APP_TARGET_X64)" \
317+
libwolfcrypt.efi
318+
@mv libwolfcrypt.efi libwolfcrypt-nohw.efi
319+
@mv libwolfcrypt-hw-tmp.efi libwolfcrypt.efi
320+
@echo "=== Installing dual build to efifs ==="
321+
@mkdir -p efifs
322+
@cp libwolfcrypt.efi efifs/
323+
@cp libwolfcrypt-nohw.efi efifs/
324+
@cp test.efi efifs/
325+
@cp startup.nsh efifs/
326+
@cp NvVars efifs/ 2>/dev/null || true
327+
@echo "=== Running QEMU without AES-NI (fallback test) ==="
328+
qemu-system-x86_64 -m 512 -net none -serial stdio -display none \
329+
-cpu $(QEMU_CPU) \
330+
-bios /usr/share/ovmf/OVMF.fd \
331+
-drive format=raw,file=fat:rw:./efifs \
332+
-object rng-random,id=rng0,filename=/dev/urandom \
333+
-device virtio-rng-pci,rng=rng0
334+
335+
# -----------------------------------------------------------------------
336+
# clean
337+
# -----------------------------------------------------------------------
338+
.PHONY: clean
339+
clean:
340+
rm -f *.elf *.efi *.o libwolfcrypt-hw-tmp.efi libwolfcrypt-nohw.efi
341+
rm -f $(WOLFSSL_PATH)/wolfcrypt/src/*.o src/*.o
342+
343+
.PHONY: clean-objs
344+
clean-objs:
345+
rm -f $(WOLFSSL_PATH)/wolfcrypt/src/*.o src/*.o
346+
347+
.PHONY: all
348+
all: lib-nohw

uefi-library/NvVars

1.33 KB
Binary file not shown.

0 commit comments

Comments
 (0)