Skip to content
Merged
Show file tree
Hide file tree
Changes from 5 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -245,6 +245,8 @@ linuxkm/linuxkm/get_thread_size
linuxkm/linuxkm
linuxkm/src
linuxkm/patches/src
linuxkm/libwolfssl-user-build
linuxkm/linuxkm-fips-hash
*.nds

# Generated during FreeBSD kernel module build.
Expand Down
7 changes: 5 additions & 2 deletions .wolfssl_known_macro_extras
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,8 @@ CONFIG_PTHREAD_IPC
CONFIG_SCHED_INFO
CONFIG_SMP
CONFIG_SNTP_TIME_SYNC_METHOD_SMOOTH
CONFIG_STACK_GROWSUP
CONFIG_THREAD_INFO_IN_TASK
CONFIG_TIMER_TASK_STACK_DEPTH
CONFIG_TIMER_TASK_STACK_SIZE
CONFIG_TLS_STACK_WOLFSSL
Expand Down Expand Up @@ -294,6 +296,7 @@ HAVE_THREADX
HAVE_TM_TYPE
HAVE_VALIDATE_DATE
HAVE_VA_COPY
HAVE_WC_FIPS_OPTEST_CONTESTFAILURE_EXPORT
HAVE_X448
HONOR_MATH_USED_LENGTH
HSM_KEY_TYPE_HMAC_224
Expand Down Expand Up @@ -658,7 +661,7 @@ WIFI_101
WIFI_AVAILABLE
WIFI_NINA
WIN_REUSE_CRYPT_HANDLE
WOLFCRYPT_FIPS_CORE_DYNAMIC_HASH_VALUE
WOLFCRYPT_FIPS_CORE_DYNAMIC_HASH_VALUE_SUPPORT
WOLFSENTRY_H
WOLFSENTRY_NO_JSON
WOLFSSL_32BIT_MILLI_TIME
Expand Down Expand Up @@ -1061,8 +1064,8 @@ __SDCC_VERSION_MAJOR
__SDCC_VERSION_MINOR
__SDCC_VERSION_PATCH
__SIZEOF_INT128__
__SIZEOF_LONG__
__SIZEOF_LONG_LONG__
__SIZEOF_LONG__
__STDC_NO_ATOMICS__
__STDC_VERSION__
__STDC__
Expand Down
9 changes: 8 additions & 1 deletion Makefile.am
Original file line number Diff line number Diff line change
Expand Up @@ -225,14 +225,21 @@ if BUILD_LINUXKM
CFLAGS_FPU_DISABLE CFLAGS_FPU_ENABLE CFLAGS_SIMD_DISABLE CFLAGS_SIMD_ENABLE \
CFLAGS_AUTO_VECTORIZE_DISABLE CFLAGS_AUTO_VECTORIZE_ENABLE \
ASFLAGS_FPU_DISABLE_SIMD_ENABLE ASFLAGS_FPU_ENABLE_SIMD_DISABLE \
ASFLAGS_FPUSIMD_DISABLE ASFLAGS_FPUSIMD_ENABLE ENABLED_KERNEL_BENCHMARKS
ASFLAGS_FPUSIMD_DISABLE ASFLAGS_FPUSIMD_ENABLE ENABLED_KERNEL_BENCHMARKS \
FIPS_FLAVOR

module:
+$(MAKE) -C linuxkm libwolfssl.ko

module-update-fips-hash:
+$(MAKE) -C linuxkm module-update-fips-hash

module-with-matching-fips-hash:
+$(MAKE) -C linuxkm module-with-matching-fips-hash

module-with-matching-fips-hash-no-sign:
+$(MAKE) -C linuxkm module-with-matching-fips-hash-no-sign

clean_module:
+$(MAKE) -C linuxkm clean

Expand Down
34 changes: 27 additions & 7 deletions configure.ac
Original file line number Diff line number Diff line change
Expand Up @@ -131,16 +131,34 @@ then
fi

# Kernel module benchmark
ENABLED_KERNEL_BENCHMARKS=""
AC_ARG_ENABLE([kernel-benchmarks],
[AS_HELP_STRING([--enable-kernel-benchmarks],[Enable crypto benchmarking autorun at module load time for kernel module (default: disabled)])],
[ENABLED_KERNEL_BENCHMARKS=$enableval])
[ENABLED_KERNEL_BENCHMARKS=$enableval],
[ENABLED_KERNEL_BENCHMARKS="no"])
if test "$ENABLED_KERNEL_BENCHMARKS" = "yes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_KERNEL_BENCHMARKS"
fi
AC_SUBST([ENABLED_KERNEL_BENCHMARKS])

AC_ARG_ENABLE([kernel-verbose-debug],
[AS_HELP_STRING([--enable-kernel-verbose-debug],[Enable supplementary runtime debugging messages for kernel module (default: disabled)])],
[ENABLED_KERNEL_VERBOSE_DEBUG=$enableval],
[ENABLED_KERNEL_VERBOSE_DEBUG="no"])
if test "$ENABLED_KERNEL_VERBOSE_DEBUG" = "yes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_KERNEL_VERBOSE_DEBUG"
fi

AC_ARG_ENABLE([kernel-stack-debug],
[AS_HELP_STRING([--enable-kernel-stack-debug],[Enable runtime reporting of stack usage in kernel module (default: disabled)])],
[ENABLED_KERNEL_STACK_DEBUG=$enableval],
[ENABLED_KERNEL_STACK_DEBUG="no"])
if test "$ENABLED_KERNEL_STACK_DEBUG" = "yes"
then
AM_CFLAGS="$AM_CFLAGS -DWOLFSSL_KERNEL_STACK_DEBUG"
fi

# Linux Kernel Module options (more options later)
AC_ARG_ENABLE([linuxkm],
[AS_HELP_STRING([--enable-linuxkm],[Enable Linux Kernel Module (default: disabled)])],
Expand Down Expand Up @@ -415,6 +433,9 @@ AC_ARG_ENABLE([fips],
[ENABLED_FIPS=$enableval],
[ENABLED_FIPS="no"])

FIPS_FLAVOR="$ENABLED_FIPS"
AC_SUBST([FIPS_FLAVOR])

# wolfProvider Options
AC_ARG_ENABLE([wolfprovider],
[AS_HELP_STRING([--enable-wolfprovider],[Enable wolfProvider options (default: disabled)])],
Expand Down Expand Up @@ -1463,7 +1484,6 @@ then
test "$enable_pwdbased" = "" && enable_pwdbased=yes
test "$enable_aeskeywrap" = "" && enable_aeskeywrap=yes
test "$enable_x963kdf" = "" && enable_x963kdf=yes
test "$enable_scrypt" = "" && test "$enable_hmac" != "no" && enable_scrypt=yes
test "$enable_indef" = "" && enable_indef=yes
test "$enable_enckeys" = "" && enable_enckeys=yes
test "$enable_hashflags" = "" && enable_hashflags=yes
Expand All @@ -1480,11 +1500,11 @@ then
test "$enable_ssh" = "" && test "$enable_hmac" != "no" && enable_ssh=yes
test "$enable_rng_bank" = "" && enable_rng_bank=yes

# the compiler optimizer generates a weird out-of-bounds bss reference for
# find_hole() in the FP_ECC implementation.
if test "$ENABLED_LINUXKM_PIE" != yes
if test "$KERNEL_MODE_DEFAULTS" != "yes"
then
test "$enable_fpecc" = "" && test "$enable_ecc" != "no" && enable_fpecc=yes
# Scrypt is excluded from kernel module builds (unless explicitly
# enabled) because of its excessive memory requirements.
test "$enable_scrypt" = "" && test "$enable_hmac" != "no" && enable_scrypt=yes
fi

if test "x$FIPS_VERSION" != "xv1"
Expand Down
21 changes: 15 additions & 6 deletions linuxkm/Kbuild
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,11 @@ else ifeq "$(KERNEL_ARCH)" "arm"
WOLFSSL_CFLAGS += -fno-optimize-sibling-calls -Os
endif

obj-m := libwolfssl.o
ifndef LIBWOLFSSL_NAME
LIBWOLFSSL_NAME := libwolfssl
endif

obj-m := $(LIBWOLFSSL_NAME).o

WOLFSSL_OBJ_TARGETS := $(patsubst %, $(obj)/%, $(WOLFSSL_OBJ_FILES))

Expand Down Expand Up @@ -88,10 +92,10 @@ ifndef KERNEL_THREAD_STACK_SIZE
endif
MAX_STACK_FRAME_SIZE=$(shell echo $$(( $(KERNEL_THREAD_STACK_SIZE) / 4)))

libwolfssl-y := $(WOLFSSL_OBJ_FILES) linuxkm/module_hooks.o linuxkm/module_exports.o
$(LIBWOLFSSL_NAME)-y := $(WOLFSSL_OBJ_FILES) linuxkm/module_hooks.o linuxkm/module_exports.o

ifeq "$(FIPS_OPTEST)" "1"
libwolfssl-y += linuxkm/optest-140-3/linuxkm_optest_wrapper.o
$(LIBWOLFSSL_NAME)-y += linuxkm/optest-140-3/linuxkm_optest_wrapper.o
endif

WOLFSSL_CFLAGS_NO_VECTOR_INSNS := $(CFLAGS_SIMD_DISABLE) $(CFLAGS_FPU_DISABLE)
Expand Down Expand Up @@ -162,7 +166,7 @@ ifdef KERNEL_EXTRA_CFLAGS_REMOVE
ccflags-remove-y += $(KERNEL_EXTRA_CFLAGS_REMOVE)
endif

$(obj)/libwolfssl.mod.o: ccflags-y := $(PIE_SUPPORT_FLAGS)
$(obj)/$(LIBWOLFSSL_NAME).mod.o: ccflags-y := $(PIE_SUPPORT_FLAGS)
$(obj)/wolfcrypt/test/test.o: ccflags-y += -DNO_MAIN_DRIVER -DWOLFSSL_NO_OPTIONS_H
$(obj)/wolfcrypt/src/aes.o: ccflags-y := $(WOLFSSL_CFLAGS) $(WOLFSSL_CFLAGS_YES_VECTOR_INSNS) $(PIE_FLAGS) $(PIE_SUPPORT_FLAGS)
$(obj)/wolfcrypt/benchmark/benchmark.o: ccflags-y := $(WOLFSSL_CFLAGS) $(CFLAGS_FPU_ENABLE) $(CFLAGS_SIMD_ENABLE) $(PIE_SUPPORT_FLAGS) -DNO_MAIN_FUNCTION -DWOLFSSL_NO_OPTIONS_H
Expand Down Expand Up @@ -331,15 +335,19 @@ endif
# auto-generate the exported symbol list, leveraging the WOLFSSL_API visibility tags.
# exclude symbols that don't match wc_* or wolf*.
EXPORT_SYMBOL := EXPORT_SYMBOL_NS_GPL
ifndef WOLFSSL_NS
WOLFSSL_NS := WOLFSSL
endif
$(obj)/linuxkm/module_exports.c: $(src)/module_exports.c.template $(WOLFSSL_OBJ_TARGETS) $(obj)/linuxkm/module_hooks.o
@$(RENAME_PIE_TEXT_AND_DATA_SECTIONS)
@cp $< $@ || exit $$?
if [[ "$${VERSION}" -gt 6 || ("$${VERSION}" -eq 6 && "$${PATCHLEVEL}" -ge 13) ]]; then
# use ASCII octal escape to avoid syntax disruption in the awk script.
ns='\042WOLFSSL\042'
ns='\042$(WOLFSSL_NS)\042'
else
ns='WOLFSSL'
ns='$(WOLFSSL_NS)'
fi
ifndef NO_EXPORTS
$(READELF) --symbols --wide $(filter %.o,$^) |
$(AWK) '/^ *[0-9]+: / {
if ($$8 !~ /^(wc_|wolf|WOLF|TLSX_)/){next;}
Expand All @@ -348,5 +356,6 @@ $(obj)/linuxkm/module_exports.c: $(src)/module_exports.c.template $(WOLFSSL_OBJ_
}
}' >> $@ || exit $$?
echo -e "#ifndef NO_CRYPT_TEST\n$(EXPORT_SYMBOL)(wolfcrypt_test, $${ns});\n#endif" >> $@
endif

clean-files := linuxkm src wolfcrypt
95 changes: 84 additions & 11 deletions linuxkm/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,19 @@
.ONESHELL:
SHELL=bash

all: libwolfssl.ko libwolfssl.ko.signed
ifeq "$(quiet)" "silent_"
QFLAG := --quiet
else ifeq "$(V)" "1"
VFLAG := --verbose
else
QFLAG := --quiet
endif

ifndef LIBWOLFSSL_NAME
LIBWOLFSSL_NAME := libwolfssl
endif

all: $(LIBWOLFSSL_NAME).ko $(LIBWOLFSSL_NAME).ko.signed

ifndef MODULE_TOP
MODULE_TOP=$(CURDIR)
Expand Down Expand Up @@ -147,8 +159,9 @@ GENERATE_RELOC_TAB := $(AWK) ' \
n=0; \
bad_relocs=0; \
print "\#include <wolfssl/wolfcrypt/libwolfssl_sources.h>"; \
print "\#include <wolfssl/wolfcrypt/memory.h>"; \
printf("%s\n ", \
"WOLFSSL_LOCAL const struct wc_linuxkm_pie_reloc_tab_ent wc_linuxkm_pie_reloc_tab[] = { "); \
"WOLFSSL_LOCAL const struct wc_reloc_table_ent wc_linuxkm_pie_reloc_tab[] = { "); \
if ("SECTION_MAP" in ENVIRON) { \
while (getline <ENVIRON["SECTION_MAP"] > 0) \
section_map[$$1] = $$2; \
Expand Down Expand Up @@ -204,8 +217,10 @@ GENERATE_RELOC_TAB := $(AWK) ' \
print >"/dev/stderr"; \
exit(1); \
} \
printf(" { .offset = 0x%xU, .dest_segment = %s, .reloc_type = WC_%s },\n", \
strtonum("0x" gensub("^0*","",1,$$1)), \
printf(" { .offset = 0x%xU, .dest_offset = 0x%xU, .dest_addend = %+d, .dest_segment = %s, .reloc_type = WC_%s },\n", \
strtonum("0x" $$1), \
strtonum("0x" $$4), \
$$6 strtonum("0x" $$7), \
section_tag, reloc_type); \
} \
} \
Expand All @@ -214,8 +229,8 @@ GENERATE_RELOC_TAB := $(AWK) ' \
print "Found " bad_relocs " unresolvable relocations." >"/dev/stderr"; \
exit(1); \
} \
print " { .offset = ~0U, .dest_segment = WC_R_SEG_NONE, .reloc_type = WC_R_NONE } };"; \
print "WOLFSSL_LOCAL const unsigned long wc_linuxkm_pie_reloc_tab_length = sizeof wc_linuxkm_pie_reloc_tab / sizeof wc_linuxkm_pie_reloc_tab[0];"; \
print " { .offset = ~0U, .dest_offset = ~0U, .dest_addend = 0, .dest_segment = WC_R_SEG_NONE, .reloc_type = WC_R_NONE } };"; \
print "WOLFSSL_LOCAL const unsigned int wc_linuxkm_pie_reloc_tab_length = (unsigned int)(sizeof wc_linuxkm_pie_reloc_tab / sizeof wc_linuxkm_pie_reloc_tab[0]);"; \
}'

ifeq "$(V)" "1"
Expand All @@ -225,8 +240,8 @@ endif
# This rule is .PHONY because it doesn't actually build the module -- Kbuild
# does, and we always need to call Kbuild to enforce rebuild for dependencies
# and config changes.
.PHONY: libwolfssl.ko
libwolfssl.ko:
.PHONY: $(LIBWOLFSSL_NAME).ko
$(LIBWOLFSSL_NAME).ko:
@set -e
@[[ '$(V)' == 1 ]] && { echo 'MODULE_TOP = "$(MODULE_TOP)"';
echo 'SRC_TOP = "$(SRC_TOP)"';
Expand Down Expand Up @@ -303,7 +318,7 @@ else
endif

.PHONY: module-update-fips-hash
module-update-fips-hash: libwolfssl.ko
module-update-fips-hash: $(LIBWOLFSSL_NAME).ko
@set -e
@if test -z '$(FIPS_HASH)'; then echo ' $$FIPS_HASH is unset' >&2; exit 1; fi
@if [[ ! '$(FIPS_HASH)' =~ [0-9a-fA-F]{64} ]]; then echo ' $$FIPS_HASH is malformed' >&2; exit 1; fi
Expand All @@ -320,9 +335,65 @@ module-update-fips-hash: libwolfssl.ko
if [[ '$(FIPS_HASH)' == "$$current_verifyCore" ]]; then echo ' Supplied FIPS_HASH matches existing verifyCore -- no update needed.'; exit 0; fi; \
echo -n '$(FIPS_HASH)' | dd bs=1 conv=notrunc of="$<" seek=$$verifyCore_offset count=64 status=none && \
echo " FIPS verifyCore updated successfully." && \
if [[ -f libwolfssl.ko.signed ]]; then $(MAKE) -C . libwolfssl.ko.signed; fi
if [[ -f '$(LIBWOLFSSL_NAME).ko.signed' ]]; then $(MAKE) -C . '$(LIBWOLFSSL_NAME).ko.signed'; fi


# linuxkm-fips-hash implements offline (no-load) FIPS hash calculation and graft-in.
#
# libwolfssl.so is built from the same sources as the kernel module, with the
# same FIPS setting, then used with linuxkm-fips-hash to calculate and overwrite
# the hash in libwolfssl.ko. Finally, the module is [re]signed.
#
# Note that libwolfssl.so has to be built from a hierarchy of symlinks, to avoid
# depending on changes/config in the source directory. Also, aside from
# FIPS_FLAVOR, inherited configuration settings in the environment are cleansed.

libwolfssl-user-build/src/.libs/libwolfssl.so:
@set -e
@$(RM) -rf '$(MODULE_TOP)/libwolfssl-user-build'
@mkdir '$(MODULE_TOP)/libwolfssl-user-build'
@cd '$(MODULE_TOP)/libwolfssl-user-build'
@pushd '$(SRC_TOP)' >/dev/null
@echo -n 'Populating tree of symlinks...'
@readarray -d '' -t srcfiles < <(find examples src support tests testsuite wolfcrypt wolfssl configure *.in build-aux debian rpm scripts certs doc mcapi cmake linuxkm/*.[ch] \( -name options.h -o -name user_settings\* \) -prune -o \( ! -type d \) \( -name '*.[chsSi]' -o -name configure -o -name '*.in' -o -name \*.sh -o -path support/\* -o -path build-aux/\* -o -path debian/\* -o -path rpm/\* -o -path scripts/\* -o -path certs/\* -o -path doc/\* -o -path mcapi/\* -o -path cmake/\* \) -print0)
@popd >/dev/null
@for file in "$${srcfiles[@]}"; do if [[ ! -e "$$file" ]]; then mkdir -p "$$(dirname "$$file")" && cp --no-dereference --symbolic-link --no-clobber '$(SRC_TOP)'/"$$file" "$$file"; fi; done
@echo ' done.'
@echo '__attribute__ ((visibility("default"))) extern const char coreKey[];' > user_settings.h
@echo > user_settings_asm.h
@echo -n 'Configuring libwolfssl.so...'
@unset WOLFSSL_CFLAGS WOLFCRYPT_PIE_FILES ASFLAGS_FPUSIMD_ENABLE ASFLAGS_FPU_DISABLE_SIMD_ENABLE src_libwolfssl_la_OBJECTS WOLFSSL_ASFLAGS AM_CFLAGS WOLFSSL_OBJ_FILES ENABLED_LINUXKM_LKCAPI_REGISTER EXTRA_LDFLAGS CC LD
@./configure $(QFLAG) $(VFLAG) --disable-jobserver --enable-cryptonly --enable-fips="$$FIPS_FLAVOR" CFLAGS='-DWC_SYM_RELOC_TABLES_SUPPORT -DWOLFCRYPT_FIPS_CORE_DYNAMIC_HASH_VALUE -DWOLFSSL_USER_SETTINGS -DWOLFSSL_USER_SETTINGS_ASM'
@echo ' done.'
@echo -n 'Compiling and linking libwolfssl.so...'
+$(MAKE) $(QFLAG) >/dev/null
@echo ' done.'
@echo -n 'Fixing FIPS hash...'
@userhash=$$(wolfcrypt/test/testwolfcrypt 2>&1 | sed -n -E 's/^hash = (.+)$$/\1/p')
@if [[ -z "$$userhash" ]]; then echo ' FIPS hash not found!' >&2; exit 1; fi
@find wolfcrypt/src -name '*fips_test*o' -delete
+$(MAKE) $(QFLAG) EXTRA_CFLAGS=-DWOLFCRYPT_FIPS_CORE_HASH_VALUE="$$userhash"
@echo ' done.'

linuxkm-fips-hash: libwolfssl-user-build/src/.libs/libwolfssl.so linuxkm-fips-hash.c
@set -e
@echo -n 'Compiling linuxkm-fips-hash...'
# note direct invocation of cc -- we are compiling for the build host, not the target host.
@cc -Wall -Wextra -O2 -I'$(MODULE_TOP)/libwolfssl-user-build' -o linuxkm-fips-hash linuxkm/linuxkm-fips-hash.c -L '$(MODULE_TOP)/libwolfssl-user-build/src/.libs' -Wl,-rpath-link='$(MODULE_TOP)/libwolfssl-user-build/src/.libs' -Wl,-rpath='$(MODULE_TOP)/libwolfssl-user-build/src/.libs' -lwolfssl
@echo ' done.'

.PHONY: module-with-matching-fips-hash
module-with-matching-fips-hash: $(LIBWOLFSSL_NAME).ko linuxkm-fips-hash
@set -e
@./linuxkm-fips-hash-wrapper.sh "$<" $(QFLAG) $(VFLAG)
+$(MAKE) $(QFLAG) -C . '$(LIBWOLFSSL_NAME).ko.signed'

.PHONY: module-with-matching-fips-hash-no-sign
module-with-matching-fips-hash-no-sign: $(LIBWOLFSSL_NAME).ko linuxkm-fips-hash
@set -e
@./linuxkm-fips-hash-wrapper.sh "$<"

libwolfssl.ko.signed: libwolfssl.ko
$(LIBWOLFSSL_NAME).ko.signed: $(LIBWOLFSSL_NAME).ko
ifdef FORCE_NO_MODULE_SIG
@echo 'Skipping module signature operation because FORCE_NO_MODULE_SIG.'
else
Expand Down Expand Up @@ -371,6 +442,8 @@ clean:
$(RM) -rf '$(MODULE_TOP)/linuxkm'
$(RM) -rf '$(MODULE_TOP)/wolfcrypt'
$(RM) -rf '$(MODULE_TOP)/src'
$(RM) -rf '$(MODULE_TOP)/libwolfssl-user-build'
$(RM) -f '$(MODULE_TOP)/linuxkm-fips-hash'

.PHONY: check
check:
Expand Down
Loading