From 587b608b89def24717632fd5b3e548f2cf52c675 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Mon, 22 Feb 2021 17:25:24 -0500 Subject: Fix all the places we need UNUSED on arguments. Signed-off-by: Peter Jones --- lib/print_crypto.c | 2 +- lib/simple_file.c | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) (limited to 'lib') diff --git a/lib/print_crypto.c b/lib/print_crypto.c index 1bab0a6c..39dfd2c0 100644 --- a/lib/print_crypto.c +++ b/lib/print_crypto.c @@ -15,7 +15,7 @@ #include static int -print_errors_cb(const char *str, size_t len, void *u) +print_errors_cb(const char *str, size_t len, void *u UNUSED) { console_print(L"%a", str); diff --git a/lib/simple_file.c b/lib/simple_file.c index 384b20ec..e6544709 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -66,8 +66,8 @@ simple_file_open(EFI_HANDLE image, CHAR16 *name, EFI_FILE **file, UINT64 mode) } EFI_STATUS -simple_dir_read_all_by_handle(EFI_HANDLE image, EFI_FILE *file, CHAR16* name, EFI_FILE_INFO **entries, - int *count) +simple_dir_read_all_by_handle(EFI_HANDLE image UNUSED, EFI_FILE *file, + CHAR16* name, EFI_FILE_INFO **entries, int *count) { EFI_STATUS efi_status; char buf[4096]; -- cgit v1.2.3 From 58cf755d5fd5b3d1f87a5936107a70705ccbb57b Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 25 Feb 2021 23:18:24 -0500 Subject: Add get_variable_size()/set_variable()del_variable() wrappers. This get_variable_size() implementation success in either of two cases: - EFI_SUCCESS with *lenp == 0 if the variable isn't found - EFI_SUCCESS with *lenp > 0 on success In the event of other errors, it returns them to you. There's nothing particularly interesting about the set_variable() or del_variable() implementation here. Signed-off-by: Peter Jones --- include/variables.h | 6 ++++++ lib/variables.c | 37 +++++++++++++++++++++++++++++++++++++ 2 files changed, 43 insertions(+) (limited to 'lib') diff --git a/include/variables.h b/include/variables.h index 09d97c31..31cfcb65 100644 --- a/include/variables.h +++ b/include/variables.h @@ -40,6 +40,12 @@ get_variable(const CHAR16 * const var, UINT8 **data, UINTN *len, EFI_GUID owner) EFI_STATUS get_variable_attr(const CHAR16 * const var, UINT8 **data, UINTN *len, EFI_GUID owner, UINT32 *attributes); EFI_STATUS +get_variable_size(const CHAR16 * const var, EFI_GUID owner, UINTN *lenp); +EFI_STATUS +set_variable(CHAR16 *var, EFI_GUID owner, UINT32 attributes, UINTN datasize, void *data); +EFI_STATUS +del_variable(CHAR16 *var, EFI_GUID owner); +EFI_STATUS find_in_esl(UINT8 *Data, UINTN DataSize, UINT8 *key, UINTN keylen); EFI_STATUS find_in_variable_esl(const CHAR16 * const var, EFI_GUID owner, UINT8 *key, UINTN keylen); diff --git a/lib/variables.c b/lib/variables.c index 0431d4a2..6db069ef 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -259,6 +259,43 @@ get_variable(const CHAR16 * const var, UINT8 **data, UINTN *len, EFI_GUID owner) return get_variable_attr(var, data, len, owner, NULL); } +EFI_STATUS +get_variable_size(const CHAR16 * const var, EFI_GUID owner, UINTN *lenp) +{ + UINTN len = 0; + EFI_STATUS efi_status; + + efi_status = get_variable_attr(var, NULL, &len, owner, NULL); + if (EFI_ERROR(efi_status)) { + if (efi_status == EFI_BUFFER_TOO_SMALL) { + *lenp = len; + return EFI_SUCCESS; + } else if (efi_status == EFI_NOT_FOUND) { + *lenp = 0; + return EFI_SUCCESS; + } + return efi_status; + } + /* + * who knows what this means, but... + */ + *lenp = len; + return efi_status; +} + +EFI_STATUS +set_variable(CHAR16 *var, EFI_GUID owner, UINT32 attributes, + UINTN datasize, void *data) +{ + return gRT->SetVariable(var, &owner, attributes, datasize, data); +} + +EFI_STATUS +del_variable(CHAR16 *var, EFI_GUID owner) +{ + return set_variable(var, owner, 0, 0, ""); +} + EFI_STATUS find_in_esl(UINT8 *Data, UINTN DataSize, UINT8 *key, UINTN keylen) { -- cgit v1.2.3 From dddeaf3f7dc8d30640119e999bbfabf4ce068a68 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Fri, 5 Mar 2021 17:44:23 -0500 Subject: Re-organize a bunch of CFLAGS-related makefile bits Some of our makefile bits are a mess, as you may have noticed, making changes to them difficult to review. This patch attempts to make some parts of them vaguely less of a mess, in order to facilitate review of follow-up changes. To so it: - coalesces feature flags, optimizations, -W{no-,}, -W{no-}error, include directives, and define/undefine directives into (mostly) separate groups. - exports them as appropriate so the sub-makes can use them - Makes sure we have -Wextra -Werror everywhere, but adds -Wno-foo and -Wno-error=foo directives at the appropriate places to keep the net warnings the same. - makes the arch defines in Cryptlib and Cryptlib/OpenSSL use the appropriate ones, with no attempt to make them less stupid, without changing the overall order. - coalesces the various includes, with no attempt to make them less stupid, without changing the overall order. - One giant glaring whitespace fix in Cryptlib/OpenSSL/Makefile Signed-off-by: Peter Jones --- Cryptlib/Makefile | 25 +- Cryptlib/OpenSSL/Makefile | 860 +++++++++++++++++++++++----------------------- Make.defaults | 71 ++-- Make.rules | 30 ++ Makefile | 13 +- lib/Makefile | 3 +- 6 files changed, 545 insertions(+), 457 deletions(-) (limited to 'lib') diff --git a/Cryptlib/Makefile b/Cryptlib/Makefile index 18a33b19..5bae10c9 100644 --- a/Cryptlib/Makefile +++ b/Cryptlib/Makefile @@ -1,27 +1,32 @@ -EFI_INCLUDES = -I$(TOPDIR)/Include -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol +INCLUDES = -I$(TOPDIR) -iquote $(TOPDIR) -I$(TOPDIR)/Include \ + $(EFI_INCLUDES) -I$(shell $(CC) -print-file-name=include) -CFLAGS = -ggdb $(OPTIMIZATIONS) -I$(TOPDIR) -iquote $(TOPDIR) -fno-stack-protector -fno-strict-aliasing -fpic -fshort-wchar \ - -Wall $(EFI_INCLUDES) -std=gnu89 \ - -ffreestanding -I$(shell $(CC) -print-file-name=include) +CFLAGS = $(FEATUREFLAGS) \ + $(OPTIMIZATIONS) \ + $(WARNFLAGS) \ + $(WERRFLAGS) \ + $(INCLUDES) \ + $(DEFINES) CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) ifeq ($(ARCH),x86_64) - CFLAGS += -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) \ - -m64 -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ +FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ -DNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 endif ifeq ($(ARCH),ia32) - CFLAGS += -mno-mmx -mno-sse -mno-red-zone -nostdinc \ - $(CLANG_BUGS) -m32 -DMDE_CPU_IA32 +FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +DEFINES += -DMDE_CPU_IA32 endif ifeq ($(ARCH),aarch64) - CFLAGS += -DMDE_CPU_AARCH64 +DEFINES += -DMDE_CPU_AARCH64 endif ifeq ($(ARCH),arm) - CFLAGS += -DMDE_CPU_ARM +DEFINES += -DMDE_CPU_ARM endif + LDFLAGS = -nostdlib -znocombreloc TARGET = libcryptlib.a diff --git a/Cryptlib/OpenSSL/Makefile b/Cryptlib/OpenSSL/Makefile index 9a7697cc..6a58dbaa 100644 --- a/Cryptlib/OpenSSL/Makefile +++ b/Cryptlib/OpenSSL/Makefile @@ -1,440 +1,458 @@ -EFI_INCLUDES = -I$(TOPDIR)/../Include \ - -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol \ - -I$(TOPDIR)/crypto/asn1 -I$(TOPDIR)/crypto/evp -I$(TOPDIR)/crypto/modes -I$(TOPDIR)/crypto/include +DEFINES = -DL_ENDIAN \ + -D_CRT_SECURE_NO_DEPRECATE \ + -D_CRT_NONSTDC_NO_DEPRECATE \ + -DOPENSSL_SMALL_FOOTPRINT \ + -DPEDANTIC -CFLAGS = -ggdb $(OPTIMIZATIONS) -I$(TOPDIR) -I$(TOPDIR)/.. -I$(TOPDIR)/../Include/ -I$(TOPDIR)/crypto \ - -fno-stack-protector -fno-strict-aliasing -fpic -fshort-wchar -nostdinc \ - -ffreestanding -std=gnu89 -I$(shell $(CC) -print-file-name=include) \ - -Wall $(EFI_INCLUDES) -DL_ENDIAN -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DOPENSSL_SMALL_FOOTPRINT -DPEDANTIC +INCLUDES = -I$(TOPDIR) -I$(TOPDIR)/.. -I$(TOPDIR)/../Include/ -I$(TOPDIR)/crypto \ + -I$(shell $(CC) -print-file-name=include) \ + -I$(TOPDIR)/../Include $(EFI_INCLUDES) \ + -I$(TOPDIR)/crypto/asn1 -I$(TOPDIR)/crypto/evp \ + -I$(TOPDIR)/crypto/modes -I$(TOPDIR)/crypto/include + +WERRFLAGS += -Wno-error=discarded-qualifiers \ + -Wno-error=maybe-uninitialized \ + -Wno-error=unused-function \ + -Wno-error=unused-but-set-variable + +CFLAGS = $(FEATUREFLAGS) \ + $(OPTIMIZATIONS) \ + $(WARNFLAGS) \ + $(WERRFLAGS) \ + $(INCLUDES) \ + $(DEFINES) CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) ifeq ($(ARCH),x86_64) - CFLAGS += -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) \ - -m64 -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ - -UNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 +FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) +DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ + -UNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 endif ifeq ($(ARCH),ia32) - CFLAGS += -mno-mmx -mno-sse -mno-red-zone -nostdinc \ - $(CLANG_BUGS) -m32 -DMDE_CPU_IA32 +FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +DEFINES += -DMDE_CPU_IA32 endif ifeq ($(ARCH),aarch64) - CFLAGS += -O2 -DMDE_CPU_AARCH64 +OPTIMIZATIONS += -O2 +DEFINES += -DMDE_CPU_AARCH64 endif ifeq ($(ARCH),arm) - CFLAGS += -O2 -DMDE_CPU_ARM +OPTIMIZATIONS += -O2 +DEFINES += -DMDE_CPU_ARM endif + LDFLAGS = -nostdlib -znocombreloc TARGET = libopenssl.a -OBJS = crypto/cryptlib.o \ - crypto/mem.o \ - crypto/mem_clr.o \ - crypto/mem_dbg.o \ - crypto/cversion.o \ - crypto/ex_data.o \ - crypto/cpt_err.o \ - crypto/ebcdic.o \ - crypto/uid.o \ - crypto/o_time.o \ - crypto/o_str.o \ - crypto/o_dir.o \ - crypto/o_fips.o \ - crypto/o_init.o \ - crypto/fips_ers.o \ - crypto/md5/md5_dgst.o \ - crypto/md5/md5_one.o \ - crypto/sha/sha_dgst.o \ - crypto/sha/sha1dgst.o \ - crypto/sha/sha_one.o \ - crypto/sha/sha1_one.o \ - crypto/sha/sha256.o \ - crypto/sha/sha512.o \ - crypto/hmac/hmac.o \ - crypto/hmac/hm_ameth.o \ - crypto/hmac/hm_pmeth.o \ - crypto/rc4/rc4_enc.o \ - crypto/rc4/rc4_skey.o \ - crypto/rc4/rc4_utl.o \ - crypto/aes/aes_misc.o \ - crypto/aes/aes_ecb.o \ - crypto/aes/aes_cfb.o \ - crypto/aes/aes_ofb.o \ - crypto/aes/aes_ctr.o \ - crypto/aes/aes_ige.o \ - crypto/aes/aes_wrap.o \ - crypto/aes/aes_core.o \ - crypto/aes/aes_cbc.o \ - crypto/modes/cbc128.o \ - crypto/modes/ctr128.o \ - crypto/modes/cts128.o \ - crypto/modes/cfb128.o \ - crypto/modes/ofb128.o \ - crypto/modes/gcm128.o \ - crypto/modes/ccm128.o \ - crypto/modes/xts128.o \ - crypto/modes/wrap128.o \ - crypto/bn/bn_add.o \ - crypto/bn/bn_div.o \ - crypto/bn/bn_exp.o \ - crypto/bn/bn_lib.o \ - crypto/bn/bn_ctx.o \ - crypto/bn/bn_mul.o \ - crypto/bn/bn_mod.o \ - crypto/bn/bn_print.o \ - crypto/bn/bn_rand.o \ - crypto/bn/bn_shift.o \ - crypto/bn/bn_word.o \ - crypto/bn/bn_blind.o \ - crypto/bn/bn_kron.o \ - crypto/bn/bn_sqrt.o \ - crypto/bn/bn_gcd.o \ - crypto/bn/bn_prime.o \ - crypto/bn/bn_err.o \ - crypto/bn/bn_sqr.o \ - crypto/bn/bn_asm.o \ - crypto/bn/bn_recp.o \ - crypto/bn/bn_mont.o \ - crypto/bn/bn_mpi.o \ - crypto/bn/bn_exp2.o \ - crypto/bn/bn_gf2m.o \ - crypto/bn/bn_nist.o \ - crypto/bn/bn_depr.o \ - crypto/bn/bn_x931p.o \ - crypto/bn/bn_const.o \ - crypto/rsa/rsa_eay.o \ - crypto/rsa/rsa_gen.o \ - crypto/rsa/rsa_lib.o \ - crypto/rsa/rsa_sign.o \ - crypto/rsa/rsa_saos.o \ - crypto/rsa/rsa_err.o \ - crypto/rsa/rsa_pk1.o \ - crypto/rsa/rsa_ssl.o \ - crypto/rsa/rsa_none.o \ - crypto/rsa/rsa_oaep.o \ - crypto/rsa/rsa_chk.o \ - crypto/rsa/rsa_null.o \ - crypto/rsa/rsa_pss.o \ - crypto/rsa/rsa_x931.o \ - crypto/rsa/rsa_asn1.o \ - crypto/rsa/rsa_depr.o \ - crypto/rsa/rsa_ameth.o \ - crypto/rsa/rsa_prn.o \ - crypto/rsa/rsa_pmeth.o \ - crypto/rsa/rsa_crpt.o \ - crypto/dso/dso_dl.o \ - crypto/dso/dso_dlfcn.o \ - crypto/dso/dso_err.o \ - crypto/dso/dso_lib.o \ - crypto/dso/dso_null.o \ - crypto/dso/dso_openssl.o \ - crypto/dso/dso_win32.o \ - crypto/dso/dso_vms.o \ - crypto/dso/dso_beos.o \ - crypto/dh/dh_asn1.o \ - crypto/dh/dh_gen.o \ - crypto/dh/dh_key.o \ - crypto/dh/dh_lib.o \ - crypto/dh/dh_check.o \ - crypto/dh/dh_err.o \ - crypto/dh/dh_depr.o \ - crypto/dh/dh_ameth.o \ - crypto/dh/dh_pmeth.o \ - crypto/dh/dh_prn.o \ - crypto/dh/dh_rfc5114.o \ - crypto/buffer/buffer.o \ - crypto/buffer/buf_str.o \ - crypto/buffer/buf_err.o \ - crypto/bio/bio_lib.o \ - crypto/bio/bio_cb.o \ - crypto/bio/bio_err.o \ - crypto/bio/bss_mem.o \ - crypto/bio/bss_null.o \ - crypto/bio/bss_fd.o \ - crypto/bio/bss_file.o \ - crypto/bio/bss_sock.o \ - crypto/bio/bss_conn.o \ - crypto/bio/bf_null.o \ - crypto/bio/bf_buff.o \ - crypto/bio/b_dump.o \ - crypto/bio/b_print.o \ - crypto/bio/b_sock.o \ - crypto/bio/bss_acpt.o \ - crypto/bio/bf_nbio.o \ - crypto/bio/bss_log.o \ - crypto/bio/bss_bio.o \ - crypto/bio/bss_dgram.o \ - crypto/stack/stack.o \ - crypto/lhash/lhash.o \ - crypto/lhash/lh_stats.o \ - crypto/rand/md_rand.o \ - crypto/rand/randfile.o \ - crypto/rand/rand_lib.o \ - crypto/rand/rand_err.o \ - crypto/rand/rand_unix.o \ - crypto/err/err.o \ - crypto/err/err_all.o \ - crypto/err/err_prn.o \ - crypto/objects/o_names.o \ - crypto/objects/obj_dat.o \ - crypto/objects/obj_lib.o \ - crypto/objects/obj_err.o \ - crypto/objects/obj_xref.o \ - crypto/evp/encode.o \ - crypto/evp/digest.o \ - crypto/evp/evp_enc.o \ - crypto/evp/evp_key.o \ - crypto/evp/evp_acnf.o \ - crypto/evp/evp_cnf.o \ - crypto/evp/e_des.o \ - crypto/evp/e_bf.o \ - crypto/evp/e_idea.o \ - crypto/evp/e_des3.o \ - crypto/evp/e_camellia.o \ - crypto/evp/e_rc4.o \ - crypto/evp/e_aes.o \ - crypto/evp/names.o \ - crypto/evp/e_seed.o \ - crypto/evp/e_xcbc_d.o \ - crypto/evp/e_rc2.o \ - crypto/evp/e_cast.o \ - crypto/evp/e_rc5.o \ - crypto/evp/m_null.o \ - crypto/evp/m_md2.o \ - crypto/evp/m_md4.o \ - crypto/evp/m_md5.o \ - crypto/evp/m_sha.o \ - crypto/evp/m_sha1.o \ - crypto/evp/m_wp.o \ - crypto/evp/m_dss.o \ - crypto/evp/m_dss1.o \ - crypto/evp/m_mdc2.o \ - crypto/evp/m_ripemd.o \ - crypto/evp/m_ecdsa.o \ - crypto/evp/p_open.o \ - crypto/evp/p_seal.o \ - crypto/evp/p_sign.o \ - crypto/evp/p_verify.o \ - crypto/evp/p_lib.o \ - crypto/evp/p_enc.o \ - crypto/evp/p_dec.o \ - crypto/evp/bio_md.o \ - crypto/evp/bio_b64.o \ - crypto/evp/bio_enc.o \ - crypto/evp/evp_err.o \ - crypto/evp/e_null.o \ - crypto/evp/c_all.o \ - crypto/evp/c_allc.o \ - crypto/evp/c_alld.o \ - crypto/evp/evp_lib.o \ - crypto/evp/bio_ok.o \ - crypto/evp/evp_pkey.o \ - crypto/evp/evp_pbe.o \ - crypto/evp/p5_crpt.o \ - crypto/evp/p5_crpt2.o \ - crypto/evp/e_old.o \ - crypto/evp/pmeth_lib.o \ - crypto/evp/pmeth_fn.o \ - crypto/evp/pmeth_gn.o \ - crypto/evp/m_sigver.o \ - crypto/evp/e_aes_cbc_hmac_sha1.o \ - crypto/evp/e_aes_cbc_hmac_sha256.o \ - crypto/evp/e_rc4_hmac_md5.o \ - crypto/asn1/a_object.o \ - crypto/asn1/a_bitstr.o \ - crypto/asn1/a_utctm.o \ - crypto/asn1/a_gentm.o \ - crypto/asn1/a_time.o \ - crypto/asn1/a_int.o \ - crypto/asn1/a_octet.o \ - crypto/asn1/a_print.o \ - crypto/asn1/a_type.o \ - crypto/asn1/a_set.o \ - crypto/asn1/a_dup.o \ - crypto/asn1/a_d2i_fp.o \ - crypto/asn1/a_i2d_fp.o \ - crypto/asn1/a_enum.o \ - crypto/asn1/a_utf8.o \ - crypto/asn1/a_sign.o \ - crypto/asn1/a_digest.o \ - crypto/asn1/a_verify.o \ - crypto/asn1/a_mbstr.o \ - crypto/asn1/a_strex.o \ - crypto/asn1/x_algor.o \ - crypto/asn1/x_val.o \ - crypto/asn1/x_pubkey.o \ - crypto/asn1/x_sig.o \ - crypto/asn1/x_req.o \ - crypto/asn1/x_attrib.o \ - crypto/asn1/x_bignum.o \ - crypto/asn1/x_long.o \ - crypto/asn1/x_name.o \ - crypto/asn1/x_x509.o \ - crypto/asn1/x_x509a.o \ - crypto/asn1/x_crl.o \ - crypto/asn1/x_info.o \ - crypto/asn1/x_spki.o \ - crypto/asn1/nsseq.o \ - crypto/asn1/x_nx509.o \ - crypto/asn1/d2i_pu.o \ - crypto/asn1/d2i_pr.o \ - crypto/asn1/i2d_pu.o \ - crypto/asn1/i2d_pr.o \ - crypto/asn1/t_req.o \ - crypto/asn1/t_x509.o \ - crypto/asn1/t_x509a.o \ - crypto/asn1/t_crl.o \ - crypto/asn1/t_pkey.o \ - crypto/asn1/t_spki.o \ - crypto/asn1/t_bitst.o \ - crypto/asn1/tasn_new.o \ - crypto/asn1/tasn_fre.o \ - crypto/asn1/tasn_enc.o \ - crypto/asn1/tasn_dec.o \ - crypto/asn1/tasn_utl.o \ - crypto/asn1/tasn_typ.o \ - crypto/asn1/tasn_prn.o \ - crypto/asn1/ameth_lib.o \ - crypto/asn1/f_int.o \ - crypto/asn1/f_string.o \ - crypto/asn1/n_pkey.o \ - crypto/asn1/f_enum.o \ - crypto/asn1/x_pkey.o \ - crypto/asn1/a_bool.o \ - crypto/asn1/x_exten.o \ - crypto/asn1/bio_asn1.o \ - crypto/asn1/bio_ndef.o \ - crypto/asn1/asn_mime.o \ - crypto/asn1/asn1_gen.o \ - crypto/asn1/asn1_par.o \ - crypto/asn1/asn1_lib.o \ - crypto/asn1/asn1_err.o \ - crypto/asn1/a_bytes.o \ - crypto/asn1/a_strnid.o \ - crypto/asn1/evp_asn1.o \ - crypto/asn1/asn_pack.o \ - crypto/asn1/p5_pbe.o \ - crypto/asn1/p5_pbev2.o \ - crypto/asn1/p8_pkey.o \ - crypto/asn1/asn_moid.o \ - crypto/pem/pem_sign.o \ - crypto/pem/pem_seal.o \ - crypto/pem/pem_info.o \ - crypto/pem/pem_lib.o \ - crypto/pem/pem_all.o \ - crypto/pem/pem_err.o \ - crypto/pem/pem_x509.o \ - crypto/pem/pem_xaux.o \ - crypto/pem/pem_oth.o \ - crypto/pem/pem_pk8.o \ - crypto/pem/pem_pkey.o \ - crypto/pem/pvkfmt.o \ - crypto/x509/x509_def.o \ - crypto/x509/x509_d2.o \ - crypto/x509/x509_r2x.o \ - crypto/x509/x509_cmp.o \ - crypto/x509/x509_obj.o \ - crypto/x509/x509_req.o \ - crypto/x509/x509spki.o \ - crypto/x509/x509_vfy.o \ - crypto/x509/x509_set.o \ - crypto/x509/x509cset.o \ - crypto/x509/x509rset.o \ - crypto/x509/x509_err.o \ - crypto/x509/x509name.o \ - crypto/x509/x509_v3.o \ - crypto/x509/x509_ext.o \ - crypto/x509/x509_att.o \ - crypto/x509/x509type.o \ - crypto/x509/x509_lu.o \ - crypto/x509/x_all.o \ - crypto/x509/x509_txt.o \ - crypto/x509/x509_trs.o \ - crypto/x509/x509_vpm.o \ - crypto/x509v3/v3_bcons.o \ - crypto/x509v3/v3_bitst.o \ - crypto/x509v3/v3_conf.o \ - crypto/x509v3/v3_extku.o \ - crypto/x509v3/v3_ia5.o \ - crypto/x509v3/v3_lib.o \ - crypto/x509v3/v3_prn.o \ - crypto/x509v3/v3_utl.o \ - crypto/x509v3/v3err.o \ - crypto/x509v3/v3_genn.o \ - crypto/x509v3/v3_alt.o \ - crypto/x509v3/v3_skey.o \ - crypto/x509v3/v3_akey.o \ - crypto/x509v3/v3_pku.o \ - crypto/x509v3/v3_int.o \ - crypto/x509v3/v3_enum.o \ - crypto/x509v3/v3_sxnet.o \ - crypto/x509v3/v3_cpols.o \ - crypto/x509v3/v3_crld.o \ - crypto/x509v3/v3_purp.o \ - crypto/x509v3/v3_info.o \ - crypto/x509v3/v3_ocsp.o \ - crypto/x509v3/v3_akeya.o \ - crypto/x509v3/v3_pmaps.o \ - crypto/x509v3/v3_pcons.o \ - crypto/x509v3/v3_ncons.o \ - crypto/x509v3/v3_pcia.o \ - crypto/x509v3/v3_pci.o \ - crypto/x509v3/pcy_cache.o \ - crypto/x509v3/pcy_node.o \ - crypto/x509v3/pcy_data.o \ - crypto/x509v3/pcy_map.o \ - crypto/x509v3/pcy_tree.o \ - crypto/x509v3/pcy_lib.o \ - crypto/x509v3/v3_asid.o \ - crypto/x509v3/v3_addr.o \ - crypto/conf/conf_err.o \ - crypto/conf/conf_lib.o \ - crypto/conf/conf_api.o \ - crypto/conf/conf_def.o \ - crypto/conf/conf_mod.o \ - crypto/conf/conf_mall.o \ - crypto/conf/conf_sap.o \ - crypto/txt_db/txt_db.o \ - crypto/pkcs7/pk7_asn1.o \ - crypto/pkcs7/pk7_lib.o \ - crypto/pkcs7/pkcs7err.o \ - crypto/pkcs7/pk7_doit.o \ - crypto/pkcs7/pk7_smime.o \ - crypto/pkcs7/pk7_attr.o \ - crypto/pkcs7/pk7_mime.o \ - crypto/pkcs7/bio_pk7.o \ - crypto/pkcs12/p12_add.o \ - crypto/pkcs12/p12_asn.o \ - crypto/pkcs12/p12_attr.o \ - crypto/pkcs12/p12_crpt.o \ - crypto/pkcs12/p12_crt.o \ - crypto/pkcs12/p12_decr.o \ - crypto/pkcs12/p12_init.o \ - crypto/pkcs12/p12_key.o \ - crypto/pkcs12/p12_kiss.o \ - crypto/pkcs12/p12_mutl.o \ - crypto/pkcs12/p12_utl.o \ - crypto/pkcs12/p12_npas.o \ - crypto/pkcs12/pk12err.o \ - crypto/pkcs12/p12_p8d.o \ - crypto/pkcs12/p12_p8e.o \ - crypto/comp/comp_lib.o \ - crypto/comp/comp_err.o \ - crypto/comp/c_rle.o \ - crypto/comp/c_zlib.o \ - crypto/ocsp/ocsp_asn.o \ - crypto/ocsp/ocsp_ext.o \ - crypto/ocsp/ocsp_ht.o \ - crypto/ocsp/ocsp_lib.o \ - crypto/ocsp/ocsp_cl.o \ - crypto/ocsp/ocsp_srv.o \ - crypto/ocsp/ocsp_prn.o \ - crypto/ocsp/ocsp_vfy.o \ - crypto/ocsp/ocsp_err.o \ - crypto/cmac/cmac.o \ - crypto/cmac/cm_ameth.o \ - crypto/cmac/cm_pmeth.o \ +OBJS = crypto/cryptlib.o \ + crypto/mem.o \ + crypto/mem_clr.o \ + crypto/mem_dbg.o \ + crypto/cversion.o \ + crypto/ex_data.o \ + crypto/cpt_err.o \ + crypto/ebcdic.o \ + crypto/uid.o \ + crypto/o_time.o \ + crypto/o_str.o \ + crypto/o_dir.o \ + crypto/o_fips.o \ + crypto/o_init.o \ + crypto/fips_ers.o \ + crypto/md5/md5_dgst.o \ + crypto/md5/md5_one.o \ + crypto/sha/sha_dgst.o \ + crypto/sha/sha1dgst.o \ + crypto/sha/sha_one.o \ + crypto/sha/sha1_one.o \ + crypto/sha/sha256.o \ + crypto/sha/sha512.o \ + crypto/hmac/hmac.o \ + crypto/hmac/hm_ameth.o \ + crypto/hmac/hm_pmeth.o \ + crypto/rc4/rc4_enc.o \ + crypto/rc4/rc4_skey.o \ + crypto/rc4/rc4_utl.o \ + crypto/aes/aes_misc.o \ + crypto/aes/aes_ecb.o \ + crypto/aes/aes_cfb.o \ + crypto/aes/aes_ofb.o \ + crypto/aes/aes_ctr.o \ + crypto/aes/aes_ige.o \ + crypto/aes/aes_wrap.o \ + crypto/aes/aes_core.o \ + crypto/aes/aes_cbc.o \ + crypto/modes/cbc128.o \ + crypto/modes/ctr128.o \ + crypto/modes/cts128.o \ + crypto/modes/cfb128.o \ + crypto/modes/ofb128.o \ + crypto/modes/gcm128.o \ + crypto/modes/ccm128.o \ + crypto/modes/xts128.o \ + crypto/modes/wrap128.o \ + crypto/bn/bn_add.o \ + crypto/bn/bn_div.o \ + crypto/bn/bn_exp.o \ + crypto/bn/bn_lib.o \ + crypto/bn/bn_ctx.o \ + crypto/bn/bn_mul.o \ + crypto/bn/bn_mod.o \ + crypto/bn/bn_print.o \ + crypto/bn/bn_rand.o \ + crypto/bn/bn_shift.o \ + crypto/bn/bn_word.o \ + crypto/bn/bn_blind.o \ + crypto/bn/bn_kron.o \ + crypto/bn/bn_sqrt.o \ + crypto/bn/bn_gcd.o \ + crypto/bn/bn_prime.o \ + crypto/bn/bn_err.o \ + crypto/bn/bn_sqr.o \ + crypto/bn/bn_asm.o \ + crypto/bn/bn_recp.o \ + crypto/bn/bn_mont.o \ + crypto/bn/bn_mpi.o \ + crypto/bn/bn_exp2.o \ + crypto/bn/bn_gf2m.o \ + crypto/bn/bn_nist.o \ + crypto/bn/bn_depr.o \ + crypto/bn/bn_x931p.o \ + crypto/bn/bn_const.o \ + crypto/rsa/rsa_eay.o \ + crypto/rsa/rsa_gen.o \ + crypto/rsa/rsa_lib.o \ + crypto/rsa/rsa_sign.o \ + crypto/rsa/rsa_saos.o \ + crypto/rsa/rsa_err.o \ + crypto/rsa/rsa_pk1.o \ + crypto/rsa/rsa_ssl.o \ + crypto/rsa/rsa_none.o \ + crypto/rsa/rsa_oaep.o \ + crypto/rsa/rsa_chk.o \ + crypto/rsa/rsa_null.o \ + crypto/rsa/rsa_pss.o \ + crypto/rsa/rsa_x931.o \ + crypto/rsa/rsa_asn1.o \ + crypto/rsa/rsa_depr.o \ + crypto/rsa/rsa_ameth.o \ + crypto/rsa/rsa_prn.o \ + crypto/rsa/rsa_pmeth.o \ + crypto/rsa/rsa_crpt.o \ + crypto/dso/dso_dl.o \ + crypto/dso/dso_dlfcn.o \ + crypto/dso/dso_err.o \ + crypto/dso/dso_lib.o \ + crypto/dso/dso_null.o \ + crypto/dso/dso_openssl.o \ + crypto/dso/dso_win32.o \ + crypto/dso/dso_vms.o \ + crypto/dso/dso_beos.o \ + crypto/dh/dh_asn1.o \ + crypto/dh/dh_gen.o \ + crypto/dh/dh_key.o \ + crypto/dh/dh_lib.o \ + crypto/dh/dh_check.o \ + crypto/dh/dh_err.o \ + crypto/dh/dh_depr.o \ + crypto/dh/dh_ameth.o \ + crypto/dh/dh_pmeth.o \ + crypto/dh/dh_prn.o \ + crypto/dh/dh_rfc5114.o \ + crypto/buffer/buffer.o \ + crypto/buffer/buf_str.o \ + crypto/buffer/buf_err.o \ + crypto/bio/bio_lib.o \ + crypto/bio/bio_cb.o \ + crypto/bio/bio_err.o \ + crypto/bio/bss_mem.o \ + crypto/bio/bss_null.o \ + crypto/bio/bss_fd.o \ + crypto/bio/bss_file.o \ + crypto/bio/bss_sock.o \ + crypto/bio/bss_conn.o \ + crypto/bio/bf_null.o \ + crypto/bio/bf_buff.o \ + crypto/bio/b_dump.o \ + crypto/bio/b_print.o \ + crypto/bio/b_sock.o \ + crypto/bio/bss_acpt.o \ + crypto/bio/bf_nbio.o \ + crypto/bio/bss_log.o \ + crypto/bio/bss_bio.o \ + crypto/bio/bss_dgram.o \ + crypto/stack/stack.o \ + crypto/lhash/lhash.o \ + crypto/lhash/lh_stats.o \ + crypto/rand/md_rand.o \ + crypto/rand/randfile.o \ + crypto/rand/rand_lib.o \ + crypto/rand/rand_err.o \ + crypto/rand/rand_unix.o \ + crypto/err/err.o \ + crypto/err/err_all.o \ + crypto/err/err_prn.o \ + crypto/objects/o_names.o \ + crypto/objects/obj_dat.o \ + crypto/objects/obj_lib.o \ + crypto/objects/obj_err.o \ + crypto/objects/obj_xref.o \ + crypto/evp/encode.o \ + crypto/evp/digest.o \ + crypto/evp/evp_enc.o \ + crypto/evp/evp_key.o \ + crypto/evp/evp_acnf.o \ + crypto/evp/evp_cnf.o \ + crypto/evp/e_des.o \ + crypto/evp/e_bf.o \ + crypto/evp/e_idea.o \ + crypto/evp/e_des3.o \ + crypto/evp/e_camellia.o \ + crypto/evp/e_rc4.o \ + crypto/evp/e_aes.o \ + crypto/evp/names.o \ + crypto/evp/e_seed.o \ + crypto/evp/e_xcbc_d.o \ + crypto/evp/e_rc2.o \ + crypto/evp/e_cast.o \ + crypto/evp/e_rc5.o \ + crypto/evp/m_null.o \ + crypto/evp/m_md2.o \ + crypto/evp/m_md4.o \ + crypto/evp/m_md5.o \ + crypto/evp/m_sha.o \ + crypto/evp/m_sha1.o \ + crypto/evp/m_wp.o \ + crypto/evp/m_dss.o \ + crypto/evp/m_dss1.o \ + crypto/evp/m_mdc2.o \ + crypto/evp/m_ripemd.o \ + crypto/evp/m_ecdsa.o \ + crypto/evp/p_open.o \ + crypto/evp/p_seal.o \ + crypto/evp/p_sign.o \ + crypto/evp/p_verify.o \ + crypto/evp/p_lib.o \ + crypto/evp/p_enc.o \ + crypto/evp/p_dec.o \ + crypto/evp/bio_md.o \ + crypto/evp/bio_b64.o \ + crypto/evp/bio_enc.o \ + crypto/evp/evp_err.o \ + crypto/evp/e_null.o \ + crypto/evp/c_all.o \ + crypto/evp/c_allc.o \ + crypto/evp/c_alld.o \ + crypto/evp/evp_lib.o \ + crypto/evp/bio_ok.o \ + crypto/evp/evp_pkey.o \ + crypto/evp/evp_pbe.o \ + crypto/evp/p5_crpt.o \ + crypto/evp/p5_crpt2.o \ + crypto/evp/e_old.o \ + crypto/evp/pmeth_lib.o \ + crypto/evp/pmeth_fn.o \ + crypto/evp/pmeth_gn.o \ + crypto/evp/m_sigver.o \ + crypto/evp/e_aes_cbc_hmac_sha1.o \ + crypto/evp/e_aes_cbc_hmac_sha256.o \ + crypto/evp/e_rc4_hmac_md5.o \ + crypto/asn1/a_object.o \ + crypto/asn1/a_bitstr.o \ + crypto/asn1/a_utctm.o \ + crypto/asn1/a_gentm.o \ + crypto/asn1/a_time.o \ + crypto/asn1/a_int.o \ + crypto/asn1/a_octet.o \ + crypto/asn1/a_print.o \ + crypto/asn1/a_type.o \ + crypto/asn1/a_set.o \ + crypto/asn1/a_dup.o \ + crypto/asn1/a_d2i_fp.o \ + crypto/asn1/a_i2d_fp.o \ + crypto/asn1/a_enum.o \ + crypto/asn1/a_utf8.o \ + crypto/asn1/a_sign.o \ + crypto/asn1/a_digest.o \ + crypto/asn1/a_verify.o \ + crypto/asn1/a_mbstr.o \ + crypto/asn1/a_strex.o \ + crypto/asn1/x_algor.o \ + crypto/asn1/x_val.o \ + crypto/asn1/x_pubkey.o \ + crypto/asn1/x_sig.o \ + crypto/asn1/x_req.o \ + crypto/asn1/x_attrib.o \ + crypto/asn1/x_bignum.o \ + crypto/asn1/x_long.o \ + crypto/asn1/x_name.o \ + crypto/asn1/x_x509.o \ + crypto/asn1/x_x509a.o \ + crypto/asn1/x_crl.o \ + crypto/asn1/x_info.o \ + crypto/asn1/x_spki.o \ + crypto/asn1/nsseq.o \ + crypto/asn1/x_nx509.o \ + crypto/asn1/d2i_pu.o \ + crypto/asn1/d2i_pr.o \ + crypto/asn1/i2d_pu.o \ + crypto/asn1/i2d_pr.o \ + crypto/asn1/t_req.o \ + crypto/asn1/t_x509.o \ + crypto/asn1/t_x509a.o \ + crypto/asn1/t_crl.o \ + crypto/asn1/t_pkey.o \ + crypto/asn1/t_spki.o \ + crypto/asn1/t_bitst.o \ + crypto/asn1/tasn_new.o \ + crypto/asn1/tasn_fre.o \ + crypto/asn1/tasn_enc.o \ + crypto/asn1/tasn_dec.o \ + crypto/asn1/tasn_utl.o \ + crypto/asn1/tasn_typ.o \ + crypto/asn1/tasn_prn.o \ + crypto/asn1/ameth_lib.o \ + crypto/asn1/f_int.o \ + crypto/asn1/f_string.o \ + crypto/asn1/n_pkey.o \ + crypto/asn1/f_enum.o \ + crypto/asn1/x_pkey.o \ + crypto/asn1/a_bool.o \ + crypto/asn1/x_exten.o \ + crypto/asn1/bio_asn1.o \ + crypto/asn1/bio_ndef.o \ + crypto/asn1/asn_mime.o \ + crypto/asn1/asn1_gen.o \ + crypto/asn1/asn1_par.o \ + crypto/asn1/asn1_lib.o \ + crypto/asn1/asn1_err.o \ + crypto/asn1/a_bytes.o \ + crypto/asn1/a_strnid.o \ + crypto/asn1/evp_asn1.o \ + crypto/asn1/asn_pack.o \ + crypto/asn1/p5_pbe.o \ + crypto/asn1/p5_pbev2.o \ + crypto/asn1/p8_pkey.o \ + crypto/asn1/asn_moid.o \ + crypto/pem/pem_sign.o \ + crypto/pem/pem_seal.o \ + crypto/pem/pem_info.o \ + crypto/pem/pem_lib.o \ + crypto/pem/pem_all.o \ + crypto/pem/pem_err.o \ + crypto/pem/pem_x509.o \ + crypto/pem/pem_xaux.o \ + crypto/pem/pem_oth.o \ + crypto/pem/pem_pk8.o \ + crypto/pem/pem_pkey.o \ + crypto/pem/pvkfmt.o \ + crypto/x509/x509_def.o \ + crypto/x509/x509_d2.o \ + crypto/x509/x509_r2x.o \ + crypto/x509/x509_cmp.o \ + crypto/x509/x509_obj.o \ + crypto/x509/x509_req.o \ + crypto/x509/x509spki.o \ + crypto/x509/x509_vfy.o \ + crypto/x509/x509_set.o \ + crypto/x509/x509cset.o \ + crypto/x509/x509rset.o \ + crypto/x509/x509_err.o \ + crypto/x509/x509name.o \ + crypto/x509/x509_v3.o \ + crypto/x509/x509_ext.o \ + crypto/x509/x509_att.o \ + crypto/x509/x509type.o \ + crypto/x509/x509_lu.o \ + crypto/x509/x_all.o \ + crypto/x509/x509_txt.o \ + crypto/x509/x509_trs.o \ + crypto/x509/x509_vpm.o \ + crypto/x509v3/v3_bcons.o \ + crypto/x509v3/v3_bitst.o \ + crypto/x509v3/v3_conf.o \ + crypto/x509v3/v3_extku.o \ + crypto/x509v3/v3_ia5.o \ + crypto/x509v3/v3_lib.o \ + crypto/x509v3/v3_prn.o \ + crypto/x509v3/v3_utl.o \ + crypto/x509v3/v3err.o \ + crypto/x509v3/v3_genn.o \ + crypto/x509v3/v3_alt.o \ + crypto/x509v3/v3_skey.o \ + crypto/x509v3/v3_akey.o \ + crypto/x509v3/v3_pku.o \ + crypto/x509v3/v3_int.o \ + crypto/x509v3/v3_enum.o \ + crypto/x509v3/v3_sxnet.o \ + crypto/x509v3/v3_cpols.o \ + crypto/x509v3/v3_crld.o \ + crypto/x509v3/v3_purp.o \ + crypto/x509v3/v3_info.o \ + crypto/x509v3/v3_ocsp.o \ + crypto/x509v3/v3_akeya.o \ + crypto/x509v3/v3_pmaps.o \ + crypto/x509v3/v3_pcons.o \ + crypto/x509v3/v3_ncons.o \ + crypto/x509v3/v3_pcia.o \ + crypto/x509v3/v3_pci.o \ + crypto/x509v3/pcy_cache.o \ + crypto/x509v3/pcy_node.o \ + crypto/x509v3/pcy_data.o \ + crypto/x509v3/pcy_map.o \ + crypto/x509v3/pcy_tree.o \ + crypto/x509v3/pcy_lib.o \ + crypto/x509v3/v3_asid.o \ + crypto/x509v3/v3_addr.o \ + crypto/conf/conf_err.o \ + crypto/conf/conf_lib.o \ + crypto/conf/conf_api.o \ + crypto/conf/conf_def.o \ + crypto/conf/conf_mod.o \ + crypto/conf/conf_mall.o \ + crypto/conf/conf_sap.o \ + crypto/txt_db/txt_db.o \ + crypto/pkcs7/pk7_asn1.o \ + crypto/pkcs7/pk7_lib.o \ + crypto/pkcs7/pkcs7err.o \ + crypto/pkcs7/pk7_doit.o \ + crypto/pkcs7/pk7_smime.o \ + crypto/pkcs7/pk7_attr.o \ + crypto/pkcs7/pk7_mime.o \ + crypto/pkcs7/bio_pk7.o \ + crypto/pkcs12/p12_add.o \ + crypto/pkcs12/p12_asn.o \ + crypto/pkcs12/p12_attr.o \ + crypto/pkcs12/p12_crpt.o \ + crypto/pkcs12/p12_crt.o \ + crypto/pkcs12/p12_decr.o \ + crypto/pkcs12/p12_init.o \ + crypto/pkcs12/p12_key.o \ + crypto/pkcs12/p12_kiss.o \ + crypto/pkcs12/p12_mutl.o \ + crypto/pkcs12/p12_utl.o \ + crypto/pkcs12/p12_npas.o \ + crypto/pkcs12/pk12err.o \ + crypto/pkcs12/p12_p8d.o \ + crypto/pkcs12/p12_p8e.o \ + crypto/comp/comp_lib.o \ + crypto/comp/comp_err.o \ + crypto/comp/c_rle.o \ + crypto/comp/c_zlib.o \ + crypto/ocsp/ocsp_asn.o \ + crypto/ocsp/ocsp_ext.o \ + crypto/ocsp/ocsp_ht.o \ + crypto/ocsp/ocsp_lib.o \ + crypto/ocsp/ocsp_cl.o \ + crypto/ocsp/ocsp_srv.o \ + crypto/ocsp/ocsp_prn.o \ + crypto/ocsp/ocsp_vfy.o \ + crypto/ocsp/ocsp_err.o \ + crypto/cmac/cmac.o \ + crypto/cmac/cm_ameth.o \ + crypto/cmac/cm_pmeth.o \ all: $(TARGET) diff --git a/Make.defaults b/Make.defaults index 4a82fb9e..5f30e292 100644 --- a/Make.defaults +++ b/Make.defaults @@ -32,10 +32,8 @@ OPTIMIZATIONS ?= -Os SUBDIRS = $(TOPDIR)/Cryptlib $(TOPDIR)/lib EFI_INCLUDE ?= /usr/include/efi -EFI_INCLUDES = -nostdinc -I$(TOPDIR)/Cryptlib -I$(TOPDIR)/Cryptlib/Include \ - -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol \ - -I$(TOPDIR)/include -iquote $(TOPDIR) -iquote $(shell pwd) - +EFI_INCLUDES = -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol +override EFI_INCLUDES := $(EFI_INCLUDES) EFI_CRT_OBJS = $(EFI_PATH)/crt0-efi-$(ARCH).o EFI_LDS = $(TOPDIR)/elf_$(ARCH)_efi.lds @@ -88,28 +86,58 @@ ifeq ($(ARCH),arm) TIMESTAMP_LOCATION := 72 endif -MACRO_PREFIX_MAP := -fmacro-prefix-map="$(TOPDIR)/"="$(DEBUGSRC)" -CFLAGS = -ggdb $(OPTIMIZATIONS) -fno-stack-protector -fno-strict-aliasing -fpic \ - -fshort-wchar -Wall -Wsign-compare -Werror -fno-builtin \ - -Werror=sign-compare -ffreestanding -std=gnu89 \ - $(if $(filter-out undefined,$(FANALYZER)),-fanalyzer,) \ - $(if $(filter-out undefined,$(COLOR)),-fdiagnostics-color=always,) \ - $(MACRO_PREFIX_MAP) \ +DEFINES = -DDEFAULT_LOADER='L"$(DEFAULT_LOADER)"' \ + -DDEFAULT_LOADER_CHAR='"$(DEFAULT_LOADER)"' + +INCLUDES = -nostdinc \ -I$(shell $(CC) $(ARCH_CFLAGS) -print-file-name=include) \ - "-DDEFAULT_LOADER=L\"$(DEFAULT_LOADER)\"" \ - "-DDEFAULT_LOADER_CHAR=\"$(DEFAULT_LOADER)\"" \ - $(EFI_INCLUDES) $(ARCH_CFLAGS) + -I$(TOPDIR)/Cryptlib -I$(TOPDIR)/Cryptlib/Include \ + -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol \ + -I$(TOPDIR)/include -iquote $(TOPDIR) -iquote $(shell pwd) + + +override DEFAULT_FEATUREFLAGS = \ + -std=gnu89 \ + -ggdb \ + -fno-builtin \ + -ffreestanding \ + -fmacro-prefix-map='$(TOPDIR)/=$(DEBUGSRC)' \ + -fno-stack-protector \ + -fno-strict-aliasing \ + -fpic \ + -fshort-wchar +$(call update-variable,FEATUREFLAGS) +$(call conditional-add-flag,$(FANALYZER),analyzer,FEATUREFLAGS,-fanalyzer) +$(call conditional-add-flag,$(COLOR),diagnostics-color,FEATUREFLAGS,-fdiagnostics-color=always) + +override DEFAULT_WARNFLAGS = \ + -Wall \ + -Wsign-compare +$(call update-variable,WARNFLAGS) + +override DEFAULT_WERRFLAGS = \ + -Werror \ + -Werror=sign-compare +$(call update-variable,WERRFLAGS) + +CFLAGS = $(FEATUREFLAGS) \ + $(OPTIMIZATIONS) \ + $(WARNFLAGS) \ + $(ARCH_CFLAGS) \ + $(WERRFLAGS) \ + $(INCLUDES) \ + $(DEFINES) ifneq ($(origin OVERRIDE_SECURITY_POLICY), undefined) - CFLAGS += -DOVERRIDE_SECURITY_POLICY + DEFINES += -DOVERRIDE_SECURITY_POLICY endif ifneq ($(origin REQUIRE_TPM), undefined) - CFLAGS += -DREQUIRE_TPM + DEFINES += -DREQUIRE_TPM endif ifneq ($(origin DISABLE_EBS_PROTECTION), undefined) - CFLAGS += -DDISABLE_EBS_PROTECTION + DEFINES += -DDISABLE_EBS_PROTECTION endif LIB_GCC = $(shell $(CC) $(ARCH_CFLAGS) -print-libgcc-file-name) @@ -130,16 +158,17 @@ SHIMHASHNAME = $(SHIMSTEM).hash BOOTEFINAME ?= BOOT$(ARCH_SUFFIX_UPPER).EFI BOOTCSVNAME ?= BOOT$(ARCH_SUFFIX_UPPER).CSV -CFLAGS += "-DEFI_ARCH=L\"$(ARCH_SUFFIX)\"" "-DDEBUGDIR=L\"/usr/lib/debug/usr/share/shim/$(ARCH_SUFFIX)-$(VERSION)$(DASHRELEASE)/\"" +DEFINES += -DEFI_ARCH='L"$(ARCH_SUFFIX)"' \ + -DDEBUGDIR='L"/usr/lib/debug/usr/share/shim/$(ARCH_SUFFIX)-$(VERSION)$(DASHRELEASE)/"' ifneq ($(origin VENDOR_DB_FILE), undefined) - CFLAGS += -DVENDOR_DB_FILE=\"$(VENDOR_DB_FILE)\" +DEFINES += -DVENDOR_DB_FILE=\"$(VENDOR_DB_FILE)\" endif ifneq ($(origin VENDOR_CERT_FILE), undefined) - CFLAGS += -DVENDOR_CERT_FILE=\"$(VENDOR_CERT_FILE)\" +DEFINES += -DVENDOR_CERT_FILE=\"$(VENDOR_CERT_FILE)\" endif ifneq ($(origin VENDOR_DBX_FILE), undefined) - CFLAGS += -DVENDOR_DBX_FILE=\"$(VENDOR_DBX_FILE)\" +DEFINES += -DVENDOR_DBX_FILE=\"$(VENDOR_DBX_FILE)\" endif LDFLAGS = --hash-style=sysv -nostdlib -znocombreloc -T $(EFI_LDS) -shared -Bsymbolic -L$(EFI_PATH) -L$(LIBDIR) -LCryptlib -LCryptlib/OpenSSL $(EFI_CRT_OBJS) --build-id=sha1 $(ARCH_LDFLAGS) --no-undefined diff --git a/Make.rules b/Make.rules index e4e31ff4..532aab66 100644 --- a/Make.rules +++ b/Make.rules @@ -6,3 +6,33 @@ define add-vendor-sbat $(OBJCOPY) --add-section ".$(patsubst %.csv,%,$(1))=$(1)" $(2) endef + +# true if the strings are the same +define str-eq +$(if $(subst $(1),,$(2)),,$(1)) +endef + +# true if 1 is in 2 +define has-flag +$(if $(findstring $(space)$(1)$(space),$(space)$(2)$(space)),$(1)) +endef + +# true if 1 is not in 2 +define has-not-flag +$(if $(call has-flag,$(1),$(2)),,$(1)) +endef + +# if 1 is set and 2 isn't in the thing named by 3, +# add 4 to the thing named by 3 +define conditional-add-flag +$(if $(and $(strip $(1)),$(strip $(call has-not-flag,$(2),$($(3))))),$(eval override $(value 3) += $(4))) +endef + +# Add everything from DEFAULT_$(1) to $(1) if it isn't there (in whole) +define update-variable +$(strip $(foreach x,$(DEFAULT_$(1)), + $(if $(call has-flag,$(x),$($(1))),, + $(eval override $(1)+=$(x))))) +endef + +# vim:filetype=make diff --git a/Makefile b/Makefile index c4403588..6c9083d2 100644 --- a/Makefile +++ b/Makefile @@ -17,8 +17,8 @@ endif override TOPDIR := $(abspath $(TOPDIR)) VPATH = $(TOPDIR) -include $(TOPDIR)/Make.defaults include $(TOPDIR)/Make.rules +include $(TOPDIR)/Make.defaults include $(TOPDIR)/include/coverity.mk include $(TOPDIR)/include/scan-build.mk include $(TOPDIR)/include/fanalyzer.mk @@ -260,10 +260,14 @@ clean-shim-objs: @rm -vf Cryptlib/*.[oa] Cryptlib/*/*.[oa] @if [ -d .git ] ; then git clean -f -d -e 'Cryptlib/OpenSSL/*'; fi -clean: clean-shim-objs clean-test-objs - $(MAKE) -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile clean +clean-openssl-objs: $(MAKE) -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile clean +clean-cryptlib-objs: + $(MAKE) -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile clean + +clean: clean-shim-objs clean-test-objs clean-openssl-objs clean-cryptlib-objs + GITTAG = $(VERSION) test-archive: @@ -293,4 +297,5 @@ archive: tag .PHONY : install-deps shim.key -export ARCH CC LD OBJCOPY EFI_INCLUDE OPTIMIZATIONS +export ARCH CC LD OBJCOPY EFI_INCLUDE EFI_INCLUDES OPTIMIZATIONS +export FEATUREFLAGS WARNFLAGS WERRFLAGS diff --git a/lib/Makefile b/lib/Makefile index 573c52bd..d9188c74 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -2,7 +2,8 @@ TARGET = lib.a LIBFILES = $(foreach x,$(wildcard *.c),$(patsubst %.c,%.o,$(x))) -EFI_INCLUDES = -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH) -I$(EFI_INCLUDE)/protocol -I$(TOPDIR)/../include \ +INCLUDES = $(EFI_INCLUDES) \ + -I$(TOPDIR)/../include \ -I$(TOPDIR)/CryptLib/Include/openssl/ lib.a: $(LIBFILES) -- cgit v1.2.3 From 6d3f247c323c68f78e810f6f76863ddee76f8532 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Fri, 5 Mar 2021 13:33:52 -0500 Subject: Don't use WCHAR even when we're assigning wide string literals Note that there are still some occurrences of WCHAR in Cryptlib/OpenSSL/, but they're only built on win32 platforms we don't support. Signed-off-by: Peter Jones --- lib/console.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'lib') diff --git a/lib/console.c b/lib/console.c index 05f7ec16..ffa8ea5c 100644 --- a/lib/console.c +++ b/lib/console.c @@ -572,7 +572,7 @@ console_mode_handle(VOID) /* Copy of gnu-efi-3.0 with the added secure boot strings */ static struct { EFI_STATUS Code; - WCHAR *Desc; + CHAR16 *Desc; } error_table[] = { { EFI_SUCCESS, L"Success"}, { EFI_LOAD_ERROR, L"Load Error"}, -- cgit v1.2.3 From f033a1da9f4c3acf7e3dfef906d01e348b6fcf42 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Tue, 9 Mar 2021 11:42:34 -0500 Subject: Restructure our includes. This re-structures our includes so we can be sure everything is always including all the system headers in a uniform, predictable way. Temporarily it also adds a bunch of junk at all the places we use variadic functions to specifically pick either the MS (cdecl) or ELF ABIs. I'm not 100% sure that's all correct (see later patch) but it's enough to allow this to build. Signed-off-by: Peter Jones --- Cryptlib/Include/OpenSslSupport.h | 13 +++++++----- Cryptlib/Include/ctype.h | 16 -------------- Cryptlib/Include/openssl/crypto.h | 1 + Cryptlib/Include/stdarg.h | 16 -------------- Cryptlib/Include/stddef.h | 15 -------------- Cryptlib/Include/stdlib.h | 16 -------------- Cryptlib/Include/string.h | 16 -------------- Cryptlib/Include/strings.h | 15 -------------- Cryptlib/InternalCryptLib.h | 2 ++ Cryptlib/Makefile | 14 +++++++++---- Cryptlib/OpenSSL/Makefile | 16 +++++++++----- Cryptlib/OpenSSL/crypto/bio/b_print.c | 8 +++---- Make.defaults | 3 ++- Makefile | 7 ++++--- MokManager.c | 8 +------ PasswordCrypt.c | 6 ++---- crypt_blowfish.c | 5 ----- errlog.c | 29 +++++++++++++------------- fallback.c | 4 ---- httpboot.c | 4 ---- include/console.h | 8 +++---- include/hexdump.h | 17 ++++++++------- include/system/alloca.h | 10 +++++++++ include/system/ctype.h | 14 +++++++++++++ include/system/inttypes.h | 13 ++++++++++++ include/system/stdarg.h | 31 ++++++++++++++++++++++++++++ include/system/stdio.h | 13 ++++++++++++ include/system/stdlib.h | 16 ++++++++++++++ include/system/string.h | 14 +++++++++++++ include/system/strings.h | 10 +++++++++ include/test.h | 4 ++-- lib/Makefile | 39 +++++++++++++++++++++++++++++++++-- lib/configtable.c | 3 --- lib/console.c | 21 +++++++------------ lib/execute.c | 4 ---- lib/print_crypto.c | 5 ----- lib/security_policy.c | 4 ---- lib/shell.c | 3 --- lib/simple_file.c | 4 ---- lib/variables.c | 3 --- mok.c | 4 ---- netboot.c | 2 -- pe.c | 1 - replacements.c | 5 ----- sbat.c | 1 - shim.c | 1 - shim.h | 25 ++++++++++++++++------ test.c | 3 ++- tpm.c | 6 ------ 49 files changed, 262 insertions(+), 236 deletions(-) delete mode 100644 Cryptlib/Include/ctype.h delete mode 100644 Cryptlib/Include/stdarg.h delete mode 100644 Cryptlib/Include/stddef.h delete mode 100644 Cryptlib/Include/stdlib.h delete mode 100644 Cryptlib/Include/string.h delete mode 100644 Cryptlib/Include/strings.h create mode 100644 include/system/alloca.h create mode 100644 include/system/ctype.h create mode 100644 include/system/inttypes.h create mode 100644 include/system/stdarg.h create mode 100644 include/system/stdio.h create mode 100644 include/system/stdlib.h create mode 100644 include/system/string.h create mode 100644 include/system/strings.h (limited to 'lib') diff --git a/Cryptlib/Include/OpenSslSupport.h b/Cryptlib/Include/OpenSslSupport.h index 0b555271..7af9650f 100644 --- a/Cryptlib/Include/OpenSslSupport.h +++ b/Cryptlib/Include/OpenSslSupport.h @@ -15,6 +15,14 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. #ifndef __OPEN_SSL_SUPPORT_H__ #define __OPEN_SSL_SUPPORT_H__ +/* + * Include stddef.h to avoid redefining "offsetof" + */ +#include +#include +#include +#include + #include #include #include "Base.h" @@ -23,11 +31,6 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. #include "Library/MemoryAllocationLib.h" #include "Library/DebugLib.h" -/* - * Include stddef.h to avoid redefining "offsetof" - */ -#include - #define CONST const // diff --git a/Cryptlib/Include/ctype.h b/Cryptlib/Include/ctype.h deleted file mode 100644 index ee07f6bc..00000000 --- a/Cryptlib/Include/ctype.h +++ /dev/null @@ -1,16 +0,0 @@ -/** @file - Include file to support building OpenSSL Crypto Library. - -Copyright (c) 2010, Intel Corporation. All rights reserved.
-This program and the accompanying materials -are licensed and made available under the terms and conditions of the BSD License -which accompanies this distribution. The full text of the license may be found at -http://opensource.org/licenses/bsd-license.php - -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, -WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. - -**/ - -#include - diff --git a/Cryptlib/Include/openssl/crypto.h b/Cryptlib/Include/openssl/crypto.h index bea4ca19..e201a123 100644 --- a/Cryptlib/Include/openssl/crypto.h +++ b/Cryptlib/Include/openssl/crypto.h @@ -117,6 +117,7 @@ #ifndef HEADER_CRYPTO_H # define HEADER_CRYPTO_H +# include # include # include diff --git a/Cryptlib/Include/stdarg.h b/Cryptlib/Include/stdarg.h deleted file mode 100644 index ee07f6bc..00000000 --- a/Cryptlib/Include/stdarg.h +++ /dev/null @@ -1,16 +0,0 @@ -/** @file - Include file to support building OpenSSL Crypto Library. - -Copyright (c) 2010, Intel Corporation. All rights reserved.
-This program and the accompanying materials -are licensed and made available under the terms and conditions of the BSD License -which accompanies this distribution. The full text of the license may be found at -http://opensource.org/licenses/bsd-license.php - -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, -WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. - -**/ - -#include - diff --git a/Cryptlib/Include/stddef.h b/Cryptlib/Include/stddef.h deleted file mode 100644 index 8dfc36ff..00000000 --- a/Cryptlib/Include/stddef.h +++ /dev/null @@ -1,15 +0,0 @@ -/** @file - Include file to support building OpenSSL Crypto Library. - -Copyright (c) 2010, Intel Corporation. All rights reserved.
-This program and the accompanying materials -are licensed and made available under the terms and conditions of the BSD License -which accompanies this distribution. The full text of the license may be found at -http://opensource.org/licenses/bsd-license.php - -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, -WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. - -**/ - -#include diff --git a/Cryptlib/Include/stdlib.h b/Cryptlib/Include/stdlib.h deleted file mode 100644 index ee07f6bc..00000000 --- a/Cryptlib/Include/stdlib.h +++ /dev/null @@ -1,16 +0,0 @@ -/** @file - Include file to support building OpenSSL Crypto Library. - -Copyright (c) 2010, Intel Corporation. All rights reserved.
-This program and the accompanying materials -are licensed and made available under the terms and conditions of the BSD License -which accompanies this distribution. The full text of the license may be found at -http://opensource.org/licenses/bsd-license.php - -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, -WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. - -**/ - -#include - diff --git a/Cryptlib/Include/string.h b/Cryptlib/Include/string.h deleted file mode 100644 index ee07f6bc..00000000 --- a/Cryptlib/Include/string.h +++ /dev/null @@ -1,16 +0,0 @@ -/** @file - Include file to support building OpenSSL Crypto Library. - -Copyright (c) 2010, Intel Corporation. All rights reserved.
-This program and the accompanying materials -are licensed and made available under the terms and conditions of the BSD License -which accompanies this distribution. The full text of the license may be found at -http://opensource.org/licenses/bsd-license.php - -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, -WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. - -**/ - -#include - diff --git a/Cryptlib/Include/strings.h b/Cryptlib/Include/strings.h deleted file mode 100644 index 8dfc36ff..00000000 --- a/Cryptlib/Include/strings.h +++ /dev/null @@ -1,15 +0,0 @@ -/** @file - Include file to support building OpenSSL Crypto Library. - -Copyright (c) 2010, Intel Corporation. All rights reserved.
-This program and the accompanying materials -are licensed and made available under the terms and conditions of the BSD License -which accompanies this distribution. The full text of the license may be found at -http://opensource.org/licenses/bsd-license.php - -THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, -WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. - -**/ - -#include diff --git a/Cryptlib/InternalCryptLib.h b/Cryptlib/InternalCryptLib.h index e9a4c20a..dc1a95e6 100644 --- a/Cryptlib/InternalCryptLib.h +++ b/Cryptlib/InternalCryptLib.h @@ -15,6 +15,8 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. #ifndef __INTERNAL_CRYPT_LIB_H__ #define __INTERNAL_CRYPT_LIB_H__ +#include + #include "Library/BaseLib.h" #include "Library/BaseMemoryLib.h" #include "Library/MemoryAllocationLib.h" diff --git a/Cryptlib/Makefile b/Cryptlib/Makefile index bc5681c5..65a3918c 100644 --- a/Cryptlib/Makefile +++ b/Cryptlib/Makefile @@ -2,8 +2,14 @@ ifneq ($(CCACHE_DISABLE),) export CCACHE_DISABLE endif -INCLUDES = -I$(TOPDIR) -iquote $(TOPDIR) -I$(TOPDIR)/Include \ - $(EFI_INCLUDES) -I$(shell $(CC) -print-file-name=include) +CRYPTDIR = $(TOPDIR)/Cryptlib + +FEATUREFLAGS += -nostdinc + +INCLUDES = -I$(CRYPTDIR) -I$(CRYPTDIR)/Include \ + $(EFI_INCLUDES) \ + -isystem $(TOPDIR)/include/system \ + -isystem $(shell $(CC) -print-file-name=include) CFLAGS = $(FEATUREFLAGS) \ $(OPTIMIZATIONS) \ @@ -15,12 +21,12 @@ CFLAGS = $(FEATUREFLAGS) \ CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) ifeq ($(ARCH),x86_64) -FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ -DNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 endif ifeq ($(ARCH),ia32) -FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) DEFINES += -DMDE_CPU_IA32 endif ifeq ($(ARCH),aarch64) diff --git a/Cryptlib/OpenSSL/Makefile b/Cryptlib/OpenSSL/Makefile index 5bd72481..294e889a 100644 --- a/Cryptlib/OpenSSL/Makefile +++ b/Cryptlib/OpenSSL/Makefile @@ -2,17 +2,23 @@ ifneq ($(CCACHE_DISABLE),) export CCACHE_DISABLE endif +CRYPTDIR = $(TOPDIR)/Cryptlib +OSSLDIR = $(TOPDIR)/Cryptlib/OpenSSL + DEFINES = -DL_ENDIAN \ -D_CRT_SECURE_NO_DEPRECATE \ -D_CRT_NONSTDC_NO_DEPRECATE \ -DOPENSSL_SMALL_FOOTPRINT \ -DPEDANTIC -INCLUDES = -I$(TOPDIR) -I$(TOPDIR)/.. -I$(TOPDIR)/../Include/ -I$(TOPDIR)/crypto \ - -I$(shell $(CC) -print-file-name=include) \ - -I$(TOPDIR)/../Include $(EFI_INCLUDES) \ - -I$(TOPDIR)/crypto/asn1 -I$(TOPDIR)/crypto/evp \ - -I$(TOPDIR)/crypto/modes -I$(TOPDIR)/crypto/include +INCLUDES = -I$(OSSLDIR) -I$(CRYPTDIR) -I$(OSSLDIR)/Include/ \ + -I$(OSSLDIR)/crypto -I$(CRYPTDIR)/Include $(EFI_INCLUDES) \ + -I$(OSSLDIR)/crypto/asn1 -I$(OSSLDIR)/crypto/evp \ + -I$(OSSLDIR)/crypto/modes -I$(OSSLDIR)/crypto/include \ + -isystem $(TOPDIR)/include/system \ + -isystem $(shell $(CC) -print-file-name=include) + +FEATUREFLAGS += -nostdinc WERRFLAGS += -Wno-error=discarded-qualifiers \ -Wno-error=maybe-uninitialized \ diff --git a/Cryptlib/OpenSSL/crypto/bio/b_print.c b/Cryptlib/OpenSSL/crypto/bio/b_print.c index fea73864..2d303ee8 100644 --- a/Cryptlib/OpenSSL/crypto/bio/b_print.c +++ b/Cryptlib/OpenSSL/crypto/bio/b_print.c @@ -134,9 +134,9 @@ static int fmtfp(char **, char **, size_t *, size_t *, LDOUBLE, int, int, int); #endif static int doapr_outch(char **, char **, size_t *, size_t *, int); -static int _dopr(char **sbuffer, char **buffer, - size_t *maxlen, size_t *retlen, int *truncated, - const char *format, va_list args); +static int EFIAPI _dopr(char **sbuffer, char **buffer, + size_t *maxlen, size_t *retlen, int *truncated, + const char *format, va_list args); /* format read states */ #define DP_S_DEFAULT 0 @@ -167,7 +167,7 @@ static int _dopr(char **sbuffer, char **buffer, #define char_to_int(p) (p - '0') #define OSSL_MAX(p,q) ((p >= q) ? p : q) -static int +static int EFIAPI _dopr(char **sbuffer, char **buffer, size_t *maxlen, diff --git a/Make.defaults b/Make.defaults index bef3cb51..ebb9e3c3 100644 --- a/Make.defaults +++ b/Make.defaults @@ -102,7 +102,8 @@ INCLUDES = -nostdinc \ -I$(shell $(CC) $(ARCH_CFLAGS) -print-file-name=include) \ -I$(TOPDIR)/Cryptlib -I$(TOPDIR)/Cryptlib/Include \ -I$(EFI_INCLUDE) -I$(EFI_INCLUDE)/$(ARCH_GNUEFI) -I$(EFI_INCLUDE)/protocol \ - -I$(TOPDIR)/include -iquote $(TOPDIR) -iquote $(shell pwd) + -I$(TOPDIR)/include -iquote $(TOPDIR) -iquote $(shell pwd) \ + -isystem $(TOPDIR)/include/system override DEFAULT_FEATUREFLAGS = \ -std=gnu11 \ diff --git a/Makefile b/Makefile index c1d13947..6a62e00a 100644 --- a/Makefile +++ b/Makefile @@ -16,6 +16,7 @@ override TOPDIR := $(shell pwd) endif override TOPDIR := $(abspath $(TOPDIR)) VPATH = $(TOPDIR) +export TOPDIR include $(TOPDIR)/Make.rules include $(TOPDIR)/Make.defaults @@ -134,15 +135,15 @@ gnu-efi/$(ARCH_GNUEFI)/gnuefi/libgnuefi.a gnu-efi/$(ARCH_GNUEFI)/lib/libefi.a: Cryptlib/libcryptlib.a: for i in Hash Hmac Cipher Rand Pk Pem SysCall; do mkdir -p Cryptlib/$$i; done - $(MAKE) VPATH=$(TOPDIR)/Cryptlib TOPDIR=$(TOPDIR)/Cryptlib -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile + $(MAKE) VPATH=$(TOPDIR)/Cryptlib -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile Cryptlib/OpenSSL/libopenssl.a: for i in x509v3 x509 txt_db stack sha rsa rc4 rand pkcs7 pkcs12 pem ocsp objects modes md5 lhash kdf hmac evp err dso dh conf comp cmac buffer bn bio async/arch asn1 aes; do mkdir -p Cryptlib/OpenSSL/crypto/$$i; done - $(MAKE) VPATH=$(TOPDIR)/Cryptlib/OpenSSL TOPDIR=$(TOPDIR)/Cryptlib/OpenSSL -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile + $(MAKE) VPATH=$(TOPDIR)/Cryptlib/OpenSSL -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile lib/lib.a: | $(TOPDIR)/lib/Makefile $(wildcard $(TOPDIR)/include/*.[ch]) if [ ! -d lib ]; then mkdir lib ; fi - $(MAKE) VPATH=$(TOPDIR)/lib TOPDIR=$(TOPDIR) CFLAGS="$(CFLAGS)" -C lib -f $(TOPDIR)/lib/Makefile lib.a + $(MAKE) VPATH=$(TOPDIR)/lib -C lib -f $(TOPDIR)/lib/Makefile lib.a buildid : $(TOPDIR)/buildid.c $(CC) -Og -g3 -Wall -Werror -Wextra -o $@ $< -lelf diff --git a/MokManager.c b/MokManager.c index 5a851d86..cd1492f8 100644 --- a/MokManager.c +++ b/MokManager.c @@ -1,18 +1,12 @@ // SPDX-License-Identifier: BSD-2-Clause-Patent +#include "shim.h" -#include -#include -#include #include #include #include #include #include -#include "shim.h" - -#include "hexdump.h" - #define PASSWORD_MAX 256 #define PASSWORD_MIN 1 #define SB_PASSWORD_LEN 16 diff --git a/PasswordCrypt.c b/PasswordCrypt.c index 311c914b..1030a6dd 100644 --- a/PasswordCrypt.c +++ b/PasswordCrypt.c @@ -1,13 +1,11 @@ // SPDX-License-Identifier: BSD-2-Clause-Patent -#include -#include +#include "shim.h" + #include #include #include -#include "shim.h" - #define TRAD_DES_HASH_SIZE 13 /* (64/6+1) + (12/6) */ #define BSDI_DES_HASH_SIZE 20 /* (64/6+1) + (24/6) + 4 + 1 */ #define BLOWFISH_HASH_SIZE 31 /* 184/6+1 */ diff --git a/crypt_blowfish.c b/crypt_blowfish.c index 7a474f26..b1eb0e60 100644 --- a/crypt_blowfish.c +++ b/crypt_blowfish.c @@ -43,11 +43,6 @@ * Blowfish library (I can't be sure if I would think of something if I * hadn't seen his code). */ - -#include -#include - -/* Just to make sure the prototypes match the actual definitions */ #include "shim.h" typedef unsigned int BF_word; diff --git a/errlog.c b/errlog.c index 714d09d3..16af23b0 100644 --- a/errlog.c +++ b/errlog.c @@ -5,30 +5,29 @@ */ #include "shim.h" -#include "hexdump.h" static CHAR16 **errs = NULL; static UINTN nerrs = 0; -EFI_STATUS -vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, va_list args) +EFI_STATUS EFIAPI +vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, elf_va_list args) { - va_list args2; + elf_va_list args2; EFI_STATUS efi_status = EFI_SUCCESS; if (verbose) { - va_copy(args2, args); + elf_va_copy(args2, args); console_print(L"%a:%d:%a() ", file, line, func); efi_status = VPrint(fmt, args2); - va_end(args2); + elf_va_end(args2); } return efi_status; } -EFI_STATUS -VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, va_list args) +EFI_STATUS EFIAPI +VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, elf_va_list args) { - va_list args2; + elf_va_list args2; CHAR16 **newerrs; newerrs = ReallocatePool(errs, (nerrs + 1) * sizeof(*errs), @@ -39,11 +38,11 @@ VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, va_li newerrs[nerrs] = PoolPrint(L"%a:%d %a() ", file, line, func); if (!newerrs[nerrs]) return EFI_OUT_OF_RESOURCES; - va_copy(args2, args); + elf_va_copy(args2, args); newerrs[nerrs+1] = VPoolPrint(fmt, args2); if (!newerrs[nerrs+1]) return EFI_OUT_OF_RESOURCES; - va_end(args2); + elf_va_end(args2); nerrs += 2; newerrs[nerrs] = NULL; @@ -52,15 +51,15 @@ VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, va_li return EFI_SUCCESS; } -EFI_STATUS +EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) { - va_list args; + elf_va_list args; EFI_STATUS efi_status; - va_start(args, fmt); + elf_va_start(args, fmt); efi_status = VLogError(file, line, func, fmt, args); - va_end(args); + elf_va_end(args); return efi_status; } diff --git a/fallback.c b/fallback.c index fc81c5e4..ba90bb3b 100644 --- a/fallback.c +++ b/fallback.c @@ -3,10 +3,6 @@ * Copyright Red Hat, Inc. * Copyright Peter Jones */ - -#include -#include - #include "shim.h" #define NO_REBOOT L"FB_NO_REBOOT" diff --git a/httpboot.c b/httpboot.c index bedb99d2..fe08f3f7 100644 --- a/httpboot.c +++ b/httpboot.c @@ -7,10 +7,6 @@ * (http://tianocore.sf.net) and are Copyright 2009-2012 Intel * Corporation. */ - -#include -#include - #include "shim.h" static UINTN diff --git a/include/console.h b/include/console.h index b2ab5fe4..d8af3cd3 100644 --- a/include/console.h +++ b/include/console.h @@ -17,9 +17,9 @@ EFI_STATUS console_get_keystroke(EFI_INPUT_KEY *key); -UINTN +UINTN EFIAPI console_print(const CHAR16 *fmt, ...); -UINTN +UINTN EFIAPI console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...); void console_print_box_at(CHAR16 *str_arr[], int highlight, @@ -101,8 +101,8 @@ extern UINT32 verbose; #define dprint(fmt, ...) \ dprint_(L"%a:%d:%a() " fmt, __FILE__, __LINE__ - 1, __func__, \ ##__VA_ARGS__) -extern EFI_STATUS -vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, va_list args); +extern EFI_STATUS EFIAPI vdprint_(const CHAR16 *fmt, const char *file, int line, + const char *func, elf_va_list args); #define vdprint(fmt, ...) \ vdprint_(fmt, __FILE__, __LINE__ - 1, __func__, ##__VA_ARGS__) diff --git a/include/hexdump.h b/include/hexdump.h index 8b8b4557..36d77ec4 100644 --- a/include/hexdump.h +++ b/include/hexdump.h @@ -3,7 +3,8 @@ #ifndef STATIC_HEXDUMP_H #define STATIC_HEXDUMP_H -#include +#include "shim.h" +#include "include/console.h" static inline unsigned long UNUSED prepare_hex(const void *data, size_t size, char *buf, unsigned int position) @@ -80,8 +81,9 @@ prepare_text(const void *data, size_t size, char *buf, unsigned int position) * variadic hexdump formatted * think of it as: printf("%s%s\n", vformat(fmt, ap), hexdump(data,size)); */ -static inline void UNUSED -vhexdumpf(const char *file, int line, const char *func, const CHAR16 * const fmt, const void *data, unsigned long size, size_t at, va_list ap) +static inline void UNUSED EFIAPI +vhexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, + const void *data, unsigned long size, size_t at, elf_va_list ap) { unsigned long display_offset = at; unsigned long offset = 0; @@ -115,13 +117,14 @@ vhexdumpf(const char *file, int line, const char *func, const CHAR16 * const fmt * think of it as: printf("%s%s", format(fmt, ...), hexdump(data,size)[lineN]); */ static inline void UNUSED -hexdumpf(const char *file, int line, const char *func, const CHAR16 * const fmt, const void *data, unsigned long size, size_t at, ...) +hexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, + const void *data, unsigned long size, size_t at, ...) { - va_list ap; + elf_va_list ap; - va_start(ap, at); + elf_va_start(ap, at); vhexdumpf(file, line, func, fmt, data, size, at, ap); - va_end(ap); + elf_va_end(ap); } static inline void UNUSED diff --git a/include/system/alloca.h b/include/system/alloca.h new file mode 100644 index 00000000..dc11b60d --- /dev/null +++ b/include/system/alloca.h @@ -0,0 +1,10 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _ALLOCA_H +#define _ALLOCA_H + +#endif /* !_ALLOCA_H */ +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/ctype.h b/include/system/ctype.h new file mode 100644 index 00000000..c771bb69 --- /dev/null +++ b/include/system/ctype.h @@ -0,0 +1,14 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * ctype.h - standard ctype functions + */ +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _CTYPE_H +#define _CTYPE_H + + +#endif /* !_CTYPE_H */ +#endif /* !SHIM_UNIT_TEST */ +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/inttypes.h b/include/system/inttypes.h new file mode 100644 index 00000000..a35b0090 --- /dev/null +++ b/include/system/inttypes.h @@ -0,0 +1,13 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _INTTYPES_H +#define _INTTYPES_H + +#include +#include + +#endif /* !INTTYPES_H_ */ +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/stdarg.h b/include/system/stdarg.h new file mode 100644 index 00000000..346b760d --- /dev/null +++ b/include/system/stdarg.h @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * stdarg.h - try to make consistent va_* handling for EFI + */ +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _STDARG_H +#define _STDARG_H + +#include + +#endif /* !_STDARG_H */ +#endif +#ifndef SHIM_STDARG_H_ +#define SHIM_STDARG_H_ + +typedef __builtin_ms_va_list ms_va_list; +#define ms_va_copy(dest, start) __builtin_ms_va_copy(dest, start) +#define ms_va_start(marker, arg) __builtin_ms_va_start(marker, arg) +#define ms_va_arg(marker, type) __builtin_va_arg(marker, type) +#define ms_va_end(marker) __builtin_ms_va_end(marker) + +typedef __builtin_va_list elf_va_list; +#define elf_va_copy(dest, start) __builtin_va_copy(dest, start) +#define elf_va_start(marker, arg) __builtin_va_start(marker, arg) +#define elf_va_arg(marker, type) __builtin_va_arg(marker, type) +#define elf_va_end(marker) __builtin_va_end(marker) + +#endif /* !SHIM_STDARG_H_ */ +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/stdio.h b/include/system/stdio.h new file mode 100644 index 00000000..6ea60d71 --- /dev/null +++ b/include/system/stdio.h @@ -0,0 +1,13 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * stdio.h - sigh + */ +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _STDIO_H +#define _STDIO_H + +#endif /* !_STDIO_H */ +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/stdlib.h b/include/system/stdlib.h new file mode 100644 index 00000000..f2660f63 --- /dev/null +++ b/include/system/stdlib.h @@ -0,0 +1,16 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _STDLIB_H +#define _STDLIB_H + +/* + * I don't know why, but openssl expects to get size_t from stdlib.h + * instead of stddef.h, so... whatever. + */ +#include + +#endif /* !_STDLIB_H */ +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/string.h b/include/system/string.h new file mode 100644 index 00000000..21e46c1d --- /dev/null +++ b/include/system/string.h @@ -0,0 +1,14 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _STRING_H +#define _STRING_H + +#include + +__typeof__(__builtin_memset) memset; +__typeof__(__builtin_memcpy) memcpy; + +#endif /* _STRING_H */ +#endif diff --git a/include/system/strings.h b/include/system/strings.h new file mode 100644 index 00000000..c82bd917 --- /dev/null +++ b/include/system/strings.h @@ -0,0 +1,10 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +#ifdef SHIM_UNIT_TEST +#include_next +#else +#ifndef _STRINGS_H +#define _STRINGS_H + +#endif /* !_STRINGS_H */ +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/test.h b/include/test.h index 6fc178ba..8a970fd2 100644 --- a/include/test.h +++ b/include/test.h @@ -11,13 +11,13 @@ #include #if defined(__aarch64__) -#include +#include #elif defined(__arm__) #include #elif defined(__i386__) || defined(__i486__) || defined(__i686__) #include #elif defined(__x86_64__) -#include +#include #else #error what arch is this #endif diff --git a/lib/Makefile b/lib/Makefile index d9188c74..63893c3e 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -2,9 +2,44 @@ TARGET = lib.a LIBFILES = $(foreach x,$(wildcard *.c),$(patsubst %.c,%.o,$(x))) +CRYPTDIR = $(TOPDIR)/Cryptlib + INCLUDES = $(EFI_INCLUDES) \ - -I$(TOPDIR)/../include \ - -I$(TOPDIR)/CryptLib/Include/openssl/ + -I$(TOPDIR)/include \ + -I$(CRYPTDIR)/Include/openssl/ \ + -I$(CRYPTDIR)/Include/ \ + -I$(CRYPTDIR) \ + -I$(TOPDIR) \ + -isystem $(TOPDIR)/include/system \ + -isystem $(shell $(CC) -print-file-name=include) + +CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) + +ifeq ($(ARCH),x86_64) +FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ + -UNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 +endif +ifeq ($(ARCH),ia32) +FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) +DEFINES += -DMDE_CPU_IA32 +endif +ifeq ($(ARCH),aarch64) +DEFINES += -DMDE_CPU_AARCH64 +endif +ifeq ($(ARCH),arm) +DEFINES += -DMDE_CPU_ARM +endif + +LDFLAGS = -nostdlib -znocombreloc + + +CFLAGS = $(FEATUREFLAGS) \ + $(OPTIMIZATIONS) \ + $(WARNFLAGS) \ + $(WERRFLAGS) \ + $(INCLUDES) \ + $(DEFINES) lib.a: $(LIBFILES) $(AR) rcs lib.a $(LIBFILES) diff --git a/lib/configtable.c b/lib/configtable.c index 8675fad1..66e97f63 100644 --- a/lib/configtable.c +++ b/lib/configtable.c @@ -4,9 +4,6 @@ * * read some platform configuration tables */ -#include -#include - #include "shim.h" void * diff --git a/lib/console.c b/lib/console.c index ffa8ea5c..32c6d55d 100644 --- a/lib/console.c +++ b/lib/console.c @@ -3,11 +3,6 @@ * Copyright 2012 * Copyright 2013 Red Hat Inc. */ -#include -#include -#include -#include - #include "shim.h" static UINT8 console_text_mode = 0; @@ -88,27 +83,27 @@ VOID console_fini(VOID) setup_console(0); } -UINTN +UINTN EFIAPI console_print(const CHAR16 *fmt, ...) { - va_list args; + elf_va_list args; UINTN ret; if (!console_text_mode) setup_console(1); - va_start(args, fmt); + elf_va_start(args, fmt); ret = VPrint(fmt, args); - va_end(args); + elf_va_end(args); return ret; } -UINTN +UINTN EFIAPI console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) { SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut; - va_list args; + elf_va_list args; UINTN ret; if (!console_text_mode) @@ -116,9 +111,9 @@ console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) co->SetCursorPosition(co, col, row); - va_start(args, fmt); + elf_va_start(args, fmt); ret = VPrint(fmt, args); - va_end(args); + elf_va_end(args); return ret; } diff --git a/lib/execute.c b/lib/execute.c index f57a6321..642f94a3 100644 --- a/lib/execute.c +++ b/lib/execute.c @@ -3,10 +3,6 @@ * Copyright 2012 * Code Copyright 2012 Red Hat, Inc */ - -#include -#include - #include "shim.h" EFI_STATUS diff --git a/lib/print_crypto.c b/lib/print_crypto.c index 39dfd2c0..ccdb65b1 100644 --- a/lib/print_crypto.c +++ b/lib/print_crypto.c @@ -2,11 +2,6 @@ /* * Copyright 2019 SUSE LLC */ - -#include -#include -#include - #include "shim.h" #include diff --git a/lib/security_policy.c b/lib/security_policy.c index 6a9b13ed..6c42cc14 100644 --- a/lib/security_policy.c +++ b/lib/security_policy.c @@ -4,10 +4,6 @@ * * Install and remove a platform security2 override policy */ - -#include -#include - #include "shim.h" #if defined(OVERRIDE_SECURITY_POLICY) diff --git a/lib/shell.c b/lib/shell.c index 87f279d6..146d9a21 100644 --- a/lib/shell.c +++ b/lib/shell.c @@ -4,9 +4,6 @@ * * misc shell helper functions */ -#include -#include - #include "shim.h" EFI_STATUS diff --git a/lib/simple_file.c b/lib/simple_file.c index e6544709..5fd3e1a6 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -2,10 +2,6 @@ /* * Copyright 2012 */ - -#include -#include - #include "shim.h" EFI_STATUS diff --git a/lib/variables.c b/lib/variables.c index 6db069ef..57875e26 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -10,9 +10,6 @@ * Copyright (c) 2011 - 2012, Intel Corporation. All rights reserved.
* */ -#include -#include - #include "shim.h" EFI_STATUS diff --git a/mok.c b/mok.c index ac0276ec..6bd506be 100644 --- a/mok.c +++ b/mok.c @@ -6,10 +6,6 @@ #include "shim.h" -#include - -#include "hexdump.h" - /* * Check if a variable exists */ diff --git a/netboot.c b/netboot.c index 25a6df7f..450e9def 100644 --- a/netboot.c +++ b/netboot.c @@ -13,8 +13,6 @@ #include "shim.h" -#include - #define ntohs(x) __builtin_bswap16(x) /* supported both by GCC and clang */ #define htons(x) ntohs(x) diff --git a/pe.c b/pe.c index 45dd4714..73b05a51 100644 --- a/pe.c +++ b/pe.c @@ -5,7 +5,6 @@ */ #include "shim.h" -#include "hexdump.h" #include #include diff --git a/replacements.c b/replacements.c index 69dbd5a2..278a8e78 100644 --- a/replacements.c +++ b/replacements.c @@ -18,11 +18,6 @@ * National Security Policy and Scientific Developments, November 20, * 1969. */ - -#include -#include -#include - #include "shim.h" static EFI_SYSTEM_TABLE *systab; diff --git a/sbat.c b/sbat.c index f46bb8ab..d8750962 100644 --- a/sbat.c +++ b/sbat.c @@ -4,7 +4,6 @@ */ #include "shim.h" -#include "string.h" EFI_STATUS parse_sbat_section(char *section_base, size_t section_size, diff --git a/shim.c b/shim.c index 32bc3e81..6f627b1f 100644 --- a/shim.c +++ b/shim.c @@ -12,7 +12,6 @@ */ #include "shim.h" -#include "hexdump.h" #if defined(ENABLE_SHIM_CERT) #include "shim_cert.h" #endif /* defined(ENABLE_SHIM_CERT) */ diff --git a/shim.h b/shim.h index d28e16b7..61dafa82 100644 --- a/shim.h +++ b/shim.h @@ -26,6 +26,14 @@ #endif #endif +#include +#include +#include +#include +#include +#include +#include + #ifndef SHIM_UNIT_TEST #include #include @@ -34,9 +42,6 @@ #include #endif -#include -#include - #ifdef SHIM_UNIT_TEST #include "include/test.h" #endif @@ -158,9 +163,14 @@ #include "include/tpm.h" #include "include/ucs2.h" #include "include/variables.h" +#include "include/hexdump.h" #include "version.h" +#ifndef SHIM_UNIT_TEST +#include "Cryptlib/Include/OpenSslSupport.h" +#endif + INTERFACE_DECL(_SHIM_LOCK); typedef @@ -196,9 +206,12 @@ typedef struct _SHIM_LOCK { extern EFI_STATUS shim_init(void); extern void shim_fini(void); -extern EFI_STATUS LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...); -extern EFI_STATUS VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, va_list args); -extern VOID LogHexdump_(const char *file, int line, const char *func, const void *data, size_t sz); +extern EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, + const CHAR16 *fmt, ...); +extern EFI_STATUS EFIAPI VLogError(const char *file, int line, const char *func, + const CHAR16 *fmt, elf_va_list args); +extern VOID LogHexdump_(const char *file, int line, const char *func, + const void *data, size_t sz); extern VOID PrintErrors(VOID); extern VOID ClearErrors(VOID); extern VOID restore_loaded_image(VOID); diff --git a/test.c b/test.c index b21e2191..aa0da1fd 100644 --- a/test.c +++ b/test.c @@ -12,7 +12,8 @@ UINT8 in_protocol = 0; int debug = DEFAULT_DEBUG_PRINT_STATE; -EFI_STATUS LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) +EFI_STATUS EFIAPI +LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) { assert(0); return EFI_SUCCESS; diff --git a/tpm.c b/tpm.c index e1fcb8be..808e0444 100644 --- a/tpm.c +++ b/tpm.c @@ -1,10 +1,4 @@ // SPDX-License-Identifier: BSD-2-Clause-Patent - -#include -#include -#include -#include - #include "shim.h" typedef struct { -- cgit v1.2.3 From 766aac4d5cfbe76026be5ce718b0883ee211f323 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Tue, 9 Mar 2021 11:54:58 -0500 Subject: Consolidate most of our standard lib functions to lib Signed-off-by: Peter Jones --- Cryptlib/Include/OpenSslSupport.h | 23 +--- Cryptlib/Makefile | 3 +- Cryptlib/SysCall/BaseStrings.c | 34 +----- Cryptlib/SysCall/CrtWrapper.c | 82 ------------- Cryptlib/SysCall/memset.c | 40 ------- Makefile | 4 +- csv.c | 4 +- gnu-efi | 2 +- httpboot.c | 14 +-- include/compiler.h | 5 + include/endian.h | 19 +++ include/hexdump.h | 2 - include/str.h | 118 +----------------- include/system/alloca.h | 6 + include/system/builtins_begin_.h | 94 +++++++++++++++ include/system/builtins_end_.h | 28 +++++ include/system/ctype.h | 73 +++++++++++- include/system/stdlib.h | 12 ++ include/system/string.h | 51 +++++++- include/system/strings.h | 9 ++ lib/string.c | 245 ++++++++++++++++++++++++++++++++++++++ mok.c | 2 +- netboot.c | 8 +- sbat.c | 4 +- shim.h | 2 + 25 files changed, 566 insertions(+), 318 deletions(-) delete mode 100644 Cryptlib/SysCall/memset.c create mode 100644 include/endian.h create mode 100644 include/system/builtins_begin_.h create mode 100644 include/system/builtins_end_.h create mode 100644 lib/string.c (limited to 'lib') diff --git a/Cryptlib/Include/OpenSslSupport.h b/Cryptlib/Include/OpenSslSupport.h index 7af9650f..6bb7ba64 100644 --- a/Cryptlib/Include/OpenSslSupport.h +++ b/Cryptlib/Include/OpenSslSupport.h @@ -288,34 +288,21 @@ extern int errno; void *malloc (size_t); void *realloc (void *, size_t); void free (void *); -int isdigit (int); -int isspace (int); -int tolower (int); -int isupper (int); -int isxdigit (int); -int isalnum (int); void *memcpy (void *, const void *, size_t); void *memset (void *, int, size_t); void *memchr (const void *, int, size_t); int memcmp (const void *, const void *, size_t); void *memmove (void *, const void *, size_t); -int strcmp (const char *, const char *); -int strncmp (const char *, const char *, size_t); char *strcpy (char *, const char *); char *strncpy (char *, const char *, size_t); -size_t strlen (const char *); char *strcat (char *, const char *); char *strchr (const char *, int); int strcasecmp (const char *, const char *); int strncasecmp (const char *, const char *, size_t); char *strncpy (char *, const char *, size_t); -int strncmp (const char *, const char *, size_t); -char *strrchr (const char *, int); unsigned long strtoul (const char *, char **, int); long strtol (const char *, char **, int); char *strerror (int); -size_t strspn (const char *, const char *); -size_t strcspn (const char *, const char *); int printf (const char *, ...); int sscanf (const char *, const char *, ...); int open (const char *, int, ...); @@ -351,7 +338,6 @@ gid_t getegid (void); void qsort (void *, size_t, size_t, int (*)(const void *, const void *)); char *getenv (const char *); void exit (int); -void abort (void); __sighandler_t *signal (int, __sighandler_t *); // @@ -361,7 +347,7 @@ extern FILE *stderr; extern FILE *stdin; extern FILE *stdout; -#define AsciiStrLen(x) strlena(x) +#define AsciiStrLen(x) strlen(x) #define AsciiStrnCmp(s1, s2, len) strncmpa((CHAR8 *)s1, (CHAR8 *)s2, len) // @@ -372,17 +358,10 @@ extern FILE *stdout; #define memchr(buf,ch,count) ScanMem8((CHAR8 *)buf,(UINTN)(count),ch) #define memcmp(buf1,buf2,count) (int)(CompareMem(buf1,buf2,(UINTN)(count))) #define memmove(dest,source,count) CopyMem(dest,source,(UINTN)(count)) -#define strlen(str) (size_t)(AsciiStrLen((CHAR8 *)str)) -#define strcpy(strDest,strSource) AsciiStrCpy((CHAR8 *)strDest,(const CHAR8 *)strSource) -#define strncpy(strDest,strSource,count) AsciiStrnCpy((CHAR8 *)strDest,(const CHAR8 *)strSource,(UINTN)count) -#define strcat(strDest,strSource) AsciiStrCat((CHAR8 *)strDest,(const CHAR8 *)strSource) -#define strchr(str,ch) (char *)(ScanMem8((CHAR8 *)str,AsciiStrSize((CHAR8 *)str),ch)) -#define strncmp(string1,string2,count) (int)(AsciiStrnCmp((const CHAR8 *)string1, (const CHAR8 *)string2,(UINTN)(count))) #define localtime(timer) NULL #define assert(expression) #define atoi(nptr) AsciiStrDecimalToUintn((const CHAR8 *)nptr) #define gettimeofday(tvp,tz) do { (tvp)->tv_sec = time(NULL); (tvp)->tv_usec = 0; } while (0) #define gmtime_r(timer,result) (result = NULL) -#define abort() #endif diff --git a/Cryptlib/Makefile b/Cryptlib/Makefile index 65a3918c..27614618 100644 --- a/Cryptlib/Makefile +++ b/Cryptlib/Makefile @@ -63,8 +63,7 @@ OBJS = Hash/CryptMd4Null.o \ SysCall/CrtWrapper.o \ SysCall/TimerWrapper.o \ SysCall/BaseMemAllocation.o \ - SysCall/BaseStrings.o \ - SysCall/memset.o + SysCall/BaseStrings.o all: $(TARGET) diff --git a/Cryptlib/SysCall/BaseStrings.c b/Cryptlib/SysCall/BaseStrings.c index c4b3e18e..29a16100 100644 --- a/Cryptlib/SysCall/BaseStrings.c +++ b/Cryptlib/SysCall/BaseStrings.c @@ -3,7 +3,7 @@ CHAR8 * AsciiStrCat(CHAR8 *Destination, const CHAR8 *Source) { - UINTN dest_len = strlena((CHAR8 *)Destination); + UINTN dest_len = strlen((CHAR8 *)Destination); UINTN i; for (i = 0; Source[i] != '\0'; i++) @@ -61,37 +61,7 @@ WriteUnaligned32(UINT32 *Buffer, UINT32 Value) UINTN AsciiStrSize(const CHAR8 *string) { - return strlena(string) + 1; -} - -int -strcmp (const char *str1, const char *str2) -{ - return strcmpa((CHAR8 *)str1,(CHAR8 *)str2); -} - -inline static char -toupper (char c) -{ - return ((c >= 'a' && c <= 'z') ? c - ('a' - 'A') : c); -} - -/* Based on AsciiStriCmp() in edk2 MdePkg/Library/BaseLib/String.c */ -int -strcasecmp (const char *str1, const char *str2) -{ - char c1, c2; - - c1 = toupper (*str1); - c2 = toupper (*str2); - while ((*str1 != '\0') && (c1 == c2)) { - str1++; - str2++; - c1 = toupper (*str1); - c2 = toupper (*str2); - } - - return c1 - c2; + return strlen(string) + 1; } /* Based on AsciiStrDecimalToUintnS() in edk2 diff --git a/Cryptlib/SysCall/CrtWrapper.c b/Cryptlib/SysCall/CrtWrapper.c index 698e1eef..4bdaede9 100644 --- a/Cryptlib/SysCall/CrtWrapper.c +++ b/Cryptlib/SysCall/CrtWrapper.c @@ -121,21 +121,6 @@ QuickSortWorker ( // -- String Manipulation Routines -- // -/* Scan a string for the last occurrence of a character */ -char *strrchr (const char *str, int c) -{ - char * save; - - for (save = NULL; ; ++str) { - if (*str == c) { - save = (char *)str; - } - if (*str == 0) { - return (save); - } - } -} - /* Read formatted data from a string */ int sscanf (const char *buffer, const char *format, ...) { @@ -146,59 +131,6 @@ int sscanf (const char *buffer, const char *format, ...) return 0; } -// -// -- Character Classification Routines -- -// - -/* Determines if a particular character is a decimal-digit character */ -int isdigit (int c) -{ - // - // ::= [0-9] - // - return (('0' <= (c)) && ((c) <= '9')); -} - -/* Determine if an integer represents character that is a hex digit */ -int isxdigit (int c) -{ - // - // ::= [0-9] | [a-f] | [A-F] - // - return ((('0' <= (c)) && ((c) <= '9')) || - (('a' <= (c)) && ((c) <= 'f')) || - (('A' <= (c)) && ((c) <= 'F'))); -} - -/* Determines if a particular character represents a space character */ -int isspace (int c) -{ - // - // ::= [ ] - // - return ((c) == ' '); -} - -/* Determine if a particular character is an alphanumeric character */ -int isalnum (int c) -{ - // - // ::= [0-9] | [a-z] | [A-Z] - // - return ((('0' <= (c)) && ((c) <= '9')) || - (('a' <= (c)) && ((c) <= 'z')) || - (('A' <= (c)) && ((c) <= 'Z'))); -} - -/* Determines if a particular character is in upper case */ -int isupper (int c) -{ - // - // := [A-Z] - // - return (('A' <= (c)) && ((c) <= 'Z')); -} - // // -- Data Conversion Routines -- // @@ -223,15 +155,6 @@ unsigned long strtoul (const char *nptr, char **endptr, int base) return 0; } -/* Convert character to lowercase */ -int tolower (int c) -{ - if (('A' <= (c)) && ((c) <= 'Z')) { - return (c - ('A' - 'a')); - } - return (c); -} - // // -- Searching and Sorting Routines -- // @@ -424,11 +347,6 @@ int stat (const char *c, struct stat *s) return -1; } -int strncasecmp (const char *c, const char *s, size_t l) -{ - return 0; -} - void syslog (int a, const char *c, ...) { diff --git a/Cryptlib/SysCall/memset.c b/Cryptlib/SysCall/memset.c deleted file mode 100644 index 76deed68..00000000 --- a/Cryptlib/SysCall/memset.c +++ /dev/null @@ -1,40 +0,0 @@ -/* - * Copyright 2016 SUSE LINUX GmbH - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * - * Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * - * Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the - * distribution. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS - * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT - * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS - * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE - * COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, - * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, - * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED - * OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -#include -#include - -typedef UINTN size_t; - -void * -memset (void *dest, int ch, size_t count) -{ - SetMem(dest, count, (UINT8)(ch)); - return dest; -} diff --git a/Makefile b/Makefile index 6a62e00a..7c0fbb11 100644 --- a/Makefile +++ b/Makefile @@ -116,12 +116,12 @@ LIBS = Cryptlib/libcryptlib.a \ gnu-efi/$(ARCH_GNUEFI)/gnuefi/libgnuefi.a $(SHIMSONAME): $(OBJS) $(LIBS) - $(LD) -o $@ $(LDFLAGS) $^ $(EFI_LIBS) + $(LD) -o $@ $(LDFLAGS) $^ $(EFI_LIBS) lib/lib.a fallback.o: $(FALLBACK_SRCS) $(FBSONAME): $(FALLBACK_OBJS) $(LIBS) - $(LD) -o $@ $(LDFLAGS) $^ $(EFI_LIBS) + $(LD) -o $@ $(LDFLAGS) $^ $(EFI_LIBS) lib/lib.a MokManager.o: $(MOK_SOURCES) diff --git a/csv.c b/csv.c index 3c821414..d141f035 100644 --- a/csv.c +++ b/csv.c @@ -21,8 +21,8 @@ parse_csv_line(char * line, size_t max, size_t *n_columns, const char *columns[] valid = strntoken(next, max, delims, &token, &state); } if (valid) { - next += strlena(token) + 1; - max -= strlena(token) + 1; + next += strlen(token) + 1; + max -= strlen(token) + 1; columns[n] = token; new_n = n + 1; } else { diff --git a/gnu-efi b/gnu-efi index 9aa86c75..d7e183a3 160000 --- a/gnu-efi +++ b/gnu-efi @@ -1 +1 @@ -Subproject commit 9aa86c7526a4adc363afe6847bc3a4c8efe6df84 +Subproject commit d7e183a351d1a81efb2402e5148a4a69fc170365 diff --git a/httpboot.c b/httpboot.c index fe08f3f7..93d88931 100644 --- a/httpboot.c +++ b/httpboot.c @@ -130,7 +130,7 @@ find_httpboot (EFI_HANDLE device) /* Save the current URI */ UriNode = (URI_DEVICE_PATH *)Node; - uri_size = strlena(UriNode->Uri); + uri_size = strlen(UriNode->Uri); uri = AllocatePool(uri_size + 1); if (!uri) { perror(L"Failed to allocate uri\n"); @@ -156,10 +156,10 @@ generate_next_uri (CONST CHAR8 *current_uri, CONST CHAR8 *next_loader, UINTN path_len = 0; UINTN count = 0; - if (strncmpa(current_uri, (CHAR8 *)"http://", 7) == 0) { + if (strncmp(current_uri, (CHAR8 *)"http://", 7) == 0) { ptr = current_uri + 7; count += 7; - } else if (strncmpa(current_uri, (CHAR8 *)"https://", 8) == 0) { + } else if (strncmp(current_uri, (CHAR8 *)"https://", 8) == 0) { ptr = current_uri + 8; count += 8; } else { @@ -167,7 +167,7 @@ generate_next_uri (CONST CHAR8 *current_uri, CONST CHAR8 *next_loader, } /* Extract the path */ - next_len = strlena(next_loader); + next_len = strlen(next_loader); while (*ptr != '\0') { count++; if (*ptr == '/') @@ -192,9 +192,9 @@ extract_hostname (CONST CHAR8 *url, CHAR8 **hostname) CONST CHAR8 *ptr, *start; UINTN host_len = 0; - if (strncmpa(url, (CHAR8 *)"http://", 7) == 0) + if (strncmp(url, (CHAR8 *)"http://", 7) == 0) start = url + 7; - else if (strncmpa(url, (CHAR8 *)"https://", 8) == 0) + else if (strncmp(url, (CHAR8 *)"https://", 8) == 0) start = url + 8; else return EFI_INVALID_PARAMETER; @@ -571,7 +571,7 @@ receive_http_response(EFI_HTTP_PROTOCOL *http, VOID **buffer, UINT64 *buf_size) /* Check the length of the file */ for (i = 0; i < rx_message.HeaderCount; i++) { - if (!strcmpa(rx_message.Headers[i].FieldName, (CHAR8 *)"Content-Length")) { + if (!strcmp(rx_message.Headers[i].FieldName, (CHAR8 *)"Content-Length")) { *buf_size = ascii_to_int(rx_message.Headers[i].FieldValue); } } diff --git a/include/compiler.h b/include/compiler.h index 3cabd09c..40358a11 100644 --- a/include/compiler.h +++ b/include/compiler.h @@ -179,5 +179,10 @@ #define MIN(a, b) ({(a) < (b) ? (a) : (b);}) #define MAX(a, b) ({(a) <= (b) ? (b) : (a);}) +/** + * Builtins that don't go in string.h + */ +#define unreachable() __builtin_unreachable() + #endif /* !COMPILER_H_ */ // vim:fenc=utf-8:tw=75:et diff --git a/include/endian.h b/include/endian.h new file mode 100644 index 00000000..267fbf00 --- /dev/null +++ b/include/endian.h @@ -0,0 +1,19 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * endian.h - bswap decls that can't go in compiler.h + * Copyright Peter Jones + */ + +#ifndef ENDIAN_H_ +#define ENDIAN_H_ + +#include + +#include "system/builtins_begin_.h" +mkbi1_(uint16_t, bswap16, uint16_t, x) +mkbi1_(uint32_t, bswap32, uint32_t, x) +mkbi1_(uint64_t, bswap64, uint64_t, x) +#include "system/builtins_end_.h" + +#endif /* !ENDIAN_H_ */ +// vim:fenc=utf-8:tw=75:noet diff --git a/include/hexdump.h b/include/hexdump.h index 36d77ec4..a6aa2bfa 100644 --- a/include/hexdump.h +++ b/include/hexdump.h @@ -48,8 +48,6 @@ prepare_hex(const void *data, size_t size, char *buf, unsigned int position) return ret; } -#define isprint(c) ((c) >= 0x20 && (c) <= 0x7e) - static inline void UNUSED prepare_text(const void *data, size_t size, char *buf, unsigned int position) { diff --git a/include/str.h b/include/str.h index c4d12113..189aceff 100644 --- a/include/str.h +++ b/include/str.h @@ -9,122 +9,8 @@ #pragma GCC diagnostic ignored "-Wnonnull-compare" #endif -static inline UNUSED NONNULL(1) unsigned long -strnlena(const CHAR8 *s, unsigned long n) -{ - unsigned long i; - for (i = 0; i < n; i++) - if (s[i] == '\0') - break; - return i; -} - -static inline UNUSED RETURNS_NONNULL NONNULL(1, 2) CHAR8 * -strncpya(CHAR8 *dest, const CHAR8 *src, unsigned long n) -{ - unsigned long i; - - for (i = 0; i < n && src[i] != '\0'; i++) - dest[i] = src[i]; - for (; i < n; i++) - dest[i] = '\0'; - - return dest; -} - -static inline UNUSED RETURNS_NONNULL NONNULL(1, 2) CHAR8 * -strcata(CHAR8 *dest, const CHAR8 *src) -{ - unsigned long dest_len = strlena(dest); - unsigned long i; - - for (i = 0; src[i] != '\0'; i++) - dest[dest_len + i] = src[i]; - dest[dest_len + i] = '\0'; - - return dest; -} - -static inline UNUSED NONNULL(1) CHAR8 * -strdup(const CHAR8 * const src) -{ - UINTN len; - CHAR8 *news = NULL; - - len = strlena(src); - news = AllocateZeroPool(len + 1); - if (news) - strncpya(news, src, len); - return news; -} - -static inline UNUSED NONNULL(1) CHAR8 * -strndupa(const CHAR8 * const src, const UINTN srcmax) -{ - UINTN len; - CHAR8 *news = NULL; - - len = strnlena(src, srcmax); - news = AllocateZeroPool(len + 1); - if (news) - strncpya(news, src, len); - return news; -} - -static inline UNUSED RETURNS_NONNULL NONNULL(1, 2) char * -stpcpy(char *dest, const char * const src) -{ - size_t i = 0; - for (i = 0; src[i]; i++) - dest[i] = src[i]; - dest[i] = '\000'; - return &dest[i]; -} - -static inline UNUSED CHAR8 * -translate_slashes(CHAR8 *out, const char *str) -{ - int i; - int j; - if (str == NULL || out == NULL) - return NULL; - - for (i = 0, j = 0; str[i] != '\0'; i++, j++) { - if (str[i] == '\\') { - out[j] = '/'; - if (str[i+1] == '\\') - i++; - } else - out[j] = str[i]; - } - out[j] = '\0'; - return out; -} - -static inline UNUSED RETURNS_NONNULL NONNULL(1) CHAR8 * -strchrnula(const CHAR8 *s, int c) -{ - unsigned int i; - - for (i = 0; s[i] != '\000' && s[i] != c; i++) - ; - - return (CHAR8 *)&s[i]; -} - -static inline UNUSED NONNULL(1) CHAR8 * -strchra(const CHAR8 *s, int c) -{ - const CHAR8 *s1; - - s1 = strchrnula(s, c); - if (!s1 || s1[0] == '\000') - return NULL; - - return (CHAR8 *)s1; -} - -static inline UNUSED RETURNS_NONNULL NONNULL(1) char * +static inline UNUSED RETURNS_NONNULL NONNULL(1) +char * strnchrnul(const char *s, size_t max, int c) { unsigned int i; diff --git a/include/system/alloca.h b/include/system/alloca.h index dc11b60d..a9d1aab1 100644 --- a/include/system/alloca.h +++ b/include/system/alloca.h @@ -5,6 +5,12 @@ #ifndef _ALLOCA_H #define _ALLOCA_H +#include +mkbi1_(void *, alloca, size_t, size) +#define alloca_with_align(size, alignment) __builtin_alloca_with_align(size, alignment) +#define alloca_with_align_and_max(size, alignment, max) __builtin_alloca_with_align_and_max(size, alignment, max) +#include + #endif /* !_ALLOCA_H */ #endif // vim:fenc=utf-8:tw=75:noet diff --git a/include/system/builtins_begin_.h b/include/system/builtins_begin_.h new file mode 100644 index 00000000..92ea5e3a --- /dev/null +++ b/include/system/builtins_begin_.h @@ -0,0 +1,94 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/** + * macros to build builtin wrappers + */ +#ifndef mkbi_cat_ +#define mkbi_cat_(a, b) a##b +#endif +#ifdef SHIM_STRING_C_ + +#ifndef mkbi1_ +#define mkbi1_(rtype, x, typea, a) __typeof__(mkbi_cat_(__builtin_, x)) x; +#endif +#ifndef mkbi2_ +#define mkbi2_(rtype, x, typea, a, typeb, b) __typeof__(mkbi_cat_(__builtin_, x)) x; +#endif + +#ifndef mkbi3_ +#define mkbi3_(rtype, x, typea, a, typeb, b, typec, c) __typeof__(mkbi_cat_(__builtin_, x)) x; +#endif + +#ifndef mkdepbi1_ +#define mkdepbi1_(rtype, x, typea, a) __typeof__(mkbi_cat_(__builtin_, x)) x; +#endif + +#ifndef mkdepbi2_ +#define mkdepbi2_(rtype, x, typea, a, typeb, b) __typeof__(mkbi_cat_(__builtin_, x)) x; +#endif + +#else /* ! SHIM_STRING_C_ */ + +#ifndef mkbi1_ +#define mkbi1_(rtype, x, typea, a) \ + static inline __attribute__((__unused__)) \ + rtype \ + x(typea a) \ + { \ + return mkbi_cat_(__builtin_, x)(a); \ + } +#endif + +#ifndef mkbi2_ +#define mkbi2_(rtype, x, typea, a, typeb, b) \ + static inline __attribute__((__unused__)) \ + rtype \ + x(typea a, typeb b) \ + { \ + return mkbi_cat_(__builtin_, x)(a, b); \ + } +#endif + +#ifndef mkbi3_ +#define mkbi3_(rtype, x, typea, a, typeb, b, typec, c) \ + static inline __attribute__((__unused__)) \ + rtype \ + x(typea a, typeb b, typec c) \ + { \ + return mkbi_cat_(__builtin_, x)(a, b,c); \ + } +#endif + +#ifdef SHIM_DEPRECATE_STRLEN +#ifndef mkdepbi_dep_ +#define mkdepbi_dep_ __attribute__((__deprecated__)) +#endif +#else /* !SHIM_DEPRECATE_STRLEN */ +#ifndef mkdepbi_dep_ +#define mkdepbi_dep_ +#endif +#endif /* SHIM_DEPRECATE_STRLEN */ + +#ifndef mkdepbi1_ +#define mkdepbi1_(rtype, x, typea, a) \ + static inline __attribute__((__unused__)) \ + mkdepbi_dep_ \ + rtype \ + x(typea a) \ + { \ + return mkbi_cat_(__builtin_, x)(a); \ + } +#endif + +#ifndef mkdepbi2_ +#define mkdepbi2_(rtype, x, typea, a, typeb, b) \ + static inline __attribute__((__unused__)) \ + mkdepbi_dep_ \ + rtype \ + x(typea a, typeb b) \ + { \ + return mkbi_cat_(__builtin_, x)(a, b); \ + } +#endif +#endif /* SHIM_STRING_C_ */ + +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/builtins_end_.h b/include/system/builtins_end_.h new file mode 100644 index 00000000..0a6ad60a --- /dev/null +++ b/include/system/builtins_end_.h @@ -0,0 +1,28 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent + +#ifdef mkbi1_ +#undef mkbi1_ +#endif +#ifdef mkbi2_ +#undef mkbi2_ +#endif +#ifdef mkbi3_ +#undef mkbi3_ +#endif +#ifdef mkdepbi1_ +#undef mkdepbi1_ +#endif +#ifdef mkdepbi2_ +#undef mkdepbi2_ +#endif +#ifdef mkdepbi_dep_ +#undef mkdepbi_dep_ +#endif +#ifdef mkbi_cat_ +#undef mkbi_cat_ +#endif + +#ifdef _BUILTINS_BEGIN__H +#undef _BUILTINS_BEGIN__H +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/ctype.h b/include/system/ctype.h index c771bb69..65e7348f 100644 --- a/include/system/ctype.h +++ b/include/system/ctype.h @@ -3,11 +3,82 @@ * ctype.h - standard ctype functions */ #ifdef SHIM_UNIT_TEST -#include_next +#include_next #else #ifndef _CTYPE_H #define _CTYPE_H +#define isprint(c) ((c) >= 0x20 && (c) <= 0x7e) + +/* Determines if a particular character is a decimal-digit character */ +static inline __attribute__((__unused__)) int +isdigit(int c) +{ + // + // ::= [0-9] + // + return (('0' <= (c)) && ((c) <= '9')); +} + +/* Determine if an integer represents character that is a hex digit */ +static inline __attribute__((__unused__)) int +isxdigit(int c) +{ + // + // ::= [0-9] | [a-f] | [A-F] + // + return ((('0' <= (c)) && ((c) <= '9')) || + (('a' <= (c)) && ((c) <= 'f')) || + (('A' <= (c)) && ((c) <= 'F'))); +} + +/* Determines if a particular character represents a space character */ +static inline __attribute__((__unused__)) int +isspace(int c) +{ + // + // ::= [ ] + // + return ((c) == ' '); +} + +/* Determine if a particular character is an alphanumeric character */ +static inline __attribute__((__unused__)) int +isalnum(int c) +{ + // + // ::= [0-9] | [a-z] | [A-Z] + // + return ((('0' <= (c)) && ((c) <= '9')) || + (('a' <= (c)) && ((c) <= 'z')) || + (('A' <= (c)) && ((c) <= 'Z'))); +} + +/* Determines if a particular character is in upper case */ +static inline __attribute__((__unused__)) int +isupper(int c) +{ + // + // := [A-Z] + // + return (('A' <= (c)) && ((c) <= 'Z')); +} + +/* Convert character to lowercase */ +static inline __attribute__((__unused__)) int +tolower(int c) +{ + if (('A' <= (c)) && ((c) <= 'Z')) { + return (c - ('A' - 'a')); + } + return (c); +} + +static inline __attribute__((__unused__)) int +toupper(int c) +{ + return ((c >= 'a' && c <= 'z') ? c - ('a' - 'A') : c); +} #endif /* !_CTYPE_H */ #endif /* !SHIM_UNIT_TEST */ diff --git a/include/system/stdlib.h b/include/system/stdlib.h index f2660f63..da7d3af9 100644 --- a/include/system/stdlib.h +++ b/include/system/stdlib.h @@ -11,6 +11,18 @@ */ #include +static inline void abort(void) { } + +#include +mkbi1_(int, abs, int, j) +mkbi1_(long int, labs, long int, j) +mkbi1_(long long int, llabs, long long int, j) + +#ifdef _INTTYPES_H +mkbi1_(intmax_t, imaxabs, intmax_t, j) +#endif /* _INTTYPES_H */ +#include + #endif /* !_STDLIB_H */ #endif // vim:fenc=utf-8:tw=75:noet diff --git a/include/system/string.h b/include/system/string.h index 21e46c1d..822e28fa 100644 --- a/include/system/string.h +++ b/include/system/string.h @@ -7,8 +7,55 @@ #include -__typeof__(__builtin_memset) memset; -__typeof__(__builtin_memcpy) memcpy; +#include + +mkbi1_(long int, ffsl, long int, x) +mkbi1_(long int, clzl, long int, x) +mkbi1_(long int, ctzl, long int, x) +mkbi1_(long int, clrsbl, long int, x) +mkbi1_(long int, popcountl, long int, x) +mkbi1_(long int, parityl, long int, x) +mkbi1_(long long int, ffsll, long long int, x) +mkbi1_(long long int, clzll, long long int, x) +mkbi1_(long long int, ctzll, long long int, x) +mkbi1_(long long int, clrsbll, long long int, x) +mkbi1_(long long int, popcountll, long long int, x) +mkbi1_(long long int, parityll, long long int, x) + +mkbi3_(int, bcmp, const void *, s1, const void *, s2, size_t, n) +mkbi3_(void, bcopy, const void *, src, void *, dest, size_t, n) +mkbi2_(void, bzero, void *, s, size_t, n) +mkdepbi2_(char *, index, const char *, s, int, c) +mkbi3_(void *, memchr, const void *, s, int, c, size_t, n) +mkbi3_(int, memcmp, const void *, s1, const void *, s2, size_t, n) +mkbi3_(void *, memcpy, void *, dest, const void *, src, size_t, n) +mkbi3_(void *, memmove, void *, dest, const void *, src, size_t, n) +mkbi3_(void *, mempcpy, void *, dest, const void *, src, size_t, n) +mkdepbi2_(char *, rindex, const char *, s, int, c) +mkdepbi2_(char *, stpcpy, char *, dest, const char *, src) +mkbi3_(char *, stpncpy, char *, dest, const char *, src, size_t, n) +mkdepbi2_(int, strcasecmp, const char *, s1, const char *, s2) +mkdepbi2_(char *, strcat, char *, dest, const char *, src) +mkdepbi2_(char *, strchr, const char *, s, int, c) +mkdepbi2_(int, strcmp, const char *, s1, const char *, s2) +mkdepbi2_(char *, strcpy, char *, dest, const char *, src) +mkdepbi2_(size_t, strcspn, const char *, s, const char *, reject) +mkdepbi1_(char *, strdup, const char *, s) +mkbi2_(char *, strndup, const char *, s, size_t, n) +mkdepbi1_(size_t, strlen, const char *, s) +mkbi3_(int, strncasecmp, const char *, s1, const char *, s2, size_t, n) +mkbi3_(char *, strncat, char *, dest, const char *, src, size_t, n) +mkbi3_(int, strncmp, const char *, s1, const char *, s2, size_t, n) +mkbi3_(char *, strncpy, char *, dest, const char *, src, size_t, n) +mkbi2_(int, strnlen, const char *, s1, size_t, n) +mkdepbi2_(char *, strpbrk, const char *, s, const char *, accept) +mkdepbi2_(char *, strrchr, const char *, s, int, c) +mkdepbi2_(size_t, strspn, const char *, s, const char *, accept) +mkdepbi2_(char *, strstr, const char *, haystack, const char *, needle) + +mkbi3_(void *, memset, void *, s, int, c, size_t, n); + +#include #endif /* _STRING_H */ #endif diff --git a/include/system/strings.h b/include/system/strings.h index c82bd917..99bc05f2 100644 --- a/include/system/strings.h +++ b/include/system/strings.h @@ -5,6 +5,15 @@ #ifndef _STRINGS_H #define _STRINGS_H +#include +mkbi1_(int, ffs, int, x) +mkbi1_(int, clz, int, x) +mkbi1_(int, ctz, int, x) +mkbi1_(int, clrsb, int, x) +mkbi1_(int, popcount, int, x) +mkbi1_(int, parity, int, x) +#include + #endif /* !_STRINGS_H */ #endif // vim:fenc=utf-8:tw=75:noet diff --git a/lib/string.c b/lib/string.c new file mode 100644 index 00000000..1f58f3ec --- /dev/null +++ b/lib/string.c @@ -0,0 +1,245 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * string.c - implementations we need for string finctions + */ +#define SHIM_STRING_C_ +#include "shim.h" + +size_t +strlen(const char *s1) +{ + size_t len; + + for (len = 0; *s1; s1 += 1, len += 1) + ; + return len; +} + +int +strcmp(const char *s1p, const char *s2p) +{ + const uint8_t *s1 = (const uint8_t *)s1p; + const uint8_t *s2 = (const uint8_t *)s2p; + + while (*s1) { + if (*s1 != *s2) { + break; + } + + s1 += 1; + s2 += 1; + } + + return *s1 - *s2; +} + +int +strncmp(const char *s1p, const char *s2p, size_t len) +{ + const uint8_t *s1 = (const uint8_t *)s1p; + const uint8_t *s2 = (const uint8_t *)s2p; + + while (*s1 && len) { + if (*s1 != *s2) { + break; + } + + s1 += 1; + s2 += 1; + len -= 1; + } + + return len ? *s1 - *s2 : 0; +} + +/* Based on AsciiStriCmp() in edk2 MdePkg/Library/BaseLib/String.c */ +int +strncasecmp(const char *s1p, const char *s2p, size_t n) +{ + const uint8_t *s1 = (const uint8_t *)s1p; + const uint8_t *s2 = (const uint8_t *)s2p; + + while (*s1 && n) { + if (toupper(*s1) != toupper(*s2)) { + break; + } + + s1 += 1; + s2 += 1; + n -= 1; + } + + return n ? *s1 - *s2 : 0; +} + +/* Based on AsciiStriCmp() in edk2 MdePkg/Library/BaseLib/String.c */ +int +strcasecmp(const char *str1, const char *str2) +{ + char c1, c2; + + c1 = toupper(*str1); + c2 = toupper(*str2); + while ((*str1 != '\0') && (c1 == c2)) { + str1++; + str2++; + c1 = toupper(*str1); + c2 = toupper(*str2); + } + + return c1 - c2; +} + +/* Scan a string for the last occurrence of a character */ +char * +strrchr(const char *str, int c) +{ + char *save; + + for (save = NULL;; ++str) { + if (*str == c) { + save = (char *)str; + } + if (*str == 0) { + return (save); + } + } +} + +NONNULL(1) +size_t +strnlen(const char *s, size_t n) +{ + size_t i; + for (i = 0; i < n; i++) + if (s[i] == '\0') + break; + return i; +} + +RETURNS_NONNULL NONNULL(1, 2) +char * +strcpy(char *dest, const char *src) +{ + size_t i; + + for (i = 0; src[i] != '\0'; i++) + dest[i] = src[i]; + + dest[i] = '\0'; + return dest; +} + +RETURNS_NONNULL NONNULL(1, 2) +char * +strncpy(char *dest, const char *src, size_t n) +{ + size_t i; + + for (i = 0; i < n && src[i] != '\0'; i++) + dest[i] = src[i]; + for (; i < n; i++) + dest[i] = '\0'; + + return dest; +} + +RETURNS_NONNULL NONNULL(1, 2) +char * +strcat(char *dest, const char *src) +{ + size_t dest_len = strlen(dest); + size_t i; + + for (i = 0; src[i] != '\0'; i++) + dest[dest_len + i] = src[i]; + dest[dest_len + i] = '\0'; + + return dest; +} + +NONNULL(1) +char * +strdup(const char *const src) +{ + size_t len; + char *news = NULL; + + len = strlen(src); + news = AllocateZeroPool(len + 1); + if (news) + strncpy(news, src, len); + return news; +} + +NONNULL(1) +char * +strndup(const char *const src, const size_t srcmax) +{ + size_t len; + char *news = NULL; + + len = strnlen(src, srcmax); + news = AllocateZeroPool(len + 1); + if (news) + strncpy(news, src, len); + return news; +} + +RETURNS_NONNULL NONNULL(1, 2) +char * +stpcpy(char *dest, const char *const src) +{ + size_t i = 0; + for (i = 0; src[i]; i++) + dest[i] = src[i]; + dest[i] = '\000'; + return &dest[i]; +} + +RETURNS_NONNULL NONNULL(1) +char * +strchrnul(const char *s, int c) +{ + unsigned int i; + + for (i = 0; s[i] != '\000' && s[i] != c; i++) + ; + + return (char *)&s[i]; +} + +NONNULL(1) +char * +strchr(const char *s, int c) +{ + const char *s1; + + s1 = strchrnul(s, c); + if (!s1 || s1[0] == '\000') + return NULL; + + return (char *)s1; +} + +char * +translate_slashes(char *out, const char *str) +{ + int i; + int j; + if (str == NULL || out == NULL) + return NULL; + + for (i = 0, j = 0; str[i] != '\0'; i++, j++) { + if (str[i] == '\\') { + out[j] = '/'; + if (str[i + 1] == '\\') + i++; + } else + out[j] = str[i]; + } + out[j] = '\0'; + return out; +} + +// vim:fenc=utf-8:tw=75:noet diff --git a/mok.c b/mok.c index 6bd506be..be477c48 100644 --- a/mok.c +++ b/mok.c @@ -1013,7 +1013,7 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle) struct mok_state_variable *v = &mok_state_variables[i]; ZeroMem(&config_template, sizeof(config_template)); - strncpya(config_template.name, (CHAR8 *)v->rtname8, 255); + strncpy(config_template.name, (CHAR8 *)v->rtname8, 255); config_template.name[255] = '\0'; config_template.data_size = v->data_size; diff --git a/netboot.c b/netboot.c index 450e9def..3f5c5198 100644 --- a/netboot.c +++ b/netboot.c @@ -172,7 +172,7 @@ static BOOLEAN extract_tftp_info(CHAR8 *url) // to check against str2ip6() errors memset(ip6inv, 0, sizeof(ip6inv)); - if (strncmp((UINT8 *)url, (UINT8 *)"tftp://", 7)) { + if (strncmp((const char *)url, (const char *)"tftp://", 7)) { console_print(L"URLS MUST START WITH tftp://\n"); return FALSE; } @@ -258,7 +258,7 @@ static EFI_STATUS parseDhcp4() pkt_v4 = &pxe->Mode->PxeReply.Dhcpv4; } - INTN dir_len = strnlena((CHAR8 *)pkt_v4->BootpBootFile, 127); + INTN dir_len = strnlen((CHAR8 *)pkt_v4->BootpBootFile, 127); INTN i; UINT8 *dir = pkt_v4->BootpBootFile; @@ -274,13 +274,13 @@ static EFI_STATUS parseDhcp4() return EFI_OUT_OF_RESOURCES; if (dir_len > 0) { - strncpya(full_path, (CHAR8 *)dir, dir_len); + strncpy(full_path, (CHAR8 *)dir, dir_len); if (full_path[dir_len-1] == '/' && template[0] == '/') full_path[dir_len-1] = '\0'; } if (dir_len == 0 && dir[0] != '/' && template[0] == '/') template_ofs++; - strcata(full_path, template + template_ofs); + strcat(full_path, template + template_ofs); memcpy(&tftp_addr.v4, pkt_v4->BootpSiAddr, 4); return EFI_SUCCESS; diff --git a/sbat.c b/sbat.c index d8750962..fec22a73 100644 --- a/sbat.c +++ b/sbat.c @@ -48,7 +48,7 @@ parse_sbat_section(char *section_base, size_t section_size, efi_status = EFI_INVALID_PARAMETER; goto err; } - allocsz += strlena(row->columns[i]) + 1; + allocsz += strlen(row->columns[i]) + 1; } n++; } @@ -226,7 +226,7 @@ parse_sbat_var_data(list_t *entry_list, UINT8 *data, UINTN datasize) efi_status = EFI_INVALID_PARAMETER; goto err; } - allocsz += strlena(row->columns[i]) + 1; + allocsz += strlen(row->columns[i]) + 1; } n++; } diff --git a/shim.h b/shim.h index 61dafa82..3d2ac2d4 100644 --- a/shim.h +++ b/shim.h @@ -259,4 +259,6 @@ verify_buffer (char *data, int datasize, #define LogError(fmt, ...) #endif +char *translate_slashes(char *out, const char *str); + #endif /* SHIM_H_ */ -- cgit v1.2.3 From 9beca885c29c77bb901547321a5ce6fd3c9c8ee3 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Tue, 9 Mar 2021 14:40:03 -0500 Subject: Fix stdarg to work the same everywhere. This gets us the same working definition for VA_* va_* etc everywhere, and it's the same definition edk2 is using. Signed-off-by: Peter Jones --- Cryptlib/Include/OpenSslSupport.h | 125 ++++++-------------------------------- Cryptlib/Library/BaseLib.h | 16 +++++ Cryptlib/Makefile | 3 +- Cryptlib/OpenSSL/Makefile | 3 +- Make.defaults | 4 +- errlog.c | 24 ++++---- include/console.h | 2 +- include/hexdump.h | 10 +-- include/system/efistdarg.h | 15 +++++ include/system/stdarg.h | 41 ++++++++----- lib/Makefile | 3 +- lib/console.c | 12 ++-- shim.h | 23 +++++-- 13 files changed, 120 insertions(+), 161 deletions(-) create mode 100644 include/system/efistdarg.h (limited to 'lib') diff --git a/Cryptlib/Include/OpenSslSupport.h b/Cryptlib/Include/OpenSslSupport.h index 6bb7ba64..1f475a32 100644 --- a/Cryptlib/Include/OpenSslSupport.h +++ b/Cryptlib/Include/OpenSslSupport.h @@ -15,6 +15,22 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. #ifndef __OPEN_SSL_SUPPORT_H__ #define __OPEN_SSL_SUPPORT_H__ +#if defined(__x86_64__) +/* shim.h will check if the compiler is new enough in some other CU */ + +#if !defined(GNU_EFI_USE_EXTERNAL_STDARG) +#define GNU_EFI_USE_EXTERNAL_STDARG +#endif + +#if !defined(GNU_EFI_USE_MS_ABI) +#define GNU_EFI_USE_MS_ABI +#endif + +#ifdef NO_BUILTIN_VA_FUNCS +#undef NO_BUILTIN_VA_FUNCS +#endif +#endif + /* * Include stddef.h to avoid redefining "offsetof" */ @@ -64,113 +80,6 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. // typedef VOID *FILE; -// -// Map all va_xxxx elements to VA_xxx defined in MdePkg/Include/Base.h -// -#if !defined(__CC_ARM) || defined(_STDARG_H) // if va_list is not already defined -/* - * These are now unconditionally #defined by GNU_EFI's efistdarg.h, - * so we should #undef them here before providing a new definition. - */ -#undef va_arg -#undef va_start -#undef va_end - -#define va_list VA_LIST -#define va_arg VA_ARG -#define va_start VA_START -#define va_end VA_END - -# if !defined(NO_BUILTIN_VA_FUNCS) - -typedef __builtin_va_list VA_LIST; - -#define VA_START(Marker, Parameter) __builtin_va_start (Marker, Parameter) - -#define VA_ARG(Marker, TYPE) ((sizeof (TYPE) < sizeof (UINTN)) ? (TYPE)(__builtin_va_arg (Marker, UINTN)) : (TYPE)(__builtin_va_arg (Marker, TYPE))) - -#define VA_END(Marker) __builtin_va_end (Marker) - -#define VA_COPY(Dest, Start) __builtin_va_copy (Dest, Start) - -# else - -#define _INT_SIZE_OF(n) ((sizeof (n) + sizeof (UINTN) - 1) &~(sizeof (UINTN) - 1)) -/// -/// Variable used to traverse the list of arguments. This type can vary by -/// implementation and could be an array or structure. -/// -typedef CHAR8 *VA_LIST; - -/** - Retrieves a pointer to the beginning of a variable argument list, based on - the name of the parameter that immediately precedes the variable argument list. - - This function initializes Marker to point to the beginning of the variable - argument list that immediately follows Parameter. The method for computing the - pointer to the next argument in the argument list is CPU-specific following the - EFIAPI ABI. - - @param Marker The VA_LIST used to traverse the list of arguments. - @param Parameter The name of the parameter that immediately precedes - the variable argument list. - - @return A pointer to the beginning of a variable argument list. - -**/ -#define VA_START(Marker, Parameter) (Marker = (VA_LIST) ((UINTN) & (Parameter) + _INT_SIZE_OF (Parameter))) - -/** - Returns an argument of a specified type from a variable argument list and updates - the pointer to the variable argument list to point to the next argument. - - This function returns an argument of the type specified by TYPE from the beginning - of the variable argument list specified by Marker. Marker is then updated to point - to the next argument in the variable argument list. The method for computing the - pointer to the next argument in the argument list is CPU-specific following the EFIAPI ABI. - - @param Marker VA_LIST used to traverse the list of arguments. - @param TYPE The type of argument to retrieve from the beginning - of the variable argument list. - - @return An argument of the type specified by TYPE. - -**/ -#define VA_ARG(Marker, TYPE) (*(TYPE *) ((Marker += _INT_SIZE_OF (TYPE)) - _INT_SIZE_OF (TYPE))) - -/** - Terminates the use of a variable argument list. - - This function initializes Marker so it can no longer be used with VA_ARG(). - After this macro is used, the only way to access the variable argument list is - by using VA_START() again. - - @param Marker VA_LIST used to traverse the list of arguments. - -**/ -#define VA_END(Marker) (Marker = (VA_LIST) 0) - -/** - Initializes a VA_LIST as a copy of an existing VA_LIST. - - This macro initializes Dest as a copy of Start, as if the VA_START macro had been applied to Dest - followed by the same sequence of uses of the VA_ARG macro as had previously been used to reach - the present state of Start. - - @param Dest VA_LIST used to traverse the list of arguments. - @param Start VA_LIST used to traverse the list of arguments. - -**/ -#define VA_COPY(Dest, Start) ((void)((Dest) = (Start))) - -# endif - -#else // __CC_ARM -#define va_start(Marker, Parameter) __va_start(Marker, Parameter) -#define va_arg(Marker, TYPE) __va_arg(Marker, TYPE) -#define va_end(Marker) ((void)0) -#endif - // // #defines from EFI Application Toolkit required to buiild Open SSL // @@ -318,7 +227,7 @@ size_t fwrite (const void *, size_t, size_t, FILE *); char *fgets (char *, int, FILE *); int fputs (const char *, FILE *); int fprintf (FILE *, const char *, ...); -int vfprintf (FILE *, const char *, VA_LIST); +int vfprintf (FILE *, const char *, va_list); int fflush (FILE *); int fclose (FILE *); DIR *opendir (const char *); diff --git a/Cryptlib/Library/BaseLib.h b/Cryptlib/Library/BaseLib.h index 93d5c691..94b25c93 100644 --- a/Cryptlib/Library/BaseLib.h +++ b/Cryptlib/Library/BaseLib.h @@ -1,3 +1,19 @@ +#if defined(__x86_64__) +/* shim.h will check if the compiler is new enough in some other CU */ + +#if !defined(GNU_EFI_USE_EXTERNAL_STDARG) +#define GNU_EFI_USE_EXTERNAL_STDARG +#endif + +#if !defined(GNU_EFI_USE_MS_ABI) +#define GNU_EFI_USE_MS_ABI +#endif + +#ifdef NO_BUILTIN_VA_FUNCS +#undef NO_BUILTIN_VA_FUNCS +#endif +#endif + #include #include diff --git a/Cryptlib/Makefile b/Cryptlib/Makefile index 27614618..547fd106 100644 --- a/Cryptlib/Makefile +++ b/Cryptlib/Makefile @@ -22,8 +22,7 @@ CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) ifeq ($(ARCH),x86_64) FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) -DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ - -DNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 +DEFINES += -DMDE_CPU_X64 endif ifeq ($(ARCH),ia32) FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) diff --git a/Cryptlib/OpenSSL/Makefile b/Cryptlib/OpenSSL/Makefile index 294e889a..1b8ca318 100644 --- a/Cryptlib/OpenSSL/Makefile +++ b/Cryptlib/OpenSSL/Makefile @@ -36,8 +36,7 @@ CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) ifeq ($(ARCH),x86_64) FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone $(CLANG_BUGS) -DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ - -UNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 +DEFINES += -DMDE_CPU_X64 endif ifeq ($(ARCH),ia32) FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) diff --git a/Make.defaults b/Make.defaults index 50164ae8..f956c005 100644 --- a/Make.defaults +++ b/Make.defaults @@ -53,9 +53,7 @@ COMMIT_ID ?= $(shell if [ -e .git ] ; then git log -1 --pretty=format:%H ; elif ifeq ($(ARCH),x86_64) ARCH_CFLAGS ?= -mno-mmx -mno-sse -mno-red-zone -nostdinc \ $(CLANG_BUGS) -m64 \ - -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ - -UNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 \ - -DPAGE_SIZE=4096 + -DMDE_CPU_X64 -DPAGE_SIZE=4096 ARCH_GNUEFI ?= x86_64 ARCH_SUFFIX ?= x64 ARCH_SUFFIX_UPPER ?= X64 diff --git a/errlog.c b/errlog.c index 16af23b0..ac657151 100644 --- a/errlog.c +++ b/errlog.c @@ -10,24 +10,26 @@ static CHAR16 **errs = NULL; static UINTN nerrs = 0; EFI_STATUS EFIAPI -vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, elf_va_list args) +vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, + va_list args) { - elf_va_list args2; + va_list args2; EFI_STATUS efi_status = EFI_SUCCESS; if (verbose) { - elf_va_copy(args2, args); + va_copy(args2, args); console_print(L"%a:%d:%a() ", file, line, func); efi_status = VPrint(fmt, args2); - elf_va_end(args2); + va_end(args2); } return efi_status; } EFI_STATUS EFIAPI -VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, elf_va_list args) +VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, + va_list args) { - elf_va_list args2; + va_list args2; CHAR16 **newerrs; newerrs = ReallocatePool(errs, (nerrs + 1) * sizeof(*errs), @@ -38,11 +40,11 @@ VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, elf_v newerrs[nerrs] = PoolPrint(L"%a:%d %a() ", file, line, func); if (!newerrs[nerrs]) return EFI_OUT_OF_RESOURCES; - elf_va_copy(args2, args); + va_copy(args2, args); newerrs[nerrs+1] = VPoolPrint(fmt, args2); if (!newerrs[nerrs+1]) return EFI_OUT_OF_RESOURCES; - elf_va_end(args2); + va_end(args2); nerrs += 2; newerrs[nerrs] = NULL; @@ -54,12 +56,12 @@ VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, elf_v EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) { - elf_va_list args; + va_list args; EFI_STATUS efi_status; - elf_va_start(args, fmt); + va_start(args, fmt); efi_status = VLogError(file, line, func, fmt, args); - elf_va_end(args); + va_end(args); return efi_status; } diff --git a/include/console.h b/include/console.h index d8af3cd3..00982744 100644 --- a/include/console.h +++ b/include/console.h @@ -102,7 +102,7 @@ extern UINT32 verbose; dprint_(L"%a:%d:%a() " fmt, __FILE__, __LINE__ - 1, __func__, \ ##__VA_ARGS__) extern EFI_STATUS EFIAPI vdprint_(const CHAR16 *fmt, const char *file, int line, - const char *func, elf_va_list args); + const char *func, va_list args); #define vdprint(fmt, ...) \ vdprint_(fmt, __FILE__, __LINE__ - 1, __func__, ##__VA_ARGS__) diff --git a/include/hexdump.h b/include/hexdump.h index a6aa2bfa..f778de9a 100644 --- a/include/hexdump.h +++ b/include/hexdump.h @@ -81,7 +81,7 @@ prepare_text(const void *data, size_t size, char *buf, unsigned int position) */ static inline void UNUSED EFIAPI vhexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, - const void *data, unsigned long size, size_t at, elf_va_list ap) + const void *data, unsigned long size, size_t at, va_list ap) { unsigned long display_offset = at; unsigned long offset = 0; @@ -114,15 +114,15 @@ vhexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, * hexdump formatted * think of it as: printf("%s%s", format(fmt, ...), hexdump(data,size)[lineN]); */ -static inline void UNUSED +static inline void UNUSED EFIAPI hexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, const void *data, unsigned long size, size_t at, ...) { - elf_va_list ap; + va_list ap; - elf_va_start(ap, at); + va_start(ap, at); vhexdumpf(file, line, func, fmt, data, size, at, ap); - elf_va_end(ap); + va_end(ap); } static inline void UNUSED diff --git a/include/system/efistdarg.h b/include/system/efistdarg.h new file mode 100644 index 00000000..837c4f23 --- /dev/null +++ b/include/system/efistdarg.h @@ -0,0 +1,15 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * efistdarg.h - AAAARGGGG + * Copyright Peter Jones + */ + +#ifndef SHIM_UNIT_TEST +#ifndef _EFISTDARG_H_ +#define _EFISTDARG_H_ + +#include + +#endif /* !_EFISTDARG_H_ */ +#endif +// vim:fenc=utf-8:tw=75:noet diff --git a/include/system/stdarg.h b/include/system/stdarg.h index 346b760d..af1ac59b 100644 --- a/include/system/stdarg.h +++ b/include/system/stdarg.h @@ -8,24 +8,33 @@ #ifndef _STDARG_H #define _STDARG_H -#include - -#endif /* !_STDARG_H */ +#ifndef GNU_EFI_USE_EXTERNAL_STDARG +#define GNU_EFI_USE_EXTERNAL_STDARG #endif -#ifndef SHIM_STDARG_H_ -#define SHIM_STDARG_H_ -typedef __builtin_ms_va_list ms_va_list; -#define ms_va_copy(dest, start) __builtin_ms_va_copy(dest, start) -#define ms_va_start(marker, arg) __builtin_ms_va_start(marker, arg) -#define ms_va_arg(marker, type) __builtin_va_arg(marker, type) -#define ms_va_end(marker) __builtin_ms_va_end(marker) +#if defined(__aarch64__) || defined(__arm__) || defined(__i386__) || \ + defined(__i486__) || defined(__i686__) || defined(SHIM_UNIT_TEST) +typedef __builtin_va_list va_list; +#define va_copy(dest, start) __builtin_va_copy(dest, start) +#define va_start(marker, arg) __builtin_va_start(marker, arg) +#define va_arg(marker, type) __builtin_va_arg(marker, type) +#define va_end(marker) __builtin_va_end(marker) +#elif defined(__x86_64__) +typedef __builtin_ms_va_list va_list; +#define va_copy(dest, start) __builtin_ms_va_copy(dest, start) +#define va_start(marker, arg) __builtin_ms_va_start(marker, arg) +#define va_arg(marker, type) __builtin_va_arg(marker, type) +#define va_end(marker) __builtin_ms_va_end(marker) +#else +#error what arch is this +#endif -typedef __builtin_va_list elf_va_list; -#define elf_va_copy(dest, start) __builtin_va_copy(dest, start) -#define elf_va_start(marker, arg) __builtin_va_start(marker, arg) -#define elf_va_arg(marker, type) __builtin_va_arg(marker, type) -#define elf_va_end(marker) __builtin_va_end(marker) +typedef va_list VA_LIST; +#define VA_COPY(dest, start) va_copy(dest, start) +#define VA_START(marker, arg) va_start(marker, arg) +#define VA_END(marker) va_end(marker) +#define VA_ARG(marker, type) va_arg(marker, type) -#endif /* !SHIM_STDARG_H_ */ +#endif /* !_STDARG_H */ +#endif /* !SHIM_UNIT_TEST */ // vim:fenc=utf-8:tw=75:noet diff --git a/lib/Makefile b/lib/Makefile index 63893c3e..0d2d0a9d 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -17,8 +17,7 @@ CLANG_BUGS = $(if $(findstring gcc,$(CC)),-maccumulate-outgoing-args,) ifeq ($(ARCH),x86_64) FEATUREFLAGS += -m64 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) -DEFINES += -DEFI_FUNCTION_WRAPPER -DGNU_EFI_USE_MS_ABI \ - -UNO_BUILTIN_VA_FUNCS -DMDE_CPU_X64 +DEFINES += -DMDE_CPU_X64 endif ifeq ($(ARCH),ia32) FEATUREFLAGS += -m32 -mno-mmx -mno-sse -mno-red-zone -nostdinc $(CLANG_BUGS) diff --git a/lib/console.c b/lib/console.c index 32c6d55d..2da20b31 100644 --- a/lib/console.c +++ b/lib/console.c @@ -86,15 +86,15 @@ VOID console_fini(VOID) UINTN EFIAPI console_print(const CHAR16 *fmt, ...) { - elf_va_list args; + va_list args; UINTN ret; if (!console_text_mode) setup_console(1); - elf_va_start(args, fmt); + va_start(args, fmt); ret = VPrint(fmt, args); - elf_va_end(args); + va_end(args); return ret; } @@ -103,7 +103,7 @@ UINTN EFIAPI console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) { SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut; - elf_va_list args; + va_list args; UINTN ret; if (!console_text_mode) @@ -111,9 +111,9 @@ console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) co->SetCursorPosition(co, col, row); - elf_va_start(args, fmt); + va_start(args, fmt); ret = VPrint(fmt, args); - elf_va_end(args); + va_end(args); return ret; } diff --git a/shim.h b/shim.h index 3d2ac2d4..0ea182eb 100644 --- a/shim.h +++ b/shim.h @@ -17,20 +17,29 @@ #endif #if defined(__x86_64__) -#if !defined(GNU_EFI_USE_MS_ABI) -#error On x86_64 you must use ms_abi (GNU_EFI_USE_MS_ABI) in gnu-efi and shim. -#endif /* gcc 4.5.4 is the first documented release with -mabi=ms */ #if !GNUC_PREREQ(4, 7) && !CLANG_PREREQ(3, 4) #error On x86_64 you must have a compiler new enough to support __attribute__((__ms_abi__)) #endif + +#if !defined(GNU_EFI_USE_EXTERNAL_STDARG) +#define GNU_EFI_USE_EXTERNAL_STDARG +#endif + +#if !defined(GNU_EFI_USE_MS_ABI) +#define GNU_EFI_USE_MS_ABI +#endif + +#ifdef NO_BUILTIN_VA_FUNCS +#undef NO_BUILTIN_VA_FUNCS +#endif #endif #include #include #include #include -#include +#include #include #include @@ -40,6 +49,10 @@ #undef uefi_call_wrapper #include #include + +#if defined(__x86_64__) && !defined(HAVE_USE_MS_ABI) +#error something has gone wrong with the gnu-efi includes and defines +#endif #endif #ifdef SHIM_UNIT_TEST @@ -209,7 +222,7 @@ extern void shim_fini(void); extern EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...); extern EFI_STATUS EFIAPI VLogError(const char *file, int line, const char *func, - const CHAR16 *fmt, elf_va_list args); + const CHAR16 *fmt, va_list args); extern VOID LogHexdump_(const char *file, int line, const char *func, const void *data, size_t sz); extern VOID PrintErrors(VOID); -- cgit v1.2.3 From bbdfa72a0a5f8d5a8dd4a47e67195504a22ece5b Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Tue, 9 Mar 2021 11:56:31 -0500 Subject: Add some test cases, and make "make test" actually work. Note the one test case I'm not 100% sure about. Someone let me know. Signed-off-by: Peter Jones --- include/console.h | 6 ++ include/system/string.h | 17 +++++ include/test.h | 47 +++++++++++++ include/test.mk | 1 + lib/string.c | 17 +++++ shim.h | 4 ++ test-sbat.c | 47 ++++++------- test-str.c | 170 ++++++++++++++++++++++++++++++++++++++++++++++-- 8 files changed, 283 insertions(+), 26 deletions(-) (limited to 'lib') diff --git a/include/console.h b/include/console.h index 00982744..036262ef 100644 --- a/include/console.h +++ b/include/console.h @@ -92,6 +92,7 @@ struct _EFI_CONSOLE_CONTROL_PROTOCOL { extern VOID console_fini(VOID); extern VOID setup_verbosity(VOID); extern UINT32 verbose; +#ifndef SHIM_UNIT_TEST #define dprint_(fmt, ...) ({ \ UINTN __dprint_ret = 0; \ if (verbose) \ @@ -101,6 +102,11 @@ extern UINT32 verbose; #define dprint(fmt, ...) \ dprint_(L"%a:%d:%a() " fmt, __FILE__, __LINE__ - 1, __func__, \ ##__VA_ARGS__) +#else +#define dprint_(...) +#define dprint(fmt, ...) +#endif + extern EFI_STATUS EFIAPI vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, va_list args); #define vdprint(fmt, ...) \ diff --git a/include/system/string.h b/include/system/string.h index 822e28fa..66e7d93e 100644 --- a/include/system/string.h +++ b/include/system/string.h @@ -1,6 +1,23 @@ // SPDX-License-Identifier: BSD-2-Clause-Patent #ifdef SHIM_UNIT_TEST #include_next + +__typeof__(strlen) shim_strlen; +__typeof__(strcmp) shim_strcmp; +__typeof__(strncmp) shim_strncmp; +__typeof__(strncasecmp) shim_strncasecmp; +__typeof__(strcasecmp) shim_strcasecmp; +__typeof__(strrchr) shim_strrchr; +__typeof__(strrchr) shim_strrchr; +__typeof__(strnlen) shim_strnlen; +__typeof__(strcpy) shim_strcpy; +__typeof__(strncpy) shim_strncpy; +__typeof__(strdup) shim_strdup; +__typeof__(strndup) shim_strndup; +__typeof__(stpcpy) shim_stpcpy; +__typeof__(strchrnul) shim_strchrnul; +__typeof__(strchr) shim_strchr; + #else #ifndef _STRING_H #define _STRING_H diff --git a/include/test.h b/include/test.h index 8a970fd2..4441f969 100644 --- a/include/test.h +++ b/include/test.h @@ -63,6 +63,53 @@ extern int debug; assert(cond); \ }) +#define assert_true_return(a, status, fmt, ...) \ + ({ \ + if (!(a)) { \ + printf("%s:%d:got %lld, expected nonzero " fmt, \ + __func__, __LINE__, (long long)(a), \ + ##__VA_ARGS__); \ + printf("%s:%d:Assertion `%s' failed.\n", __func__, \ + __LINE__, __stringify(!(a))); \ + return status; \ + } \ + }) +#define assert_nonzero_return(a, ...) assert_true_return(a, ##__VA_ARGS__) + +#define assert_false_return(a, status, fmt, ...) \ + ({ \ + if (a) { \ + printf("%s:%d:got %lld, expected zero " fmt, __func__, \ + __LINE__, (long long)(a), ##__VA_ARGS__); \ + printf("%s:%d:Assertion `%s' failed.\n", __func__, \ + __LINE__, __stringify(a)); \ + return status; \ + } \ + }) +#define assert_zero_return(a, ...) assert_false_return(a, ##__VA_ARGS__) + +#define assert_positive_return(a, status, fmt, ...) \ + ({ \ + if ((a) <= 0) { \ + printf("%s:%d:got %lld, expected > 0 " fmt, __func__, \ + __LINE__, (long long)(a), ##__VA_ARGS__); \ + printf("%s:%d:Assertion `%s' failed.\n", __func__, \ + __LINE__, __stringify((a) <= 0)); \ + return status; \ + } \ + }) + +#define assert_negative_return(a, status, fmt, ...) \ + ({ \ + if ((a) >= 0) { \ + printf("%s:%d:got %lld, expected < 0 " fmt, __func__, \ + __LINE__, (long long)(a), ##__VA_ARGS__); \ + printf("%s:%d:Assertion `%s' failed.\n", __func__, \ + __LINE__, __stringify((a) >= 0)); \ + return status; \ + } \ + }) + #define assert_equal_return(a, b, status, fmt, ...) \ ({ \ if (!((a) == (b))) { \ diff --git a/include/test.mk b/include/test.mk index 735d0dc5..542be176 100644 --- a/include/test.mk +++ b/include/test.mk @@ -35,6 +35,7 @@ test-random.h: xxd -i random.bin test-random.h test-sbat_FILES = csv.c +test-str_FILES = lib/string.c tests := $(patsubst %.c,%,$(wildcard test-*.c)) diff --git a/lib/string.c b/lib/string.c index 1f58f3ec..3dc6f1cd 100644 --- a/lib/string.c +++ b/lib/string.c @@ -5,6 +5,23 @@ #define SHIM_STRING_C_ #include "shim.h" +#ifdef SHIM_UNIT_TEST +#define strlen shim_strlen +#define strcmp shim_strcmp +#define strncmp shim_strncmp +#define strncasecmp shim_strncasecmp +#define strcasecmp shim_strcasecmp +#define strrchr shim_strrchr +#define strlen shim_strlen +#define strcpy shim_strcpy +#define strncpy shim_strncpy +#define strdup shim_strdup +#define strndup shim_strndup +#define stpcpy shim_stpcpy +#define strchrnul shim_strchrnul +#define strchr shim_strchr +#endif + size_t strlen(const char *s1) { diff --git a/shim.h b/shim.h index 0ea182eb..44dddc7a 100644 --- a/shim.h +++ b/shim.h @@ -3,6 +3,10 @@ #ifndef SHIM_H_ #define SHIM_H_ +#ifdef SHIM_UNIT_TEST +#define _GNU_SOURCE +#endif + #if defined __GNUC__ && defined __GNUC_MINOR__ # define GNUC_PREREQ(maj, min) \ ((__GNUC__ << 16) + __GNUC_MINOR__ >= ((maj) << 16) + (min)) diff --git a/test-sbat.c b/test-sbat.c index c671f03e..780e5cbe 100644 --- a/test-sbat.c +++ b/test-sbat.c @@ -427,26 +427,29 @@ test_parse_sbat_var_data(void) return 0; } -#if 0 /* * verify_sbat() tests * Note: verify_sbat also frees the underlying "sbat_entries" memory. */ int -test_verify_sbat_null_sbat(void) +test_verify_sbat_null_sbat_section(void) { - list_t *test_sbat_entries; - test_sbat_entries = create_mock_sbat_entries_one_entry("test1", "1"); - if (!test_sbat_entries) - return -1; + char sbat_var_data[] = "test1,1"; EFI_STATUS status; + list_t test_sbat_var; + size_t n = 0; + struct sbat_section_entry **entries = NULL; - status = verify_sbat(NULL, test_sbat_entries); + INIT_LIST_HEAD(&test_sbat_var); + status = parse_sbat_var_data(&test_sbat_var, sbat_var_data, sizeof(sbat_var_data)); + assert_equal_return(status, EFI_SUCCESS, -1, "got %#x expected %#x\n"); - assert(status == EFI_INVALID_PARAMETER); + status = verify_sbat_helper(&sbat_var, n, entries); + assert_equal_return(status, EFI_SUCCESS, -1, "got %#x expected %#x\n"); return 0; } +#if 0 int test_verify_sbat_null_sbat_entries(void) { @@ -969,22 +972,22 @@ main(void) test(test_parse_sbat_var_data_null_data); test(test_parse_sbat_var_data_zero_size); -#if 0 // verify_sbat tests - //test_verify_sbat_null_sbat(); - test_verify_sbat_null_sbat_entries(); - test_verify_sbat_match_one_exact(); - test_verify_sbat_match_one_higher(); - test_verify_sbat_reject_one(); - test_verify_sbat_reject_many(); - test_verify_sbat_match_many_higher(); - test_verify_sbat_match_many_exact(); - test_verify_sbat_reject_many_all(); - test_verify_sbat_match_diff_name(); - test_verify_sbat_match_diff_name_mixed(); - test_verify_sbat_reject_diff_name_mixed(); + test(test_verify_sbat_null_sbat_section); +#if 0 + test(test_verify_sbat_null_sbat_entries); + test(test_verify_sbat_match_one_exact); + test(test_verify_sbat_match_one_higher); + test(test_verify_sbat_reject_one); + test(test_verify_sbat_reject_many); + test(test_verify_sbat_match_many_higher); + test(test_verify_sbat_match_many_exact); + test(test_verify_sbat_reject_many_all); + test(test_verify_sbat_match_diff_name); + test(test_verify_sbat_match_diff_name_mixed); + test(test_verify_sbat_reject_diff_name_mixed); #endif - test_parse_and_verify(); + test(test_parse_and_verify); return 0; } diff --git a/test-str.c b/test-str.c index 8befa223..39b6d07a 100644 --- a/test-str.c +++ b/test-str.c @@ -13,15 +13,39 @@ #pragma GCC diagnostic ignored "-Wunused-variable" #pragma GCC diagnostic error "-Wnonnull" +/* + * copy-pasta from gnu-efi + */ +static inline UINTN +strncmpa ( + IN CONST CHAR8 *s1, + IN CONST CHAR8 *s2, + IN UINTN len + ) +// compare strings +{ + while (*s1 && len) { + if (*s1 != *s2) { + break; + } + + s1 += 1; + s2 += 1; + len -= 1; + } + + return len ? *s1 - *s2 : 0; +} + int test_strchrnul(void) { const char s0[] = "abcd\0fghi"; - assert_equal_return(strchrnul(s0, 'a'), &s0[0], -1, "got %p expected %p\n"); - assert_equal_return(strchrnul(s0, 'd'), &s0[3], -1, "got %p expected %p\n"); - assert_equal_return(strchrnul(s0, '\000'), &s0[4], -1, "got %p expected %p\n"); - assert_equal_return(strchrnul(s0, 'i'), &s0[4], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchrnul(s0, 'a'), &s0[0], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchrnul(s0, 'd'), &s0[3], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchrnul(s0, '\000'), &s0[4], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchrnul(s0, 'i'), &s0[4], -1, "got %p expected %p\n"); assert_equal_return(strnchrnul(s0, 0, 'b'), &s0[0], -1, "got %p expected %p\n"); assert_equal_return(strnchrnul(s0, -1, 'b'), &s0[1], 1, "got %p expected %p\n"); @@ -35,6 +59,143 @@ test_strchrnul(void) return 0; } +int +test_strncmp(void) +{ + /* + * these are constants so that the failures are readable if you get + * it wrong. + */ +#define s0 "sbat," +#define s0sz 6 +#define s0len 5 +#define s1 "sbat,1,2021030218" +#define s1sz 18 +#define s1len 17 +#define s2 "sbat,1,20210302" +#define s2sz 16 +#define s2len 15 +#define s3 "sbat,1,20210303" +#define s3sz 16 +#define s3len 15 + + int diff; + + assert_zero_return(strncmp(s0, s0, s0len), -1, "\n"); + assert_zero_return(strncmp(s0, s0, s0sz), -1, "\n"); + + assert_zero_return(strncmp(s0, s1, s0len), -1, "\n"); + assert_negative_return(strncmp(s0, s1, s0sz), -1, "\n"); + assert_equal_return(strncmp(s0, s1, s0sz), s0[s0len] - s1[s0len] , -1, "expected %d got %d\n"); + assert_positive_return(strncmp(s1, s0, s0sz), -1, "\n"); + assert_equal_return(strncmp(s1, s0, s0sz), s1[s0len] - s0[s0len] , -1, "expected %d got %d\n"); + + assert_positive_return(strncmp(s1, s2, s1sz), -1, "\n"); + assert_equal_return(strncmp(s1, s2, s2sz), s1[s2len] - s2[s2len] , -1, "expected %d got %d\n"); + assert_positive_return(strncmp(s1, s2, s1len), -1, "\n"); + assert_equal_return(strncmp(s1, s2, s2len), s1[s2len-1] - s2[s2len-1] , -1, "expected %d got %d\n"); + assert_negative_return(strncmp(s2, s1, s1sz), -1, "\n"); + assert_equal_return(strncmp(s2, s1, s1sz), s2[s2len] - s1[s2len] , -1, "expected %d got %d\n"); + + assert_zero_return(strncmp(s1, s2, s2len), -1, "\n"); + assert_positive_return(strncmp(s1, s2, s2sz), -1, "\n"); + assert_equal_return(strncmp(s1, s2, s2sz), s1[s2len] - s2[s2len] , -1, "expected %d got %d\n"); + + assert_negative_return(strncmp(s2, s3, s2sz), -1, "\n"); + assert_equal_return(strncmp(s2, s3, s2sz), s2[s2len-1] - s3[s2len-1] , -1, "expected %d got %d\n"); + assert_equal_return(strncmp(s2, s3, s2len), s2[s2len-1] - s3[s2len-1] , -1, "expected %d got %d\n"); + assert_negative_return(strncmp(s2, s3, s2len), -1, "\n"); + assert_zero_return(strncmp(s2, s3, s2len - 1), -1, "\n"); + assert_false_return(strncmp(s1, s2, s2len), -1, "\n"); + + /* + * Now test gnu-efi's version, but with a cast back to a sane type + */ +#define strncmpa(a, b, c) ((INTN)strncmpa(a, b, c)) + + assert_zero_return(strncmpa(s0, s0, s0len), -1, "\n"); + assert_zero_return(strncmpa(s0, s0, s0sz), -1, "\n"); + + assert_zero_return(strncmpa(s0, s1, s0len), -1, "\n"); + assert_negative_return(strncmpa(s0, s1, s0sz), -1, "\n"); + assert_equal_return(strncmpa(s0, s1, s0sz), s0[s0len] - s1[s0len] , -1, "expected %d got %d\n"); + assert_positive_return(strncmpa(s1, s0, s0sz), -1, "\n"); + assert_equal_return(strncmpa(s1, s0, s0sz), s1[s0len] - s0[s0len] , -1, "expected %d got %d\n"); + + assert_positive_return(strncmpa(s1, s2, s1sz), -1, "\n"); + assert_equal_return(strncmpa(s1, s2, s2sz), s1[s2len] - s2[s2len] , -1, "expected %d got %d\n"); + assert_positive_return(strncmpa(s1, s2, s1len), -1, "\n"); + assert_equal_return(strncmpa(s1, s2, s2len), s1[s2len-1] - s2[s2len-1] , -1, "expected %d got %d\n"); + assert_negative_return(strncmpa(s2, s1, s1sz), -1, "\n"); + assert_equal_return(strncmpa(s2, s1, s1sz), s2[s2len] - s1[s2len] , -1, "expected %d got %d\n"); + + assert_zero_return(strncmpa(s1, s2, s2len), -1, "\n"); + assert_positive_return(strncmpa(s1, s2, s2sz), -1, "\n"); + assert_equal_return(strncmpa(s1, s2, s2sz), s1[s2len] - s2[s2len] , -1, "expected %d got %d\n"); + + assert_negative_return(strncmpa(s2, s3, s2sz), -1, "\n"); + assert_equal_return(strncmpa(s2, s3, s2sz), s2[s2len-1] - s3[s2len-1] , -1, "expected %d got %d\n"); + assert_equal_return(strncmpa(s2, s3, s2len), s2[s2len-1] - s3[s2len-1] , -1, "expected %d got %d\n"); + assert_negative_return(strncmpa(s2, s3, s2len), -1, "\n"); + assert_zero_return(strncmpa(s2, s3, s2len - 1), -1, "\n"); + assert_false_return(strncmpa(s1, s2, s2len), -1, "\n"); + + + /* + * Once more, but with the casting /and the warnings/ turned off + * + * The ones marked with XXX I've inverted the test to make it work + * "correctly", because UINTN is what makes positive. + */ +#undef strncmpa +#pragma GCC diagnostic ignored "-Wtype-limits" +#pragma GCC diagnostic ignored "-Wsign-compare" + + assert_zero_return(strncmpa(s0, s0, s0len), -1, "\n"); + assert_zero_return(strncmpa(s0, s0, s0sz), -1, "\n"); + + assert_zero_return(strncmpa(s0, s1, s0len), -1, "\n"); + /*XXX*/assert_positive_return(strncmpa(s0, s1, s0sz), -1, "\n");/*XXX*/ + assert_equal_return(strncmpa(s0, s1, s0sz), s0[s0len] - s1[s0len] , -1, "expected %d got %d\n"); + assert_positive_return(strncmpa(s1, s0, s0sz), -1, "\n"); + assert_equal_return(strncmpa(s1, s0, s0sz), s1[s0len] - s0[s0len] , -1, "expected %d got %d\n"); + + assert_positive_return(strncmpa(s1, s2, s1sz), -1, "\n"); + assert_equal_return(strncmpa(s1, s2, s2sz), s1[s2len] - s2[s2len] , -1, "expected %d got %d\n"); + assert_positive_return(strncmpa(s1, s2, s1len), -1, "\n"); + assert_equal_return(strncmpa(s1, s2, s2len), s1[s2len-1] - s2[s2len-1] , -1, "expected %d got %d\n"); + /*XXX*/ assert_positive_return(strncmpa(s2, s1, s1sz), -1, "\n");/*XXX*/ + assert_equal_return(strncmpa(s2, s1, s1sz), s2[s2len] - s1[s2len] , -1, "expected %d got %d\n"); + + assert_zero_return(strncmpa(s1, s2, s2len), -1, "\n"); + assert_positive_return(strncmpa(s1, s2, s2sz), -1, "\n"); + assert_equal_return(strncmpa(s1, s2, s2sz), s1[s2len] - s2[s2len] , -1, "expected %d got %d\n"); + + assert_positive_return(strncmpa(s2, s3, s2sz), -1, "\n"); + assert_equal_return(strncmpa(s2, s3, s2sz), s2[s2len-1] - s3[s2len-1] , -1, "expected %d got %d\n"); + assert_equal_return(strncmpa(s2, s3, s2len), s2[s2len-1] - s3[s2len-1] , -1, "expected %d got %d\n"); + /*XXX*/assert_positive_return(strncmpa(s2, s3, s2len), -1,"\n");/*XXX*/ + assert_zero_return(strncmpa(s2, s3, s2len - 1), -1, "\n"); + assert_false_return(strncmpa(s1, s2, s2len), -1, "\n"); + +#pragma GCC diagnostic error "-Wsign-compare" +#pragma GCC diagnostic error "-Wtype-limits" + return 0; + +#undef s0 +#undef s0sz +#undef s0len +#undef s1 +#undef s1sz +#undef s1len +#undef s2 +#undef s2sz +#undef s2len +#undef s3 +#undef s3sz +#undef s3len +} + int test_strntoken_null(void) { bool ret; @@ -416,6 +577,7 @@ main(void) { int status = 0; test(test_strchrnul); + test(test_strncmp); test(test_strntoken_null); test(test_strntoken_size_0); test(test_strntoken_empty_size_1); -- cgit v1.2.3 From c722a590d08506f29ddb70c1c57c511a836efb7a Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Wed, 10 Mar 2021 14:26:46 -0500 Subject: Add more string test cases. This adds test cases for the rest of our ASCII string functions. While doing so, it fixes two minor bugs: - strcasecmp() now handles utf8 correctly - strncpy() no longer does the stpncpy() behavior of clearing leftover buffer Signed-off-by: Peter Jones --- include/test.h | 14 + lib/string.c | 5 +- test-str.c | 911 ++++++++++++++++++++++++++++++++++++++++++++++++++++----- 3 files changed, 854 insertions(+), 76 deletions(-) (limited to 'lib') diff --git a/include/test.h b/include/test.h index 92d1314e..012ffc51 100644 --- a/include/test.h +++ b/include/test.h @@ -213,6 +213,20 @@ extern int debug; } \ }) +#define assert_negative_goto(a, label, fmt, ...) \ + ({ \ + int rc_ = assert_negative_as_expr(a, -1, fmt, ##__VA_ARGS__); \ + if (rc_ != 0) \ + goto label; \ + }) + +#define assert_positive_goto(a, label, fmt, ...) \ + ({ \ + int rc_ = assert_positive_as_expr(a, -1, fmt, ##__VA_ARGS__); \ + if (rc_ != 0) \ + goto label; \ + }) + #define test(x, ...) \ ({ \ int rc; \ diff --git a/lib/string.c b/lib/string.c index 3dc6f1cd..37eabe8c 100644 --- a/lib/string.c +++ b/lib/string.c @@ -13,6 +13,7 @@ #define strcasecmp shim_strcasecmp #define strrchr shim_strrchr #define strlen shim_strlen +#define strnlen shim_strnlen #define strcpy shim_strcpy #define strncpy shim_strncpy #define strdup shim_strdup @@ -93,7 +94,7 @@ strncasecmp(const char *s1p, const char *s2p, size_t n) int strcasecmp(const char *str1, const char *str2) { - char c1, c2; + uint8_t c1, c2; c1 = toupper(*str1); c2 = toupper(*str2); @@ -155,7 +156,7 @@ strncpy(char *dest, const char *src, size_t n) for (i = 0; i < n && src[i] != '\0'; i++) dest[i] = src[i]; - for (; i < n; i++) + if (i < n) dest[i] = '\0'; return dest; diff --git a/test-str.c b/test-str.c index deb753d9..d0d6832b 100644 --- a/test-str.c +++ b/test-str.c @@ -2,6 +2,9 @@ /* * test-str.c - test our string functions. */ +#pragma GCC diagnostic ignored "-Wunused-variable" +#pragma GCC diagnostic error "-Wnonnull" +#pragma GCC diagnostic error "-Wunused-function" #ifndef SHIM_UNIT_TEST #define SHIM_UNIT_TEST @@ -10,43 +13,448 @@ #include -#pragma GCC diagnostic ignored "-Wunused-variable" -#pragma GCC diagnostic error "-Wnonnull" - -int -test_strchrnul_helper(__typeof__(strchrnul) fn) +static int +test_strlen(void) { - const char s0[] = "abcd\0fghi"; + const char s1[] = "abcd"; + const char s2[] = ""; - assert_equal_return(fn(s0, 'a'), &s0[0], -1, "got %p expected %p\n"); - assert_equal_return(fn(s0, 'd'), &s0[3], -1, "got %p expected %p\n"); - assert_equal_return(fn(s0, '\000'), &s0[4], -1, "got %p expected %p\n"); - assert_equal_return(fn(s0, 'i'), &s0[4], -1, "got %p expected %p\n"); + assert_equal_return(shim_strlen(s1), 4, -1, "got %d expected %d\n"); + assert_equal_return(strlen(s1), 4, -1, "got %d expected %d\n"); + assert_equal_return(shim_strlen(s2), 0, -1, "got %d expected %d\n"); + assert_equal_return(strlen(s2), 0, -1, "got %d expected %d\n"); return 0; } -int -test_strchrnul(void) +static int +test_strnlen(void) { - const char s0[] = "abcd\0fghi"; + const char s1[] = "abcd"; + const char s2[] = ""; + + assert_equal_return(shim_strnlen(s1, 0), 0, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s1, 0), 0, -1, "got %d expected %d\n"); + assert_equal_return(shim_strnlen(s1, 1), 1, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s1, 1), 1, -1, "got %d expected %d\n"); + assert_equal_return(shim_strnlen(s1, 3), 3, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s1, 3), 3, -1, "got %d expected %d\n"); + assert_equal_return(shim_strnlen(s1, 4), 4, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s1, 4), 4, -1, "got %d expected %d\n"); + assert_equal_return(shim_strnlen(s1, 5), 4, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s1, 5), 4, -1, "got %d expected %d\n"); + assert_equal_return(shim_strnlen(s2, 0), 0, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s2, 0), 0, -1, "got %d expected %d\n"); + assert_equal_return(shim_strnlen(s2, 1), 0, -1, "got %d expected %d\n"); + assert_equal_return(strnlen(s2, 1), 0, -1, "got %d expected %d\n"); - assert_equal_return(test_strchrnul_helper(shim_strchrnul), - test_strchrnul_helper(strchrnul), - -1, "got %d expected %d\n"); + return 0; +} - assert_equal_return(strnchrnul(s0, 0, 'b'), &s0[0], -1, "got %p expected %p\n"); - assert_equal_return(strnchrnul(s0, -1, 'b'), &s0[1], 1, "got %p expected %p\n"); - assert_equal_return(strnchrnul(s0, 2, 'b'), &s0[1], -1, "got %p expected %p\n"); - assert_equal_return(strnchrnul(s0, 4, 'f'), &s0[3], -1, "got %p expected %p\n"); - assert_equal_return(strnchrnul(s0, 5, 'f'), &s0[4], -1, "got %p expected %p\n"); - assert_equal_return(strnchrnul(s0, 8, 'f'), &s0[4], -1, "got %p expected %p\n"); +#pragma GCC diagnostic push +#pragma GCC diagnostic ignored "-Wshadow" - assert_equal_return(strnchrnul(&s0[4], 1, 'f'), &s0[4], -1, "got %p expected %p\n"); +/* + * these are constants so that the failures are readable if you get + * it wrong. + */ +#define s0 "sbat," +#define s0sz 6 +#define s0len 5 +#define s1 "sbat,1,2021030218" +#define s1sz 18 +#define s1len 17 +#define s2 "sbat,1,20210302" +#define s2sz 16 +#define s2len 15 +#define s3 "sbat,1,20210303" +#define s3sz 16 +#define s3len 15 +#define s4 "sbat\314\234\014," +#define s4sz 9 +#define s4len 8 +/* + * same as s4 but with a UTF8 encoding error; one bit is cleared. + */ +#define s5 "sbat\314\034\014," +#define s5sz 9 +#define s5len 8 - return 0; +#define test_strcmp_helper(fn, invert_sign_errors, invert_encoding_errors) \ + ({ \ + printf("testing %s\n", #fn); \ + int status_ = 0, rc_; \ + \ + rc_ = assert_zero_as_expr(fn(s0, s0), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s0, s1), -1, "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s0, s1), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_positive_as_expr(fn(s1, s0), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + rc_ = assert_positive_as_expr(fn(s1, s2), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s1), -1, "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s1), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s3), -1, "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s3), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_positive_as_expr(fn(s3, s2), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_encoding_errors) \ + rc_ = assert_negative_as_expr(fn(s4, s5), -1, "\n"); \ + else \ + rc_ = assert_positive_as_expr(fn(s4, s5), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (status_ < 0) \ + printf("%s failed\n", #fn); \ + status_; \ + }) + +static int +test_strcmp(void) +{ + int status = 0; + int rc; + + /* + * shim's strcmp + */ + rc = test_strcmp_helper(shim_strcmp, false, false); + status = MIN(rc, status); + + /* + * libc's strcmp + */ + rc = test_strcmp_helper(strcmp, false, false); + status = MIN(rc, status); + + return status; +} + +#undef s0 +#undef s0sz +#undef s0len +#undef s1 +#undef s1sz +#undef s1len +#undef s2 +#undef s2sz +#undef s2len +#undef s3 +#undef s3sz +#undef s3len +#undef s4 +#undef s4sz +#undef s4len +#undef s5 +#undef s5sz +#undef s5len + +/* + * these are constants so that the failures are readable if you get + * it wrong. + */ +#define s0 "sbAt," +#define s0sz 6 +#define s0len 5 +#define s1 "sbaT,1,2021030218" +#define s1sz 18 +#define s1len 17 +#define s2 "sbAt,1,20210302" +#define s2sz 16 +#define s2len 15 +#define s3 "sbaT,1,20210303" +#define s3sz 16 +#define s3len 15 +#define s4 "sbat\314\234\014," +#define s4sz 9 +#define s4len 8 +/* + * same as s4 but with a UTF8 encoding error; one bit is cleared. + */ +#define s5 "sbat\314\034\014," +#define s5sz 9 +#define s5len 8 + +#define test_strcasecmp_helper(fn, invert_sign_errors, invert_encoding_errors) \ + ({ \ + printf("testing %s\n", #fn); \ + int status_ = 0, rc_; \ + \ + rc_ = assert_zero_as_expr(fn(s0, s0), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s0, s1), -1, "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s0, s1), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_positive_as_expr(fn(s1, s0), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + rc_ = assert_positive_as_expr(fn(s1, s2), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s1), -1, "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s1), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s3), -1, "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s3), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_positive_as_expr(fn(s3, s2), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_encoding_errors) \ + rc_ = assert_negative_as_expr(fn(s4, s5), -1, "\n"); \ + else \ + rc_ = assert_positive_as_expr(fn(s4, s5), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (status_ < 0) \ + printf("%s failed\n", #fn); \ + status_; \ + }) + +static int +test_strcasecmp(void) +{ + int status = 0; + int rc; + + /* + * shim's strcasecmp + */ + rc = test_strcasecmp_helper(shim_strcasecmp, false, false); + status = MIN(rc, status); + + /* + * libc's strcasecmp + */ + rc = test_strcasecmp_helper(strcasecmp, false, false); + status = MIN(rc, status); + + return status; +} + +#undef s0 +#undef s0sz +#undef s0len +#undef s1 +#undef s1sz +#undef s1len +#undef s2 +#undef s2sz +#undef s2len +#undef s3 +#undef s3sz +#undef s3len +#undef s4 +#undef s4sz +#undef s4len +#undef s5 +#undef s5sz +#undef s5len + +/* + * these are constants so that the failures are readable if you get + * it wrong. + */ +#define s0 "sbAt," +#define s0sz 6 +#define s0len 5 +#define s1 "sbaT,1,2021030218" +#define s1sz 18 +#define s1len 17 +#define s2 "sbAt,1,20210302" +#define s2sz 16 +#define s2len 15 +#define s3 "sbaT,1,20210303" +#define s3sz 16 +#define s3len 15 +#define s4 "sbat\314\234\014," +#define s4sz 9 +#define s4len 8 +/* + * same as s4 but with a UTF8 encoding error; one bit is cleared. + */ +#define s5 "sbat\314\034\014," +#define s5sz 9 +#define s5len 8 + +#define test_strncasecmp_helper(fn, test_cmp_magnitude, invert_sign_errors, \ + invert_encoding_errors) \ + ({ \ + printf("testing %s\n", #fn); \ + int status_ = 0, rc_; \ + \ + rc_ = assert_zero_as_expr(fn(s0, s0, s0len), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_zero_as_expr(fn(s0, s0, s0sz), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + rc_ = assert_zero_as_expr(fn(s0, s1, s0len), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s0, s1, s0sz), -1, \ + "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s0, s1, s0sz), -1, \ + "\n"); \ + status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s0, s1, s0sz), \ + s0[s0len] - s1[s0len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ + rc_ = assert_positive_as_expr(fn(s1, s0, s0sz), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s1, s0, s0sz), \ + s1[s0len] - s0[s0len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ + \ + rc_ = assert_positive_as_expr(fn(s1, s2, s1sz), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s1, s2, s2sz), \ + s1[s2len] - s2[s2len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ + rc_ = assert_positive_as_expr(fn(s1, s2, s1len), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr( \ + fn(s1, s2, s2len), \ + s1[s2len - 1] - s2[s2len - 1], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s1, s1sz), -1, \ + "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s1, s1sz), -1, \ + "\n"); \ + status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s2, s1, s1sz), \ + s2[s2len] - s1[s2len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ + \ + rc_ = assert_zero_as_expr(fn(s1, s2, s2len), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_positive_as_expr(fn(s1, s2, s2sz), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s1, s2, s2sz), \ + s1[s2len] - s2[s2len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ + \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s3, s2sz), -1, \ + "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s3, s2sz), -1, \ + "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_equal_as_expr(fn(s2, s3, s2sz), \ + s2[s2len - 1] - s3[s2len - 1], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_equal_as_expr(fn(s2, s3, s2len), \ + s2[s2len - 1] - s3[s2len - 1], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + if (invert_sign_errors) \ + rc_ = assert_positive_as_expr(fn(s2, s3, s2len), -1, \ + "\n"); \ + else \ + rc_ = assert_negative_as_expr(fn(s2, s3, s2len), -1, \ + "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_zero_as_expr(fn(s2, s3, s2len - 1), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_false_as_expr(fn(s1, s2, s2len), -1, "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (invert_encoding_errors) \ + rc_ = assert_negative_as_expr(fn(s4, s5, s4sz), -1, \ + "\n"); \ + else \ + rc_ = assert_positive_as_expr(fn(s4, s5, s4sz), -1, \ + "\n"); \ + status_ = MIN(status_, rc_); \ + \ + if (status_ < 0) \ + printf("%s failed\n", #fn); \ + status_; \ + }) + +static int +test_strncasecmp(void) +{ + int status = 0; + int rc; + + /* + * shim's strncasecmp + */ + rc = test_strncasecmp_helper(shim_strncasecmp, true, false, false); + status = MIN(rc, status); + + /* + * libc's strncasecmp + */ + rc = test_strncasecmp_helper(strncasecmp, false, false, false); + status = MIN(rc, status); + + return status; } +#undef s0 +#undef s0sz +#undef s0len +#undef s1 +#undef s1sz +#undef s1len +#undef s2 +#undef s2sz +#undef s2len +#undef s3 +#undef s3sz +#undef s3len +#undef s4 +#undef s4sz +#undef s4len +#undef s5 +#undef s5sz +#undef s5len + /* * copy-pasta from gnu-efi */ @@ -113,7 +521,6 @@ gnuefi_good_strncmp ( return len ? *s1 - *s2 : 0; } - /* * these are constants so that the failures are readable if you get * it wrong. @@ -140,7 +547,8 @@ gnuefi_good_strncmp ( #define s5sz 9 #define s5len 8 -#define test_strncmp_helper(fn, invert_sign_errors, invert_encoding_errors) \ +#define test_strncmp_helper(fn, test_cmp_magnitude, invert_sign_errors, \ + invert_encoding_errors) \ ({ \ printf("testing %s\n", #fn); \ int status_ = 0, rc_; \ @@ -159,29 +567,38 @@ gnuefi_good_strncmp ( rc_ = assert_negative_as_expr(fn(s0, s1, s0sz), -1, \ "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s0, s1, s0sz), \ - s0[s0len] - s1[s0len], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s0, s1, s0sz), \ + s0[s0len] - s1[s0len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ rc_ = assert_positive_as_expr(fn(s1, s0, s0sz), -1, "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s1, s0, s0sz), \ - s1[s0len] - s0[s0len], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s1, s0, s0sz), \ + s1[s0len] - s0[s0len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ \ rc_ = assert_positive_as_expr(fn(s1, s2, s1sz), -1, "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s1, s2, s2sz), \ - s1[s2len] - s2[s2len], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s1, s2, s2sz), \ + s1[s2len] - s2[s2len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ rc_ = assert_positive_as_expr(fn(s1, s2, s1len), -1, "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s1, s2, s2len), \ - s1[s2len - 1] - s2[s2len - 1], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr( \ + fn(s1, s2, s2len), \ + s1[s2len - 1] - s2[s2len - 1], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ if (invert_sign_errors) \ rc_ = assert_positive_as_expr(fn(s2, s1, s1sz), -1, \ "\n"); \ @@ -189,19 +606,23 @@ gnuefi_good_strncmp ( rc_ = assert_negative_as_expr(fn(s2, s1, s1sz), -1, \ "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s2, s1, s1sz), \ - s2[s2len] - s1[s2len], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s2, s1, s1sz), \ + s2[s2len] - s1[s2len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ \ rc_ = assert_zero_as_expr(fn(s1, s2, s2len), -1, "\n"); \ status_ = MIN(status_, rc_); \ rc_ = assert_positive_as_expr(fn(s1, s2, s2sz), -1, "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s1, s2, s2sz), \ - s1[s2len] - s2[s2len], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr(fn(s1, s2, s2sz), \ + s1[s2len] - s2[s2len], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ \ if (invert_sign_errors) \ rc_ = assert_positive_as_expr(fn(s2, s3, s2sz), -1, \ @@ -210,14 +631,18 @@ gnuefi_good_strncmp ( rc_ = assert_negative_as_expr(fn(s2, s3, s2sz), -1, \ "\n"); \ status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s2, s3, s2sz), \ - s2[s2len - 1] - s3[s2len - 1], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ - rc_ = assert_equal_as_expr(fn(s2, s3, s2len), \ - s2[s2len - 1] - s3[s2len - 1], -1, \ - "expected %d got %d\n"); \ - status_ = MIN(status_, rc_); \ + if (test_cmp_magnitude) { \ + rc_ = assert_equal_as_expr( \ + fn(s2, s3, s2sz), \ + s2[s2len - 1] - s3[s2len - 1], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + rc_ = assert_equal_as_expr( \ + fn(s2, s3, s2len), \ + s2[s2len - 1] - s3[s2len - 1], -1, \ + "expected %d got %d\n"); \ + status_ = MIN(status_, rc_); \ + } \ if (invert_sign_errors) \ rc_ = assert_positive_as_expr(fn(s2, s3, s2len), -1, \ "\n"); \ @@ -243,7 +668,7 @@ gnuefi_good_strncmp ( status_; \ }) -int +static int test_strncmp(void) { int status = 0; @@ -252,36 +677,47 @@ test_strncmp(void) /* * shim's strncmp */ - rc = test_strncmp_helper(shim_strncmp, false, false); + rc = test_strncmp_helper(shim_strncmp, true, false, false); status = MIN(rc, status); /* * libc's strncmp */ - rc = test_strncmp_helper(strncmp, false, false); + /* + * Deliberately not testing the difference between these two + * comparisons for the symbol named "strncmp": + * strncmp("b", "a", 1) + * strncmp("c", "a", 1) + * glibc, shim_strncmp(), and even the gnuefi ones will give you 1 + * and 2, respectively, as will glibc's, but valgrind swaps in its + * own implementation, in case you're doing something that's both + * clever and dumb with the result, and it'll return 1 for both of + * them. + */ + rc = test_strncmp_helper(strncmp, false, false, false); status = MIN(rc, status); /* * gnu-efi's broken strncmpa */ +#pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wtype-limits" #pragma GCC diagnostic ignored "-Wsign-compare" - rc = test_strncmp_helper(gnuefi_strncmp, true, false); + rc = test_strncmp_helper(gnuefi_strncmp, true, true, false); status = MIN(rc, status); -#pragma GCC diagnostic error "-Wsign-compare" -#pragma GCC diagnostic error "-Wtype-limits" +#pragma GCC diagnostic pop /* * gnu-efi's broken strncmpa with the return type fixed */ - rc = test_strncmp_helper(gnuefi_signed_strncmp, false, true); + rc = test_strncmp_helper(gnuefi_signed_strncmp, true, false, true); status = MIN(rc, status); /* * gnu-efi's strncmpa with the return type fixed and unsigned * comparisons internally */ - rc = test_strncmp_helper(gnuefi_good_strncmp, false, false); + rc = test_strncmp_helper(gnuefi_good_strncmp, true, false, false); status = MIN(rc, status); return status; @@ -299,8 +735,322 @@ test_strncmp(void) #undef s3 #undef s3sz #undef s3len +#undef s4 +#undef s4sz +#undef s4len +#undef s5 +#undef s5sz +#undef s5len -int +/* + * Put -Wshadow back how it was + */ +#pragma GCC diagnostic pop + +static int +test_strchr(void) +{ + char s0[] = "abcbdbeb\0fbgb"; + + assert_equal_return(strchr(s0, 'a'), s0, -1, "got %p expected %p\n"); + assert_equal_return(strchr(s0, 'b'), &s0[1], -1, "got %p expected %p\n"); + assert_equal_return(strchr(&s0[1], 'b'), &s0[1], -1, "got %p expected %p\n"); + assert_equal_return(strchr(&s0[2], 'b'), &s0[3], -1, "got %p expected %p\n"); + assert_equal_return(strchr(&s0[4], 'b'), &s0[5], -1, "got %p expected %p\n"); + assert_equal_return(strchr(&s0[6], 'b'), &s0[7], -1, "got %p expected %p\n"); + assert_equal_return(strchr(&s0[8], 'b'), NULL, -1, "got %p expected %p\n"); + + assert_equal_return(shim_strchr(s0, 'a'), s0, -1, "got %p expected %p\n"); + assert_equal_return(shim_strchr(s0, 'b'), &s0[1], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchr(&s0[1], 'b'), &s0[1], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchr(&s0[2], 'b'), &s0[3], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchr(&s0[4], 'b'), &s0[5], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchr(&s0[6], 'b'), &s0[7], -1, "got %p expected %p\n"); + assert_equal_return(shim_strchr(&s0[8], 'b'), NULL, -1, "got %p expected %p\n"); + return 0; +} + +static int +test_stpcpy(void) +{ + char s0[] = "0123456789abcdef"; + char s1[] = "xxxxxxxxxxxxxxxx"; + char *s; + + s0[0xa] = 0; + assert_equal_return(stpcpy(s1, s0), &s1[0xa], -1, "got %p expected %p\n"); + assert_zero_return(memcmp(s0, s1, 11), -1, "\n"); + assert_zero_return(memcmp(&s1[11], "xxxxx", sizeof("xxxxx")), -1, "\n"); + + memset(s1, 'x', sizeof(s1)); + s1[16] = 0; + assert_equal_return(shim_stpcpy(s1, s0), &s1[0xa], -1, "got %p expected %p\n"); + assert_zero_return(memcmp(s0, s1, 11), -1, "\n"); + assert_zero_return(memcmp(&s1[11], "xxxxx", sizeof("xxxxx")), -1, "\n"); + + return 0; +} + +static int +test_strdup(void) +{ + char s0[] = "0123456789abcdef"; + char *s = NULL; + + s = strdup(s0); + assert_equal_goto(strcmp(s0, s), 0, err, "\n"); + free(s); + + s = shim_strdup(s0); + assert_equal_goto(strcmp(s0, s), 0, err, "\n"); + free(s); + + return 0; +err: + if (s) + free(s); + return -1; +} + +static int +test_strndup(void) +{ + char s0[] = "0123456789abcdef"; + char *s = NULL; + + s = strndup(s0, 18); + assert_equal_goto(strcmp(s0, s), 0, err, "\n"); + free(s); + s = strndup(s0, 15); + assert_positive_goto(strcmp(s0, s), err, "\n"); + free(s); + + s = shim_strndup(s0, 18); + assert_equal_goto(strcmp(s0, s), 0, err, "\n"); + free(s); + s = strndup(s0, 15); + assert_positive_goto(shim_strcmp(s0, s), err, "\n"); + free(s); + + return 0; +err: + if (s) + free(s); + return -1; +} + +static int +test_strchrnul_helper(__typeof__(strchrnul) fn) +{ + const char s0[] = "abcd\0fghi"; + + assert_equal_return(fn(s0, 'a'), &s0[0], -1, "got %p expected %p\n"); + assert_equal_return(fn(s0, 'd'), &s0[3], -1, "got %p expected %p\n"); + assert_equal_return(fn(s0, '\000'), &s0[4], -1, "got %p expected %p\n"); + assert_equal_return(fn(s0, 'i'), &s0[4], -1, "got %p expected %p\n"); + + return 0; +} + +static int +test_strchrnul(void) +{ + const char s0[] = "abcd\0fghi"; + + assert_equal_return(test_strchrnul_helper(shim_strchrnul), + test_strchrnul_helper(strchrnul), + -1, "got %d expected %d\n"); + + assert_equal_return(strnchrnul(s0, 0, 'b'), &s0[0], -1, "got %p expected %p\n"); + assert_equal_return(strnchrnul(s0, -1, 'b'), &s0[1], 1, "got %p expected %p\n"); + assert_equal_return(strnchrnul(s0, 2, 'b'), &s0[1], -1, "got %p expected %p\n"); + assert_equal_return(strnchrnul(s0, 4, 'f'), &s0[3], -1, "got %p expected %p\n"); + assert_equal_return(strnchrnul(s0, 5, 'f'), &s0[4], -1, "got %p expected %p\n"); + assert_equal_return(strnchrnul(s0, 8, 'f'), &s0[4], -1, "got %p expected %p\n"); + + assert_equal_return(strnchrnul(&s0[4], 1, 'f'), &s0[4], -1, "got %p expected %p\n"); + + return 0; +} + +static int +test_strrchr(void) { + char s0[] = "abcbebfb"; + + assert_equal_return(shim_strrchr(s0, '\n'), NULL, -1, "got %p expected %p\n"); + assert_equal_return(strrchr(s0, '\n'), NULL, -1, "got %p expected %p\n"); + assert_equal_return(shim_strrchr(s0, 'b'), &s0[7], -1, "got %p expected %p\n"); + assert_equal_return(strrchr(s0, 'b'), &s0[7], -1, "got %p expected %p\n"); + assert_equal_return(shim_strrchr(s0, 'c'), &s0[2], -1, "got %p expected %p\n"); + assert_equal_return(strrchr(s0, 'c'), &s0[2], -1, "got %p expected %p\n"); + + return 0; +} + +static int +test_strcpy(void) +{ + char s0[] = "0123456789abcdef\0000"; + char s1[sizeof(s0)]; + + memset(s1, 0, sizeof(s1)); + assert_equal_return(strcpy(s1, s0), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s0), strlen(s1), -1, "got %d expected %d\n"); + + memset(s1, 0, sizeof(s1)); + assert_equal_return(shim_strcpy(s1, s0), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s0), strlen(s1), -1, "got %d expected %d\n"); + + memset(s1, 0, sizeof(s1)); + assert_equal_return(shim_strcpy(s1, s0), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s0), strlen(s1), -1, "got %d expected %d\n"); + + return 0; +} + +static int +test_strncpy(void) +{ + char s[] = "0123456789abcdef\0000"; + char s0[4096+4096]; + char *s1 = &s0[4096]; + + memset(s0, 0, sizeof(s0)); + memcpy(s0, s, sizeof(s)); + + memset(s1, 0, 4096); + assert_equal_return(strncpy(s1, s0, 0), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s1), 0, -1, "got %d expected %d\n"); + memset(s1, 0, 4096); + assert_equal_return(shim_strncpy(s1, s0, 0), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s1), 0, -1, "got %d expected %d\n"); + + memset(s1, 0, 4096); + assert_equal_return(strncpy(s1, s0, 1), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s1), 1, -1, "got %d expected %d\n"); + assert_equal_return(s1[0], s0[0], -1, "got %#02hhx, expected %#02hhx\n"); + assert_equal_return(s0[1], '1', -1, "got %#02hhx, expected %#02hhx\n"); + assert_equal_return(s1[1], '\0', -1, "got %#02hhx, expected %#02hhx\n"); + memset(s1, 0, 4096); + assert_equal_return(shim_strncpy(s1, s0, 1), s1, -1, "got %p expected %p\n"); + assert_equal_return(strlen(s1), 1, -1, "got %d expected %d\n"); + assert_equal_return(s1[0], s0[0], -1, "got %#02hhx, expected %#02hhx\n"); + assert_equal_return(s0[1], '1', -1, "got %#02hhx, expected %#02hhx\n"); + assert_equal_return(s1[1], '\0', -1, "got %#02hhx, expected %#02hhx\n"); + + memset(s1, 0, 4096); + assert_equal_return(strncpy(s1, s0, 15), s1, -1, "got %p expected %p\n"); + assert_equal_return(s0[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[15], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[17], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + memset(s1, 0, 4096); + assert_equal_return(shim_strncpy(s1, s0, 15), s1, -1, "got %p expected %p\n"); + assert_equal_return(s0[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[15], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[17], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + + memset(s1, 0, 4096); + assert_equal_return(strncpy(s1, s0, 16), s1, -1, "got %p expected %p\n"); + assert_equal_return(s0[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[17], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + memset(s1, 0, 4096); + assert_equal_return(shim_strncpy(s1, s0, 16), s1, -1, "got %p expected %p\n"); + assert_equal_return(s0[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[17], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + + memset(s1, 0, 4096); + s1[17] = '0'; + s1[18] = '1'; + assert_equal_return(strncpy(s1, s0, 4096), s1, -1, "got %p expected %p\n"); + assert_equal_return(s0[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[17], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + memset(s1, 0, 4096); + s1[17] = '0'; + s1[18] = '1'; + assert_equal_return(shim_strncpy(s1, s0, 4096), s1, -1, "got %p expected %p\n"); + assert_equal_return(s0[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s0[18], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[14], 'e', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[15], 'f', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[16], '\000', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[17], '0', -1, "got %#02hhx expected %02hhx\n"); + assert_equal_return(s1[18], '1', -1, "got %#02hhx expected %02hhx\n"); + + return 0; +} + +static int +test_strcat(void) +{ + char s[] = "0123456789abcdef\0000"; + char s0[8192]; + char *s1 = &s0[4096]; + char *s2; + char s3[] = "0123456789abcdef0123456789abcdef\000\000\000\000\000"; + + memset(s0, 0, 8192); + memcpy(s0, s, sizeof(s)); + + memset(s1, 0, 4096); + assert_equal_return(strcat(s1, s0), s1, -1, "got %p expected %p\n"); + assert_zero_return(strncmp(s1, s0, sizeof(s)-1), 0, -1, "\n"); + assert_negative_return(memcmp(s1, s0, sizeof(s)), 0, -1, "\n"); + + memset(s1, 0, 4096); + assert_equal_return(strcat(s1, s0), s1, -1, "got %p expected %p\n"); + s2 = s1 + strlen(s1); + assert_equal_return(s2, &s1[16], -1, "got %p expected %p\n"); + assert_equal_return(strcat(s2, s0), s2, -1, "got %p expected %p\n"); + assert_zero_return(strncmp(s1, s0, strlen(s)), -1, "got %p expected %p\n"); + assert_zero_return(strncmp(s2, s0, 2*(sizeof(s)-1)), -1, "\n"); + assert_positive_return(memcmp(s1, s0, 2*sizeof(s)-2), -1, "\n"); + assert_equal_return(memcmp(s1, s3, sizeof(s3)), 0, -1, "expected %d got %d\n"); + + return 0; +} + +static int test_strntoken_null(void) { bool ret; char *token = NULL; @@ -314,7 +1064,7 @@ test_strntoken_null(void) { return 0; } -int +static int test_strntoken_size_0(void) { const char s1[] = "abc,def,.,gh,"; @@ -334,7 +1084,7 @@ test_strntoken_size_0(void) return 0; } -int +static int test_strntoken_empty_size_1(void) { char s1[] = ""; @@ -367,7 +1117,7 @@ test_strntoken_empty_size_1(void) return 0; } -int +static int test_strntoken_size_1(void) { char s1[] = ","; @@ -401,7 +1151,7 @@ test_strntoken_size_1(void) return 0; } -int +static int test_strntoken_size_2(void) { char s1[] = ","; @@ -444,7 +1194,7 @@ test_strntoken_size_2(void) return 0; } -int +static int test_strntoken_no_ascii_nul(void) { const char s1[] = "abc,def,.,gh,"; @@ -557,7 +1307,7 @@ test_strntoken_no_ascii_nul(void) return 0; } -int +static int test_strntoken_with_ascii_nul(void) { const char s1[] = "abc,def,.,gh,"; @@ -680,8 +1430,21 @@ int main(void) { int status = 0; - test(test_strchrnul); + test(test_strlen); + test(test_strnlen); + test(test_strcmp); test(test_strncmp); + test(test_strcasecmp); + test(test_strncasecmp); + test(test_strrchr); + test(test_strcpy); + test(test_strncpy); + test(test_strcat); + test(test_stpcpy); + test(test_strdup); + test(test_strndup); + test(test_strchr); + test(test_strchrnul); test(test_strntoken_null); test(test_strntoken_size_0); test(test_strntoken_empty_size_1); -- cgit v1.2.3 From ed6265c567f7e5aaa0d326e8a5fc21f3499f3ffc Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 11 Mar 2021 11:30:14 -0500 Subject: get_variable_attr(): fix a nit scan-build found. scan-build believes we can hit a situation where get_variable_attr() is called with NULL data, in which case we're not correctly returning an error. This adds the error return. Signed-off-by: Peter Jones --- lib/variables.c | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'lib') diff --git a/lib/variables.c b/lib/variables.c index 57875e26..9f5b2b57 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -224,6 +224,9 @@ get_variable_attr(const CHAR16 * const var, UINT8 **data, UINTN *len, { EFI_STATUS efi_status; + if (!len) + return EFI_INVALID_PARAMETER; + *len = 0; efi_status = gRT->GetVariable((CHAR16 *)var, &owner, NULL, len, NULL); @@ -233,6 +236,9 @@ get_variable_attr(const CHAR16 * const var, UINT8 **data, UINTN *len, return efi_status; } + if (!data) + return EFI_INVALID_PARAMETER; + /* * Add three zero pad bytes; at least one correctly aligned UCS-2 * character. -- cgit v1.2.3 From 4457d79ce0ea638e7732f5529bf13849e290940d Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 11 Mar 2021 16:48:44 -0500 Subject: More va_* work Be much more explicit about exactly which va_* stuff comes from which ABI in both shim and gnu-efi. This fixes the problem where we see: | (null):0:(null)() v->name:"(null)" v->rtname:"(null)" | (null):0:(null)() v->data_size:0 v->data:0x0 and similar messages where everything is NULL. Signed-off-by: Peter Jones --- Cryptlib/Include/OpenSslSupport.h | 2 +- Cryptlib/Include/openssl/bio.h | 4 +- Cryptlib/Include/openssl/err.h | 2 +- Cryptlib/OpenSSL/crypto/bio/b_print.c | 66 ++++++++++++++--------------- Cryptlib/OpenSSL/crypto/err/err.c | 10 ++--- Makefile | 1 + errlog.c | 22 +++++----- gnu-efi | 2 +- include/console.h | 2 +- include/hexdump.h | 8 ++-- include/system/efistdarg.h | 4 ++ include/system/stdarg.h | 80 ++++++++++++++++++++++++++--------- lib/console.c | 12 +++--- shim.h | 3 +- 14 files changed, 132 insertions(+), 86 deletions(-) (limited to 'lib') diff --git a/Cryptlib/Include/OpenSslSupport.h b/Cryptlib/Include/OpenSslSupport.h index 1f475a32..b97149e2 100644 --- a/Cryptlib/Include/OpenSslSupport.h +++ b/Cryptlib/Include/OpenSslSupport.h @@ -227,7 +227,7 @@ size_t fwrite (const void *, size_t, size_t, FILE *); char *fgets (char *, int, FILE *); int fputs (const char *, FILE *); int fprintf (FILE *, const char *, ...); -int vfprintf (FILE *, const char *, va_list); +int vfprintf (FILE *, const char *, ms_va_list); int fflush (FILE *); int fclose (FILE *); DIR *opendir (const char *); diff --git a/Cryptlib/Include/openssl/bio.h b/Cryptlib/Include/openssl/bio.h index 2efa873d..da8c6580 100644 --- a/Cryptlib/Include/openssl/bio.h +++ b/Cryptlib/Include/openssl/bio.h @@ -794,11 +794,11 @@ void BIO_copy_next_retry(BIO *b); # endif int EFIAPI BIO_printf(BIO *bio, const char *format, ...) __bio_h__attr__((__format__(__printf__, 2, 3))); -int EFIAPI BIO_vprintf(BIO *bio, const char *format, va_list args) +int EFIAPI BIO_vprintf(BIO *bio, const char *format, ms_va_list args) __bio_h__attr__((__format__(__printf__, 2, 0))); int EFIAPI BIO_snprintf(char *buf, size_t n, const char *format, ...) __bio_h__attr__((__format__(__printf__, 3, 4))); -int EFIAPI BIO_vsnprintf(char *buf, size_t n, const char *format, va_list args) +int EFIAPI BIO_vsnprintf(char *buf, size_t n, const char *format, ms_va_list args) __bio_h__attr__((__format__(__printf__, 3, 0))); # undef __bio_h__attr__ diff --git a/Cryptlib/Include/openssl/err.h b/Cryptlib/Include/openssl/err.h index 32da8c37..5a019808 100644 --- a/Cryptlib/Include/openssl/err.h +++ b/Cryptlib/Include/openssl/err.h @@ -345,7 +345,7 @@ void ERR_print_errors_fp(FILE *fp); void ERR_print_errors(BIO *bp); # endif void EFIAPI ERR_add_error_data(int num, ...); -void EFIAPI ERR_add_error_vdata(int num, va_list args); +void EFIAPI ERR_add_error_vdata(int num, ms_va_list args); void ERR_load_strings(int lib, ERR_STRING_DATA str[]); void ERR_unload_strings(int lib, ERR_STRING_DATA str[]); void ERR_load_ERR_strings(void); diff --git a/Cryptlib/OpenSSL/crypto/bio/b_print.c b/Cryptlib/OpenSSL/crypto/bio/b_print.c index 34c8fca7..29da9036 100644 --- a/Cryptlib/OpenSSL/crypto/bio/b_print.c +++ b/Cryptlib/OpenSSL/crypto/bio/b_print.c @@ -136,7 +136,7 @@ static int fmtfp(char **, char **, size_t *, size_t *, static int doapr_outch(char **, char **, size_t *, size_t *, int); static int EFIAPI _dopr(char **sbuffer, char **buffer, size_t *maxlen, size_t *retlen, int *truncated, - const char *format, va_list args); + const char *format, ms_va_list args); /* format read states */ #define DP_S_DEFAULT 0 @@ -171,7 +171,7 @@ static int EFIAPI _dopr(char **sbuffer, char **buffer, size_t *maxlen, - size_t *retlen, int *truncated, const char *format, va_list args) + size_t *retlen, int *truncated, const char *format, ms_va_list args) { char ch; LLONG value; @@ -236,7 +236,7 @@ _dopr(char **sbuffer, min = 10 * min + char_to_int(ch); ch = *format++; } else if (ch == '*') { - min = va_arg(args, int); + min = ms_va_arg(args, int); ch = *format++; state = DP_S_DOT; } else @@ -256,7 +256,7 @@ _dopr(char **sbuffer, max = 10 * max + char_to_int(ch); ch = *format++; } else if (ch == '*') { - max = va_arg(args, int); + max = ms_va_arg(args, int); ch = *format++; state = DP_S_MOD; } else @@ -297,16 +297,16 @@ _dopr(char **sbuffer, case 'i': switch (cflags) { case DP_C_SHORT: - value = (short int)va_arg(args, int); + value = (short int)ms_va_arg(args, int); break; case DP_C_LONG: - value = va_arg(args, long int); + value = ms_va_arg(args, long int); break; case DP_C_LLONG: - value = va_arg(args, LLONG); + value = ms_va_arg(args, LLONG); break; default: - value = va_arg(args, int); + value = ms_va_arg(args, int); break; } if (!fmtint(sbuffer, buffer, &currlen, maxlen, value, 10, min, @@ -322,16 +322,16 @@ _dopr(char **sbuffer, flags |= DP_F_UNSIGNED; switch (cflags) { case DP_C_SHORT: - value = (unsigned short int)va_arg(args, unsigned int); + value = (unsigned short int)ms_va_arg(args, unsigned int); break; case DP_C_LONG: - value = (LLONG) va_arg(args, unsigned long int); + value = (LLONG) ms_va_arg(args, unsigned long int); break; case DP_C_LLONG: - value = va_arg(args, unsigned LLONG); + value = ms_va_arg(args, unsigned LLONG); break; default: - value = (LLONG) va_arg(args, unsigned int); + value = (LLONG) ms_va_arg(args, unsigned int); break; } if (!fmtint(sbuffer, buffer, &currlen, maxlen, value, @@ -342,9 +342,9 @@ _dopr(char **sbuffer, #ifndef OPENSSL_SYS_UEFI case 'f': if (cflags == DP_C_LDOUBLE) - fvalue = va_arg(args, LDOUBLE); + fvalue = ms_va_arg(args, LDOUBLE); else - fvalue = va_arg(args, double); + fvalue = ms_va_arg(args, double); if (!fmtfp(sbuffer, buffer, &currlen, maxlen, fvalue, min, max, flags)) return 0; @@ -353,26 +353,26 @@ _dopr(char **sbuffer, flags |= DP_F_UP; case 'e': if (cflags == DP_C_LDOUBLE) - fvalue = va_arg(args, LDOUBLE); + fvalue = ms_va_arg(args, LDOUBLE); else - fvalue = va_arg(args, double); + fvalue = ms_va_arg(args, double); break; case 'G': flags |= DP_F_UP; case 'g': if (cflags == DP_C_LDOUBLE) - fvalue = va_arg(args, LDOUBLE); + fvalue = ms_va_arg(args, LDOUBLE); else - fvalue = va_arg(args, double); + fvalue = ms_va_arg(args, double); break; #endif case 'c': if(!doapr_outch(sbuffer, buffer, &currlen, maxlen, - va_arg(args, int))) + ms_va_arg(args, int))) return 0; break; case 's': - strvalue = va_arg(args, char *); + strvalue = ms_va_arg(args, char *); if (max < 0) { if (buffer) max = INT_MAX; @@ -384,7 +384,7 @@ _dopr(char **sbuffer, return 0; break; case 'p': - value = (long)va_arg(args, void *); + value = (long)ms_va_arg(args, void *); if (!fmtint(sbuffer, buffer, &currlen, maxlen, value, 16, min, max, flags | DP_F_NUM)) return 0; @@ -392,19 +392,19 @@ _dopr(char **sbuffer, case 'n': /* XXX */ if (cflags == DP_C_SHORT) { short int *num; - num = va_arg(args, short int *); + num = ms_va_arg(args, short int *); *num = currlen; } else if (cflags == DP_C_LONG) { /* XXX */ long int *num; - num = va_arg(args, long int *); + num = ms_va_arg(args, long int *); *num = (long int)currlen; } else if (cflags == DP_C_LLONG) { /* XXX */ LLONG *num; - num = va_arg(args, LLONG *); + num = ms_va_arg(args, LLONG *); *num = (LLONG) currlen; } else { int *num; - num = va_arg(args, int *); + num = ms_va_arg(args, int *); *num = currlen; } break; @@ -799,18 +799,18 @@ doapr_outch(char **sbuffer, int EFIAPI BIO_printf(BIO *bio, const char *format, ...) { - va_list args; + ms_va_list args; int ret; - va_start(args, format); + ms_va_start(args, format); ret = BIO_vprintf(bio, format, args); - va_end(args); + ms_va_end(args); return (ret); } -int EFIAPI BIO_vprintf(BIO *bio, const char *format, va_list args) +int EFIAPI BIO_vprintf(BIO *bio, const char *format, ms_va_list args) { int ret; size_t retlen; @@ -847,18 +847,18 @@ int EFIAPI BIO_vprintf(BIO *bio, const char *format, va_list args) */ int EFIAPI BIO_snprintf(char *buf, size_t n, const char *format, ...) { - va_list args; + ms_va_list args; int ret; - va_start(args, format); + ms_va_start(args, format); ret = BIO_vsnprintf(buf, n, format, args); - va_end(args); + ms_va_end(args); return (ret); } -int EFIAPI BIO_vsnprintf(char *buf, size_t n, const char *format, va_list args) +int EFIAPI BIO_vsnprintf(char *buf, size_t n, const char *format, ms_va_list args) { size_t retlen; int truncated; diff --git a/Cryptlib/OpenSSL/crypto/err/err.c b/Cryptlib/OpenSSL/crypto/err/err.c index d0752adf..e2251454 100644 --- a/Cryptlib/OpenSSL/crypto/err/err.c +++ b/Cryptlib/OpenSSL/crypto/err/err.c @@ -1077,13 +1077,13 @@ void ERR_set_error_data(char *data, int flags) void EFIAPI ERR_add_error_data(int num, ...) { - va_list args; - va_start(args, num); + ms_va_list args; + ms_va_start(args, num); ERR_add_error_vdata(num, args); - va_end(args); + ms_va_end(args); } -void EFIAPI ERR_add_error_vdata(int num, va_list args) +void EFIAPI ERR_add_error_vdata(int num, ms_va_list args) { int i, n, s; char *str, *p, *a; @@ -1096,7 +1096,7 @@ void EFIAPI ERR_add_error_vdata(int num, va_list args) n = 0; for (i = 0; i < num; i++) { - a = va_arg(args, char *); + a = ms_va_arg(args, char *); /* ignore NULLs, thanks to Bob Beck */ if (a != NULL) { n += strlen(a); diff --git a/Makefile b/Makefile index df2d8b6e..9a93d740 100644 --- a/Makefile +++ b/Makefile @@ -136,6 +136,7 @@ MokManager.o: $(MOK_SOURCES) $(MMSONAME): $(MOK_OBJS) $(LIBS) $(LD) -o $@ $(LDFLAGS) $^ $(EFI_LIBS) lib/lib.a +gnu-efi/$(ARCH_GNUEFI)/gnuefi/libgnuefi.a gnu-efi/$(ARCH_GNUEFI)/lib/libefi.a: CFLAGS+=-DGNU_EFI_USE_EXTERNAL_STDARG gnu-efi/$(ARCH_GNUEFI)/gnuefi/libgnuefi.a gnu-efi/$(ARCH_GNUEFI)/lib/libefi.a: $(MAKE) -C gnu-efi \ ARCH=$(ARCH_GNUEFI) TOPDIR=$(TOPDIR)/gnu-efi \ diff --git a/errlog.c b/errlog.c index ac657151..cc6a89f5 100644 --- a/errlog.c +++ b/errlog.c @@ -11,25 +11,25 @@ static UINTN nerrs = 0; EFI_STATUS EFIAPI vdprint_(const CHAR16 *fmt, const char *file, int line, const char *func, - va_list args) + ms_va_list args) { - va_list args2; + ms_va_list args2; EFI_STATUS efi_status = EFI_SUCCESS; if (verbose) { - va_copy(args2, args); + ms_va_copy(args2, args); console_print(L"%a:%d:%a() ", file, line, func); efi_status = VPrint(fmt, args2); - va_end(args2); + ms_va_end(args2); } return efi_status; } EFI_STATUS EFIAPI VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, - va_list args) + ms_va_list args) { - va_list args2; + ms_va_list args2; CHAR16 **newerrs; newerrs = ReallocatePool(errs, (nerrs + 1) * sizeof(*errs), @@ -40,11 +40,11 @@ VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, newerrs[nerrs] = PoolPrint(L"%a:%d %a() ", file, line, func); if (!newerrs[nerrs]) return EFI_OUT_OF_RESOURCES; - va_copy(args2, args); + ms_va_copy(args2, args); newerrs[nerrs+1] = VPoolPrint(fmt, args2); if (!newerrs[nerrs+1]) return EFI_OUT_OF_RESOURCES; - va_end(args2); + ms_va_end(args2); nerrs += 2; newerrs[nerrs] = NULL; @@ -56,12 +56,12 @@ VLogError(const char *file, int line, const char *func, const CHAR16 *fmt, EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) { - va_list args; + ms_va_list args; EFI_STATUS efi_status; - va_start(args, fmt); + ms_va_start(args, fmt); efi_status = VLogError(file, line, func, fmt, args); - va_end(args); + ms_va_end(args); return efi_status; } diff --git a/gnu-efi b/gnu-efi index 4444de49..f922aec7 160000 --- a/gnu-efi +++ b/gnu-efi @@ -1 +1 @@ -Subproject commit 4444de49c66b5b6758976ab1e3862bb17cff9d56 +Subproject commit f922aec7d6d60c245a4d1e1f82598d427c7765b5 diff --git a/include/console.h b/include/console.h index 036262ef..f56b1231 100644 --- a/include/console.h +++ b/include/console.h @@ -108,7 +108,7 @@ extern UINT32 verbose; #endif extern EFI_STATUS EFIAPI vdprint_(const CHAR16 *fmt, const char *file, int line, - const char *func, va_list args); + const char *func, ms_va_list args); #define vdprint(fmt, ...) \ vdprint_(fmt, __FILE__, __LINE__ - 1, __func__, ##__VA_ARGS__) diff --git a/include/hexdump.h b/include/hexdump.h index f778de9a..381e1a68 100644 --- a/include/hexdump.h +++ b/include/hexdump.h @@ -81,7 +81,7 @@ prepare_text(const void *data, size_t size, char *buf, unsigned int position) */ static inline void UNUSED EFIAPI vhexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, - const void *data, unsigned long size, size_t at, va_list ap) + const void *data, unsigned long size, size_t at, ms_va_list ap) { unsigned long display_offset = at; unsigned long offset = 0; @@ -118,11 +118,11 @@ static inline void UNUSED EFIAPI hexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, const void *data, unsigned long size, size_t at, ...) { - va_list ap; + ms_va_list ap; - va_start(ap, at); + ms_va_start(ap, at); vhexdumpf(file, line, func, fmt, data, size, at, ap); - va_end(ap); + ms_va_end(ap); } static inline void UNUSED diff --git a/include/system/efistdarg.h b/include/system/efistdarg.h index 837c4f23..034977cc 100644 --- a/include/system/efistdarg.h +++ b/include/system/efistdarg.h @@ -8,6 +8,10 @@ #ifndef _EFISTDARG_H_ #define _EFISTDARG_H_ +#ifndef GNU_EFI_USE_EXTERNAL_STDARG +#define GNU_EFI_USE_EXTERNAL_STDARG +#endif + #include #endif /* !_EFISTDARG_H_ */ diff --git a/include/system/stdarg.h b/include/system/stdarg.h index af1ac59b..ce722249 100644 --- a/include/system/stdarg.h +++ b/include/system/stdarg.h @@ -2,39 +2,79 @@ /* * stdarg.h - try to make consistent va_* handling for EFI */ -#ifdef SHIM_UNIT_TEST -#include_next -#else #ifndef _STDARG_H -#define _STDARG_H + +/* + * clang doesn't know about __builtin_sysv_va_list, apparently. + */ +#ifdef __clang__ +#pragma GCC diagnostic push +#pragma GCC diagnostic warning "-Wcpp" +typedef __builtin_va_list __builtin_sysv_va_list; +#warning clang builds may not work at all for anything other than scan-build +#pragma GCC diagnostic pop +#endif #ifndef GNU_EFI_USE_EXTERNAL_STDARG #define GNU_EFI_USE_EXTERNAL_STDARG #endif +#ifdef SHIM_UNIT_TEST +#include_next +#endif + #if defined(__aarch64__) || defined(__arm__) || defined(__i386__) || \ defined(__i486__) || defined(__i686__) || defined(SHIM_UNIT_TEST) -typedef __builtin_va_list va_list; -#define va_copy(dest, start) __builtin_va_copy(dest, start) -#define va_start(marker, arg) __builtin_va_start(marker, arg) -#define va_arg(marker, type) __builtin_va_arg(marker, type) -#define va_end(marker) __builtin_va_end(marker) + +typedef __builtin_va_list ms_va_list; +typedef __builtin_va_list __builtin_ms_va_list; +#define ms_va_copy(dest, start) __builtin_va_copy(dest, start) +#define ms_va_start(marker, arg) __builtin_va_start(marker, arg) +#define ms_va_arg(marker, type) __builtin_va_arg(marker, type) +#define ms_va_end(marker) __builtin_va_end(marker) + +typedef __builtin_va_list sysv_va_list; +#define sysv_va_copy(dest, start) __builtin_va_copy(dest, start) +#define sysv_va_start(marker, arg) __builtin_va_start(marker, arg) +#define sysv_va_arg(marker, type) __builtin_va_arg(marker, type) +#define sysv_va_end(marker) __builtin_va_end(marker) +/* + * OpenSSL's X509ConstructCertificateStack needs this. + */ +typedef __builtin_va_list VA_LIST; +#define VA_COPY(dest, start) __builtin_va_copy(dest, start) +#define VA_START(marker, arg) __builtin_va_start(marker, arg) +#define VA_END(marker) __builtin_va_end(marker) +#define VA_ARG(marker, type) __builtin_va_arg(marker, type) + #elif defined(__x86_64__) -typedef __builtin_ms_va_list va_list; -#define va_copy(dest, start) __builtin_ms_va_copy(dest, start) -#define va_start(marker, arg) __builtin_ms_va_start(marker, arg) -#define va_arg(marker, type) __builtin_va_arg(marker, type) -#define va_end(marker) __builtin_ms_va_end(marker) + +typedef __builtin_ms_va_list ms_va_list; +#define ms_va_copy(dest, start) __builtin_ms_va_copy(dest, start) +#define ms_va_start(marker, arg) __builtin_ms_va_start(marker, arg) +#define ms_va_arg(marker, type) __builtin_va_arg(marker, type) +#define ms_va_end(marker) __builtin_ms_va_end(marker) +typedef __builtin_sysv_va_list sysv_va_list; +#define sysv_va_copy(dest, start) __builtin_sysv_va_copy(dest, start) +#define sysv_va_start(marker, arg) __builtin_sysv_va_start(marker, arg) +#define sysv_va_arg(marker, type) __builtin_va_arg(marker, type) +#define sysv_va_end(marker) __builtin_sysv_va_end(marker) +/* + * OpenSSL's X509ConstructCertificateStack needs this. + */ +typedef __builtin_ms_va_list VA_LIST; +#define VA_COPY(dest, start) __builtin_ms_va_copy(dest, start) +#define VA_START(marker, arg) __builtin_ms_va_start(marker, arg) +#define VA_END(marker) __builtin_ms_va_end(marker) +#define VA_ARG(marker, type) __builtin_va_arg(marker, type) + #else #error what arch is this #endif -typedef va_list VA_LIST; -#define VA_COPY(dest, start) va_copy(dest, start) -#define VA_START(marker, arg) va_start(marker, arg) -#define VA_END(marker) va_end(marker) -#define VA_ARG(marker, type) va_arg(marker, type) +#ifndef _STDARG_H +#define _STDARG_H +#endif /* !_STDARG_H #2 */ #endif /* !_STDARG_H */ -#endif /* !SHIM_UNIT_TEST */ // vim:fenc=utf-8:tw=75:noet diff --git a/lib/console.c b/lib/console.c index 2da20b31..c310d213 100644 --- a/lib/console.c +++ b/lib/console.c @@ -86,15 +86,15 @@ VOID console_fini(VOID) UINTN EFIAPI console_print(const CHAR16 *fmt, ...) { - va_list args; + ms_va_list args; UINTN ret; if (!console_text_mode) setup_console(1); - va_start(args, fmt); + ms_va_start(args, fmt); ret = VPrint(fmt, args); - va_end(args); + ms_va_end(args); return ret; } @@ -103,7 +103,7 @@ UINTN EFIAPI console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) { SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut; - va_list args; + ms_va_list args; UINTN ret; if (!console_text_mode) @@ -111,9 +111,9 @@ console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) co->SetCursorPosition(co, col, row); - va_start(args, fmt); + ms_va_start(args, fmt); ret = VPrint(fmt, args); - va_end(args); + ms_va_end(args); return ret; } diff --git a/shim.h b/shim.h index 44dddc7a..69ad2cc3 100644 --- a/shim.h +++ b/shim.h @@ -22,6 +22,7 @@ #if defined(__x86_64__) /* gcc 4.5.4 is the first documented release with -mabi=ms */ +/* gcc 4.7.1 is the first one with __builtin_ms_va_list */ #if !GNUC_PREREQ(4, 7) && !CLANG_PREREQ(3, 4) #error On x86_64 you must have a compiler new enough to support __attribute__((__ms_abi__)) #endif @@ -226,7 +227,7 @@ extern void shim_fini(void); extern EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...); extern EFI_STATUS EFIAPI VLogError(const char *file, int line, const char *func, - const CHAR16 *fmt, va_list args); + const CHAR16 *fmt, ms_va_list args); extern VOID LogHexdump_(const char *file, int line, const char *func, const void *data, size_t sz); extern VOID PrintErrors(VOID); -- cgit v1.2.3 From 7defee6ad60d16dc762c110f67ec9074cbb4039a Mon Sep 17 00:00:00 2001 From: Thomas Frauendorfer | Miray Software Date: Wed, 17 Mar 2021 10:49:49 +0100 Subject: Sort input file names in lib/Makefile The order in which the foreach() returns files differes from Debian on WSL1 and Debian running natively. When shim is build on these two platforms the resulting binaries differ. This patch manually sorts the input file list to create identical binaries. Signed-off-by: Thomas Frauendorfer | Miray Software --- lib/Makefile | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) (limited to 'lib') diff --git a/lib/Makefile b/lib/Makefile index 0d2d0a9d..6d83f789 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -1,6 +1,7 @@ TARGET = lib.a -LIBFILES = $(foreach x,$(wildcard *.c),$(patsubst %.c,%.o,$(x))) +LIBFILES_UNSORTED := $(foreach x,$(wildcard *.c),$(patsubst %.c,%.o,$(x))) +LIBFILES := $(sort $(LIBFILES_UNSORTED)) CRYPTDIR = $(TOPDIR)/Cryptlib -- cgit v1.2.3 From 3dd40ade68c6ff63e776b5f9acbd811a3c345d01 Mon Sep 17 00:00:00 2001 From: Chris Coulson Date: Thu, 18 Mar 2021 14:32:24 +0000 Subject: Ensure that MOK variable mirroring creates well formed ESLs The MOK variable mirroring makes use of variable_create_esl, which can only create a well-formed EFI_SIGNATURE_LIST containing a single signature. Fix fill_esl and variable_create_esl to support creating a EFI_SIGNATURE_LIST with one or more supplied EFI_SIGNATURE_DATA structures. Introduce variable_create_esl_with_one_signature and fill_esl_with_one_signature for code that does want to create a EFI_SIGNATURE_LIST containing a single signature constructed from a supplied signature data buffer and owner GUID. --- include/variables.h | 16 ++++++++--- lib/variables.c | 81 +++++++++++++++++++++++++++++++++++++++++++---------- mok.c | 56 ++++++++++++++++++------------------ 3 files changed, 106 insertions(+), 47 deletions(-) (limited to 'lib') diff --git a/include/variables.h b/include/variables.h index 31cfcb65..493f433f 100644 --- a/include/variables.h +++ b/include/variables.h @@ -64,12 +64,20 @@ EFI_STATUS variable_enroll_hash(const CHAR16 * const var, EFI_GUID owner, UINT8 hash[SHA256_DIGEST_SIZE]); EFI_STATUS -variable_create_esl(const uint8_t *cert, const size_t cert_len, - const EFI_GUID *type, const EFI_GUID *owner, +variable_create_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, + const EFI_GUID *type, const UINT32 sig_size, uint8_t **out, size_t *outlen); EFI_STATUS -fill_esl(const uint8_t *data, const size_t data_len, - const EFI_GUID *type, const EFI_GUID *owner, +variable_create_esl_with_one_signature(const uint8_t* data, const size_t data_len, + const EFI_GUID *type, const EFI_GUID *owner, + uint8_t **out, size_t *outlen); +EFI_STATUS +fill_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, + const EFI_GUID *type, const UINT32 sig_size, uint8_t *out, size_t *outlen); +EFI_STATUS +fill_esl_with_one_signature(const uint8_t *data, const uint32_t data_len, + const EFI_GUID *type, const EFI_GUID *owner, + uint8_t *out, size_t *outlen); #endif /* SHIM_VARIABLES_H */ diff --git a/lib/variables.c b/lib/variables.c index 9f5b2b57..53a5d14a 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -13,18 +13,24 @@ #include "shim.h" EFI_STATUS -fill_esl(const uint8_t *data, const size_t data_len, - const EFI_GUID *type, const EFI_GUID *owner, +fill_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, + const EFI_GUID *type, const UINT32 sig_size, uint8_t *out, size_t *outlen) { EFI_SIGNATURE_LIST *sl; EFI_SIGNATURE_DATA *sd; size_t needed = 0; + size_t data_len = howmany * sig_size; - if (!data || !data_len || !type || !outlen) + dprint(L"fill_esl: data=%p, data_len=%lu", first_sig, data_len); + + if ((out && !first_sig) || !howmany || !type || !sig_size || !outlen) + return EFI_INVALID_PARAMETER; + + if (howmany > (UINT32_MAX - sizeof(EFI_SIGNATURE_LIST)) / sig_size) return EFI_INVALID_PARAMETER; - needed = sizeof(EFI_SIGNATURE_LIST) + sizeof(EFI_GUID) + data_len; + needed = sizeof(EFI_SIGNATURE_LIST) + data_len; if (!out || *outlen < needed) { *outlen = needed; return EFI_BUFFER_TOO_SMALL; @@ -35,27 +41,70 @@ fill_esl(const uint8_t *data, const size_t data_len, sl->SignatureHeaderSize = 0; sl->SignatureType = *type; - sl->SignatureSize = sizeof(EFI_GUID) + data_len; + sl->SignatureSize = sig_size; sl->SignatureListSize = needed; sd = (EFI_SIGNATURE_DATA *)(out + sizeof(EFI_SIGNATURE_LIST)); - if (owner) - sd->SignatureOwner = *owner; - - CopyMem(sd->SignatureData, data, data_len); + CopyMem(sd, first_sig, data_len); return EFI_SUCCESS; } EFI_STATUS -variable_create_esl(const uint8_t *data, const size_t data_len, - const EFI_GUID *type, const EFI_GUID *owner, +fill_esl_with_one_signature(const uint8_t *data, const uint32_t data_len, + const EFI_GUID *type, const EFI_GUID *owner, + uint8_t *out, size_t *outlen) +{ + EFI_STATUS efi_status; + EFI_SIGNATURE_DATA *sd = NULL; + UINT32 sig_size = sizeof(EFI_SIGNATURE_DATA) - 1 + data_len; + + if (data_len > UINT32_MAX - sizeof(EFI_SIGNATURE_DATA) + 1) + return EFI_INVALID_PARAMETER; + + if (out) { + sd = AllocateZeroPool(sig_size); + if (owner) + CopyMem(sd, owner, sizeof(EFI_GUID)); + CopyMem(sd->SignatureData, data, data_len); + } + + efi_status = fill_esl(sd, 1, type, sig_size, out, outlen); + + if (out) + FreePool(sd); + return efi_status; +} + +EFI_STATUS +variable_create_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, + const EFI_GUID *type, const UINT32 sig_size, uint8_t **out, size_t *outlen) { EFI_STATUS efi_status; *outlen = 0; - efi_status = fill_esl(data, data_len, type, owner, NULL, outlen); + efi_status = fill_esl(first_sig, howmany, type, sig_size, NULL, outlen); + if (efi_status != EFI_BUFFER_TOO_SMALL) + return efi_status; + + *out = AllocateZeroPool(*outlen); + if (!*out) + return EFI_OUT_OF_RESOURCES; + + return fill_esl(first_sig, howmany, type, sig_size, *out, outlen); +} + +EFI_STATUS +variable_create_esl_with_one_signature(const uint8_t* data, const size_t data_len, + const EFI_GUID *type, const EFI_GUID *owner, + uint8_t **out, size_t *outlen) +{ + EFI_STATUS efi_status; + + *outlen = 0; + efi_status = fill_esl_with_one_signature(data, data_len, type, owner, + NULL, outlen); if (efi_status != EFI_BUFFER_TOO_SMALL) return efi_status; @@ -63,7 +112,8 @@ variable_create_esl(const uint8_t *data, const size_t data_len, if (!*out) return EFI_OUT_OF_RESOURCES; - return fill_esl(data, data_len, type, owner, *out, outlen); + return fill_esl_with_one_signature(data, data_len, type, owner, *out, + outlen); } EFI_STATUS @@ -153,8 +203,9 @@ SetSecureVariable(const CHAR16 * const var, UINT8 *Data, UINTN len, if (createtimebased) { size_t ds; - efi_status = variable_create_esl(Data, len, &X509_GUID, NULL, - (uint8_t **)&Cert, &ds); + efi_status = variable_create_esl_with_one_signature( + Data, len, &X509_GUID, NULL, + (uint8_t **)&Cert, &ds); if (EFI_ERROR(efi_status)) { console_print(L"Failed to create %s certificate %d\n", var, efi_status); diff --git a/mok.c b/mok.c index e3c3d9ee..3d2b398c 100644 --- a/mok.c +++ b/mok.c @@ -303,8 +303,8 @@ mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs, UINTN *newsz, SIZE_T maxsz) { EFI_STATUS efi_status; - SIZE_T howmany, varsz = 0, esdsz; - UINT8 *var, *data; + SIZE_T howmany, varsz = 0; + UINT8 *var; howmany = MIN((maxsz - sizeof(*esl)) / esl->SignatureSize, (esl->SignatureListSize - sizeof(*esl)) / esl->SignatureSize); @@ -316,8 +316,6 @@ mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs, * We always assume esl->SignatureHeaderSize is 0 (and so far, * that's true as per UEFI 2.8) */ - esdsz = howmany * esl->SignatureSize; - data = (UINT8 *)esd; dprint(L"Trying to add %lx signatures to \"%s\" of size %lx\n", howmany, name, esl->SignatureSize); @@ -327,10 +325,9 @@ mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs, * * Compensate here. */ - efi_status = variable_create_esl(data + sizeof(EFI_GUID), - esdsz - sizeof(EFI_GUID), + efi_status = variable_create_esl(esd, howmany, &esl->SignatureType, - &esd->SignatureOwner, + esl->SignatureSize, &var, &varsz); if (EFI_ERROR(efi_status) || !var || !varsz) { LogError(L"Couldn't allocate %lu bytes for mok variable \"%s\": %r\n", @@ -349,7 +346,7 @@ mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs, return efi_status; } - *newsz = esdsz; + *newsz = howmany * esl->SignatureSize; return efi_status; } @@ -507,7 +504,7 @@ mirror_mok_db(CHAR16 *name, CHAR8 *name8, EFI_GUID *guid, UINT32 attrs, UINT8 *var; UINTN varsz; - efi_status = variable_create_esl( + efi_status = variable_create_esl_with_one_signature( null_sha256, sizeof(null_sha256), &EFI_CERT_SHA256_GUID, &SHIM_LOCK_GUID, &var, &varsz); @@ -592,10 +589,12 @@ mirror_one_mok_variable(struct mok_state_variable *v, FullDataSize, FullData); break; case VENDOR_ADDEND_X509: - efi_status = fill_esl(*v->addend, *v->addend_size, - &EFI_CERT_TYPE_X509_GUID, - &SHIM_LOCK_GUID, - NULL, &addend_esl_sz); + efi_status = fill_esl_with_one_signature(*v->addend, + *v->addend_size, + &EFI_CERT_TYPE_X509_GUID, + &SHIM_LOCK_GUID, + NULL, + &addend_esl_sz); if (efi_status != EFI_BUFFER_TOO_SMALL) { perror(L"Could not add built-in cert to %s: %r\n", v->name, efi_status); @@ -616,11 +615,11 @@ mirror_one_mok_variable(struct mok_state_variable *v, * then the build cert if it's there */ if (should_mirror_build_cert(v)) { - efi_status = fill_esl(*v->build_cert, - *v->build_cert_size, - &EFI_CERT_TYPE_X509_GUID, - &SHIM_LOCK_GUID, - NULL, &build_cert_esl_sz); + efi_status = fill_esl_with_one_signature(*v->build_cert, + *v->build_cert_size, + &EFI_CERT_TYPE_X509_GUID, + &SHIM_LOCK_GUID, + NULL, &build_cert_esl_sz); if (efi_status != EFI_BUFFER_TOO_SMALL) { perror(L"Could not add built-in cert to %s: %r\n", v->name, efi_status); @@ -703,10 +702,11 @@ mirror_one_mok_variable(struct mok_state_variable *v, FullDataSize, FullData, p, p-(uintptr_t)FullData); break; case VENDOR_ADDEND_X509: - efi_status = fill_esl(*v->addend, *v->addend_size, - &EFI_CERT_TYPE_X509_GUID, - &SHIM_LOCK_GUID, - p, &addend_esl_sz); + efi_status = fill_esl_with_one_signature(*v->addend, + *v->addend_size, + &EFI_CERT_TYPE_X509_GUID, + &SHIM_LOCK_GUID, + p, &addend_esl_sz); if (EFI_ERROR(efi_status)) { perror(L"Could not add built-in cert to %s: %r\n", v->name, efi_status); @@ -729,11 +729,11 @@ mirror_one_mok_variable(struct mok_state_variable *v, dprint(L"FullDataSize:%lu FullData:0x%llx p:0x%llx pos:%lld\n", FullDataSize, FullData, p, p-(uintptr_t)FullData); if (should_mirror_build_cert(v)) { - efi_status = fill_esl(*v->build_cert, - *v->build_cert_size, - &EFI_CERT_TYPE_X509_GUID, - &SHIM_LOCK_GUID, - p, &build_cert_esl_sz); + efi_status = fill_esl_with_one_signature(*v->build_cert, + *v->build_cert_size, + &EFI_CERT_TYPE_X509_GUID, + &SHIM_LOCK_GUID, + p, &build_cert_esl_sz); if (EFI_ERROR(efi_status)) { perror(L"Could not add built-in cert to %s: %r\n", v->name, efi_status); @@ -765,7 +765,7 @@ mirror_one_mok_variable(struct mok_state_variable *v, * need a dummy entry */ if ((v->flags & MOK_MIRROR_KEYDB) && FullDataSize == 0) { - efi_status = variable_create_esl( + efi_status = variable_create_esl_with_one_signature( null_sha256, sizeof(null_sha256), &EFI_CERT_SHA256_GUID, &SHIM_LOCK_GUID, &FullData, &FullDataSize); -- cgit v1.2.3 From 33db42def2ce6fe040b5f77642347e8b3c6420e5 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Sun, 21 Mar 2021 15:57:03 -0400 Subject: Make 'make test' work on gcc 4.8.5 --- include/endian.h | 10 ++++++---- include/test.mk | 2 +- lib/string.c | 21 +++++++++++++++++++++ test-str.c | 23 +++++++++++++++++++++++ test.c | 3 +++ 5 files changed, 54 insertions(+), 5 deletions(-) (limited to 'lib') diff --git a/include/endian.h b/include/endian.h index 267fbf00..1c4a21de 100644 --- a/include/endian.h +++ b/include/endian.h @@ -3,9 +3,11 @@ * endian.h - bswap decls that can't go in compiler.h * Copyright Peter Jones */ - -#ifndef ENDIAN_H_ -#define ENDIAN_H_ +#ifdef SHIM_UNIT_TEST +#include_next +#endif +#ifndef SHIM_ENDIAN_H_ +#define SHIM_ENDIAN_H_ #include @@ -15,5 +17,5 @@ mkbi1_(uint32_t, bswap32, uint32_t, x) mkbi1_(uint64_t, bswap64, uint64_t, x) #include "system/builtins_end_.h" -#endif /* !ENDIAN_H_ */ +#endif /* !SHIM_ENDIAN_H_ */ // vim:fenc=utf-8:tw=75:noet diff --git a/include/test.mk b/include/test.mk index 5d74bdc2..62cf983a 100644 --- a/include/test.mk +++ b/include/test.mk @@ -21,7 +21,7 @@ CFLAGS = -O2 -ggdb -std=gnu11 \ -Wno-unused \ -Werror \ -Werror=nonnull \ - -Werror=nonnull-compare \ + $(shell $(CC) -Werror=nonnull-compare -E -x c /dev/null >/dev/null 2>&1 && echo -Werror=nonnull-compare) \ $(ARCH_DEFINES) \ -DEFI_FUNCTION_WRAPPER \ -DGNU_EFI_USE_MS_ABI -DPAGE_SIZE=4096 \ diff --git a/lib/string.c b/lib/string.c index 37eabe8c..d941cd56 100644 --- a/lib/string.c +++ b/lib/string.c @@ -7,7 +7,13 @@ #ifdef SHIM_UNIT_TEST #define strlen shim_strlen +#ifdef strcmp +#undef strcmp +#endif #define strcmp shim_strcmp +#ifdef strncmp +#undef strncmp +#endif #define strncmp shim_strncmp #define strncasecmp shim_strncasecmp #define strcasecmp shim_strcasecmp @@ -15,11 +21,26 @@ #define strlen shim_strlen #define strnlen shim_strnlen #define strcpy shim_strcpy +#ifdef strncpy +#undef strncpy +#endif #define strncpy shim_strncpy +#ifdef strdup +#undef strdup +#endif #define strdup shim_strdup +#ifdef strndup +#undef strndup +#endif #define strndup shim_strndup +#ifdef stpcpy +#undef stpcpy +#endif #define stpcpy shim_stpcpy #define strchrnul shim_strchrnul +#ifdef strchr +#undef strchr +#endif #define strchr shim_strchr #endif diff --git a/test-str.c b/test-str.c index 87605b26..70d1637c 100644 --- a/test-str.c +++ b/test-str.c @@ -6,6 +6,8 @@ #pragma GCC diagnostic error "-Wnonnull" #pragma GCC diagnostic error "-Wunused-function" +#pragma GCC diagnostic warning "-Wcpp" + #ifndef SHIM_UNIT_TEST #define SHIM_UNIT_TEST #endif @@ -1046,8 +1048,29 @@ test_strcat(void) memset(s1, 0, 4096); assert_equal_return(strcat(s1, s0), s1, -1, "got %p expected %p\n"); + /* For unknown reasons, gcc 4.8.5 gives us this here: + * | In file included from shim.h:64:0, + * | from test-str.c:14: + * | test-str.c: In function 'test_strcat': + * | include/test.h:85:10: warning: array subscript is below array bounds [-Warray-bounds] + * | printf("%s:%d:got %lld, expected zero " fmt, __func__, \ + * | ^ + * | include/test.h:112:10: warning: array subscript is below array bounds [-Warray-bounds] + * | printf("%s:%d:got %lld, expected < 0 " fmt, __func__, \ + * | ^ + * + * This clearly isn't a useful error message, as it doesn't tell us + * /anything about the problem/, but also it isn't reported on + * later compilers, and it isn't clear that there's any problem + * when examining these functions. + * + * I don't know. + */ +#pragma GCC diagnostic push +#pragma GCC diagnostic warning "-Warray-bounds" assert_zero_return(strncmp(s1, s0, sizeof(s)-1), 0, -1, "\n"); assert_negative_return(memcmp(s1, s0, sizeof(s)), 0, -1, "\n"); +#pragma GCC diagnostic pop memset(s1, 0, 4096); assert_equal_return(strcat(s1, s0), s1, -1, "got %p expected %p\n"); diff --git a/test.c b/test.c index aa0da1fd..dc71941f 100644 --- a/test.c +++ b/test.c @@ -12,6 +12,9 @@ UINT8 in_protocol = 0; int debug = DEFAULT_DEBUG_PRINT_STATE; +#pragma GCC diagnostic ignored "-Wunused-parameter" +#pragma GCC diagnostic ignored "-Wunused-function" + EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) { -- cgit v1.2.3 From f9294c2fa9feaf5353c0b7a4a7ce102a820c1a3f Mon Sep 17 00:00:00 2001 From: Chris Coulson Date: Fri, 19 Mar 2021 16:50:05 +0000 Subject: Fix boot failures due to variable size constraints There are multiple issues in the MOK variable mirroring code due to volatile variable size constraints, which all result in boot failures: - If a signature is encountered which doesn't fit in to a single variable, the code enters an infinite loop because the cursor isn't advanced in mirror_mok_db() after the call to mirror_one_esl(). - If an ESL is encountered which doesn't fit in to a single variable, it looks like the intention is for the ESL to be split across multiple variables. However, mirror_one_esl() will write the maximum variable size on each call, regardless of how much data is remaining for the current ESL. If the size of a ESL isn't a multiple of the maximum variable size, the final call to mirror_one_esl() will append data from the start of the next ESL and the cursor in mirror_mok_db() will be advanced to an arbitrary location in the next ESL. This either results in garbage being mirrored (if you're lucky), or in my case - another infinite loop as it appears to encounter a signature that doesn't fit in to a single variable. - If no signatures can be mirrored when mirror_mok_db() is called with only_first=TRUE, it tries to create a variable with a single SHA256 signature in it. But mirror_mok_db() returns an error (EFI_INVALID_PARAMETER) regardless of whether this succeeds. --- lib/variables.c | 2 +- mok.c | 60 +++++++++++++++++++++++++++++---------------------------- 2 files changed, 32 insertions(+), 30 deletions(-) (limited to 'lib') diff --git a/lib/variables.c b/lib/variables.c index 53a5d14a..f606e248 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -22,7 +22,7 @@ fill_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, size_t needed = 0; size_t data_len = howmany * sig_size; - dprint(L"fill_esl: data=%p, data_len=%lu", first_sig, data_len); + dprint(L"fill_esl: first_sig=0x%llx, data_len=%lu\n", first_sig, data_len); if ((out && !first_sig) || !howmany || !type || !sig_size || !outlen) return EFI_INVALID_PARAMETER; diff --git a/mok.c b/mok.c index 345c322c..5ad9072b 100644 --- a/mok.c +++ b/mok.c @@ -300,18 +300,12 @@ get_max_var_sz(UINT32 attrs, SIZE_T *max_var_szp) static EFI_STATUS mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs, EFI_SIGNATURE_LIST *esl, EFI_SIGNATURE_DATA *esd, - UINTN *newsz, SIZE_T maxsz) + SIZE_T howmany) { EFI_STATUS efi_status; - SIZE_T howmany, varsz = 0; + SIZE_T varsz = 0; UINT8 *var; - howmany = MIN((maxsz - sizeof(*esl)) / esl->SignatureSize, - (esl->SignatureListSize - sizeof(*esl)) / esl->SignatureSize); - if (howmany < 1) { - return EFI_BUFFER_TOO_SMALL; - } - /* * We always assume esl->SignatureHeaderSize is 0 (and so far, * that's true as per UEFI 2.8) @@ -346,8 +340,6 @@ mirror_one_esl(CHAR16 *name, EFI_GUID *guid, UINT32 attrs, return efi_status; } - *newsz = howmany * esl->SignatureSize; - return efi_status; } @@ -459,12 +451,25 @@ mirror_mok_db(CHAR16 *name, CHAR8 *name8, EFI_GUID *guid, UINT32 attrs, return efi_status; } + /* The name counts towards the size of the variable */ + max_var_sz -= (StrLen(namen) + 1) * 2; + dprint(L"max_var_sz - name: %lx\n", max_var_sz); + SIZE_T howmany; - UINTN adj = 0; howmany = MIN((max_var_sz - sizeof(*esl)) / esl->SignatureSize, - (esl->SignatureListSize - sizeof(*esl)) / esl->SignatureSize); - if (!only_first && i == 0 && howmany >= 1) { - adj = howmany * esl->SignatureSize; + (esl_end_pos - pos) / esl->SignatureSize); + if (howmany == 0) { + /* No signatures from this ESL can be mirrored in to a + * single variable, so skip it. + */ + dprint(L"skipping esl, pos:0x%llx->0x%llx\n", pos, esl_end_pos); + pos = esl_end_pos; + continue; + } + + UINTN adj = howmany * esl->SignatureSize; + + if (!only_first && i == 0) { dprint(L"pos:0x%llx->0x%llx\n", pos, pos + adj); pos += adj; i++; @@ -473,25 +478,25 @@ mirror_mok_db(CHAR16 *name, CHAR8 *name8, EFI_GUID *guid, UINT32 attrs, } efi_status = mirror_one_esl(namen, guid, attrs, - esl, esd, &adj, max_var_sz); + esl, esd, howmany); dprint(L"esd:0x%llx adj:0x%llx\n", esd, adj); - if (EFI_ERROR(efi_status) && efi_status != EFI_BUFFER_TOO_SMALL) { + if (EFI_ERROR(efi_status)) { LogError(L"Could not mirror mok variable \"%s\": %r\n", namen, efi_status); break; } - if (!EFI_ERROR(efi_status)) { - did_one = TRUE; - if (only_first) - break; - dprint(L"pos:0x%llx->0x%llx\n", pos, pos + adj); - pos += adj; - i++; - } + dprint(L"pos:0x%llx->0x%llx\n", pos, pos + adj); + pos += adj; + did_one = TRUE; + if (only_first) + break; + i++; } - if (only_first && !did_one) { + if (EFI_ERROR(efi_status)) { + perror(L"Failed to set %s: %r\n", name, efi_status); + } else if (only_first && !did_one) { /* * In this case we're going to try to create a * dummy variable so that there's one there. It @@ -513,15 +518,12 @@ mirror_mok_db(CHAR16 *name, CHAR8 *name8, EFI_GUID *guid, UINT32 attrs, * doesn't. */ if (!EFI_ERROR(efi_status) && var && varsz) { - SetVariable(name, guid, + efi_status = SetVariable(name, guid, EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, varsz, var); FreePool(var); } - efi_status = EFI_INVALID_PARAMETER; - } else if (EFI_ERROR(efi_status)) { - perror(L"Failed to set %s: %r\n", name, efi_status); } return efi_status; } -- cgit v1.2.3 From 8578b75f9c18fd267c8a0746192ab3f051561df2 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Wed, 24 Mar 2021 17:51:48 -0400 Subject: Make building outside of the top directory work. This also makes the cross-build targets (and not the others) /use/ this functionality, so we'll catch it if we break it again. This fixes issue #340. Signed-off-by: Peter Jones --- .github/workflows/pullrequest.yml | 16 ++++++++++----- Make.defaults | 1 + Makefile | 43 +++++++++++++++++++++++++-------------- gnu-efi | 2 +- lib/Makefile | 2 +- 5 files changed, 42 insertions(+), 22 deletions(-) (limited to 'lib') diff --git a/.github/workflows/pullrequest.yml b/.github/workflows/pullrequest.yml index 6df69833..5329496c 100644 --- a/.github/workflows/pullrequest.yml +++ b/.github/workflows/pullrequest.yml @@ -110,18 +110,24 @@ jobs: id: update-submodules run: | make update - - name: Do 'make clean' on ${{ matrix.distro }} for ${{ matrix.efiarch }} - id: clean + - name: Make a build directory for ${{ matrix.distro }} for ${{ matrix.efiarch }} + id: builddir run: | - make CROSS_COMPILE=${{ matrix.gccarch }}-linux-gnu- ARCH=${{ matrix.makearch }} PREFIX=/usr DESTDIR=/destdir EFIDIR=test ENABLE_SHIM_HASH=true clean + rm -rf build-${{ matrix.distro }}-${{ matrix.efiarch }} + mkdir build-${{ matrix.distro }}-${{ matrix.efiarch }} + cd build-${{ matrix.distro }}-${{ matrix.efiarch }} - name: Do the build on ${{ matrix.distro }} for ${{ matrix.efiarch }} id: build run: | - make CROSS_COMPILE=${{ matrix.gccarch }}-linux-gnu- ARCH=${{ matrix.makearch }} PREFIX=/usr DESTDIR=/destdir EFIDIR=test ENABLE_SHIM_HASH=true all + pwd + cd build-${{ matrix.distro }}-${{ matrix.efiarch }} + make TOPDIR=.. -f ../Makefile CROSS_COMPILE=${{ matrix.gccarch }}-linux-gnu- ARCH=${{ matrix.makearch }} PREFIX=/usr DESTDIR=/destdir EFIDIR=test ENABLE_SHIM_HASH=true all - name: Install on ${{ matrix.distro }} for ${{ matrix.efiarch }} id: install run: | - make CROSS_COMPILE=${{ matrix.gccarch }}-linux-gnu- ARCH=${{ matrix.makearch }} PREFIX=/usr DESTDIR=/destdir EFIDIR=test ENABLE_SHIM_HASH=true install + pwd + cd build-${{ matrix.distro }}-${{ matrix.efiarch }} + make TOPDIR=.. -f ../Makefile CROSS_COMPILE=${{ matrix.gccarch }}-linux-gnu- ARCH=${{ matrix.makearch }} PREFIX=/usr DESTDIR=/destdir EFIDIR=test ENABLE_SHIM_HASH=true install echo 'results:' find /destdir -type f diff --git a/Make.defaults b/Make.defaults index b7721547..a775083e 100644 --- a/Make.defaults +++ b/Make.defaults @@ -1,6 +1,7 @@ # load the local configuration if it exists -include Make.local +-include $(TOPDIR)/Make.local COMPILER ?= gcc CC = $(CROSS_COMPILE)$(COMPILER) diff --git a/Makefile b/Makefile index e349c6f9..8e2a463d 100644 --- a/Makefile +++ b/Makefile @@ -45,7 +45,7 @@ MOK_OBJS = MokManager.o PasswordCrypt.o crypt_blowfish.o errlog.o sbat_data.o ORIG_MOK_SOURCES = MokManager.c PasswordCrypt.c crypt_blowfish.c shim.h $(wildcard include/*.h) FALLBACK_OBJS = fallback.o tpm.o errlog.o sbat_data.o ORIG_FALLBACK_SRCS = fallback.c -SBATPATH = data/sbat.csv +SBATPATH = $(TOPDIR)/data/sbat.csv ifeq ($(SOURCE_DATE_EPOCH),) UNAME=$(shell uname -s -m -p -i -o) @@ -146,21 +146,23 @@ $(MMSONAME): $(MOK_OBJS) $(LIBS) gnu-efi/$(ARCH_GNUEFI)/gnuefi/libgnuefi.a gnu-efi/$(ARCH_GNUEFI)/lib/libefi.a: CFLAGS+=-DGNU_EFI_USE_EXTERNAL_STDARG gnu-efi/$(ARCH_GNUEFI)/gnuefi/libgnuefi.a gnu-efi/$(ARCH_GNUEFI)/lib/libefi.a: + mkdir -p gnu-efi/lib gnu-efi/gnuefi $(MAKE) -C gnu-efi \ ARCH=$(ARCH_GNUEFI) TOPDIR=$(TOPDIR)/gnu-efi \ + -f $(TOPDIR)/gnu-efi/Makefile \ lib gnuefi inc Cryptlib/libcryptlib.a: for i in Hash Hmac Cipher Rand Pk Pem SysCall; do mkdir -p Cryptlib/$$i; done - $(MAKE) VPATH=$(TOPDIR)/Cryptlib -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile + $(MAKE) TOPDIR=$(TOPDIR) VPATH=$(TOPDIR)/Cryptlib -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile Cryptlib/OpenSSL/libopenssl.a: for i in x509v3 x509 txt_db stack sha rsa rc4 rand pkcs7 pkcs12 pem ocsp objects modes md5 lhash kdf hmac evp err dso dh conf comp cmac buffer bn bio async/arch asn1 aes; do mkdir -p Cryptlib/OpenSSL/crypto/$$i; done - $(MAKE) VPATH=$(TOPDIR)/Cryptlib/OpenSSL -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile + $(MAKE) TOPDIR=$(TOPDIR) VPATH=$(TOPDIR)/Cryptlib/OpenSSL -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile lib/lib.a: | $(TOPDIR)/lib/Makefile $(wildcard $(TOPDIR)/include/*.[ch]) - if [ ! -d lib ]; then mkdir lib ; fi - $(MAKE) VPATH=$(TOPDIR)/lib -C lib -f $(TOPDIR)/lib/Makefile lib.a + mkdir -p lib + $(MAKE) VPATH=$(TOPDIR)/lib TOPDIR=$(TOPDIR) -C lib -f $(TOPDIR)/lib/Makefile buildid : $(TOPDIR)/buildid.c $(HOSTCC) -I/usr/include -Og -g3 -Wall -Werror -Wextra -o $@ $< -lelf @@ -275,35 +277,46 @@ else endif test : - @make -f include/test.mk EFI_INCLUDES="$(EFI_INCLUDES)" ARCH_DEFINES="$(ARCH_DEFINES)" all + @make -f $(TOPDIR)/include/test.mk EFI_INCLUDES="$(EFI_INCLUDES)" ARCH_DEFINES="$(ARCH_DEFINES)" all $(patsubst %.c,%,$(wildcard test-*.c)) : - @make -f include/test.mk EFI_INCLUDES="$(EFI_INCLUDES)" ARCH_DEFINES="$(ARCH_DEFINES)" $@ + @make -f $(TOPDIR)/include/test.mk EFI_INCLUDES="$(EFI_INCLUDES)" ARCH_DEFINES="$(ARCH_DEFINES)" $@ .PHONY : $(patsubst %.c,%,$(wildcard test-*.c)) test clean-test-objs: - @make -f include/test.mk EFI_INCLUDES="$(EFI_INCLUDES)" ARCH_DEFINES="$(ARCH_DEFINES)" clean + @make -f $(TOPDIR)/include/test.mk EFI_INCLUDES="$(EFI_INCLUDES)" ARCH_DEFINES="$(ARCH_DEFINES)" clean clean-gnu-efi: - $(MAKE) -C gnu-efi \ - ARCH=$(ARCH_GNUEFI) TOPDIR=$(TOPDIR)/gnu-efi \ - clean + @if [ -d gnu-efi ] ; then \ + $(MAKE) -C gnu-efi \ + ARCH=$(ARCH_GNUEFI) TOPDIR=$(TOPDIR)/gnu-efi \ + -f $(TOPDIR)/gnu-efi/Makefile \ + clean ; \ + fi + +clean-lib-objs: + @if [ -d lib ] ; then \ + $(MAKE) -C lib TOPDIR=$(TOPDIR) -f $(TOPDIR)/lib/Makefile clean ; \ + fi clean-shim-objs: - $(MAKE) -C lib -f $(TOPDIR)/lib/Makefile clean @rm -rvf $(TARGET) *.o $(SHIM_OBJS) $(MOK_OBJS) $(FALLBACK_OBJS) $(KEYS) certdb $(BOOTCSVNAME) @rm -vf *.debug *.so *.efi *.efi.* *.tar.* version.c buildid @rm -vf Cryptlib/*.[oa] Cryptlib/*/*.[oa] @if [ -d .git ] ; then git clean -f -d -e 'Cryptlib/OpenSSL/*'; fi clean-openssl-objs: - $(MAKE) -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile clean + @if [ -d Cryptlib/Openssl ] ; then \ + $(MAKE) -C Cryptlib/OpenSSL -f $(TOPDIR)/Cryptlib/OpenSSL/Makefile clean ; \ + fi clean-cryptlib-objs: - $(MAKE) -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile clean + @if [ -d Cryptlib ] ; then \ + $(MAKE) -C Cryptlib -f $(TOPDIR)/Cryptlib/Makefile clean ; \ + fi -clean: clean-shim-objs clean-test-objs clean-gnu-efi clean-openssl-objs clean-cryptlib-objs +clean: clean-shim-objs clean-test-objs clean-gnu-efi clean-openssl-objs clean-cryptlib-objs clean-lib-objs GITTAG = $(VERSION) diff --git a/gnu-efi b/gnu-efi index 193ae1ae..65ecce23 160000 --- a/gnu-efi +++ b/gnu-efi @@ -1 +1 @@ -Subproject commit 193ae1aeacd940ec3b48cc52f135f0695648a5f4 +Subproject commit 65ecce23f005c4d611f48996112d4592164594cf diff --git a/lib/Makefile b/lib/Makefile index 6d83f789..a4a4855b 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -1,6 +1,6 @@ TARGET = lib.a -LIBFILES_UNSORTED := $(foreach x,$(wildcard *.c),$(patsubst %.c,%.o,$(x))) +LIBFILES_UNSORTED := $(patsubst %.c,%.o,$(subst $(TOPDIR)/lib/,,$(wildcard $(TOPDIR)/lib/*.c))) LIBFILES := $(sort $(LIBFILES_UNSORTED)) CRYPTDIR = $(TOPDIR)/Cryptlib -- cgit v1.2.3 From f1ef8dffd374048fbf8dd584923c42e5a784bbf2 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 15 Jul 2021 10:07:14 -0400 Subject: Make test cases link against libefi.a This allows us to use library functions from libefi.a in our test programs. Signed-off-by: Peter Jones --- include/test.mk | 20 +++++++++++++++++--- lib/variables.c | 48 ++++++++++++++++++++++++++---------------------- test.c | 37 ++++++------------------------------- 3 files changed, 49 insertions(+), 56 deletions(-) (limited to 'lib') diff --git a/include/test.mk b/include/test.mk index 62cf983a..c66b46de 100644 --- a/include/test.mk +++ b/include/test.mk @@ -5,6 +5,8 @@ .SUFFIXES: +include Make.defaults + CC = gcc VALGRIND ?= DEBUG_PRINTS ?= 0 @@ -28,6 +30,15 @@ CFLAGS = -O2 -ggdb -std=gnu11 \ -DSHIM_UNIT_TEST \ "-DDEFAULT_DEBUG_PRINT_STATE=$(DEBUG_PRINTS)" +libefi-test.a : + $(MAKE) -C gnu-efi ARCH=$(ARCH_GNUEFI) TOPDIR=$(TOPDIR)/gnu-efi \ + -f $(TOPDIR)/gnu-efi/Makefile \ + clean lib + mv gnu-efi/$(ARCH)/lib/libefi.a $@ + $(MAKE) -C gnu-efi ARCH=$(ARCH_GNUEFI) TOPDIR=$(TOPDIR)/gnu-efi \ + -f $(TOPDIR)/gnu-efi/Makefile \ + clean + $(wildcard test-*.c) :: %.c : test-random.h $(patsubst %.c,%,$(wildcard test-*.c)) :: | test-random.h $(patsubst %.c,%.o,$(wildcard test-*.c)) : | test-random.h @@ -36,19 +47,22 @@ test-random.h: dd if=/dev/urandom bs=512 count=17 of=random.bin xxd -i random.bin test-random.h -test-sbat_FILES = csv.c +test-sbat_FILES = csv.c lib/variables.c lib/guid.c +test-sbat :: CFLAGS+=-DHAVE_GET_VARIABLE -DHAVE_GET_VARIABLE_ATTR -DHAVE_SHIM_LOCK_GUID + test-str_FILES = lib/string.c tests := $(patsubst %.c,%,$(wildcard test-*.c)) +$(tests) :: test-% : | libefi-test.a $(tests) :: test-% : test.c test-%.c $(test-%_FILES) - $(CC) $(CFLAGS) -o $@ $^ $(wildcard $*.c) $(test-$*_FILES) + $(CC) $(CFLAGS) -o $@ $^ $(wildcard $*.c) $(test-$*_FILES) libefi-test.a $(VALGRIND) ./$@ test : $(tests) clean : - @rm -vf test-random.h random.bin + @rm -vf test-random.h random.bin libefi-test.a all : clean test diff --git a/lib/variables.c b/lib/variables.c index f606e248..ff61d0e2 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -12,6 +12,10 @@ */ #include "shim.h" +extern EFI_SYSTEM_TABLE *ST; +extern EFI_BOOT_SERVICES *BS; +extern EFI_RUNTIME_SERVICES *RT; + EFI_STATUS fill_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, const EFI_GUID *type, const UINT32 sig_size, @@ -154,7 +158,7 @@ CreateTimeBasedPayload(IN OUT UINTN * DataSize, IN OUT UINT8 ** Data) DescriptorData = (EFI_VARIABLE_AUTHENTICATION_2 *) (NewData); ZeroMem(&Time, sizeof(EFI_TIME)); - efi_status = gRT->GetTime(&Time, NULL); + efi_status = RT->GetTime(&Time, NULL); if (EFI_ERROR(efi_status)) { FreePool(NewData); return efi_status; @@ -225,7 +229,7 @@ SetSecureVariable(const CHAR16 * const var, UINT8 *Data, UINTN len, return efi_status; } - efi_status = gRT->SetVariable((CHAR16 *)var, &owner, + efi_status = RT->SetVariable((CHAR16 *)var, &owner, EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS | @@ -241,8 +245,8 @@ GetOSIndications(void) UINTN DataSize = sizeof(indications); EFI_STATUS efi_status; - efi_status = gRT->GetVariable(L"OsIndicationsSupported", &GV_GUID, - NULL, &DataSize, &indications); + efi_status = RT->GetVariable(L"OsIndicationsSupported", &GV_GUID, + NULL, &DataSize, &indications); if (EFI_ERROR(efi_status)) return 0; @@ -255,15 +259,15 @@ SETOSIndicationsAndReboot(UINT64 indications) UINTN DataSize = sizeof(indications); EFI_STATUS efi_status; - efi_status = gRT->SetVariable(L"OsIndications", &GV_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_RUNTIME_ACCESS | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - DataSize, &indications); + efi_status = RT->SetVariable(L"OsIndications", &GV_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_RUNTIME_ACCESS | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + DataSize, &indications); if (EFI_ERROR(efi_status)) return efi_status; - gRT->ResetSystem(EfiResetWarm, EFI_SUCCESS, 0, NULL); + RT->ResetSystem(EfiResetWarm, EFI_SUCCESS, 0, NULL); /* does not return */ return EFI_SUCCESS; @@ -280,7 +284,7 @@ get_variable_attr(const CHAR16 * const var, UINT8 **data, UINTN *len, *len = 0; - efi_status = gRT->GetVariable((CHAR16 *)var, &owner, NULL, len, NULL); + efi_status = RT->GetVariable((CHAR16 *)var, &owner, NULL, len, NULL); if (efi_status != EFI_BUFFER_TOO_SMALL) { if (!EFI_ERROR(efi_status)) /* this should never happen */ return EFI_PROTOCOL_ERROR; @@ -298,7 +302,7 @@ get_variable_attr(const CHAR16 * const var, UINT8 **data, UINTN *len, if (!*data) return EFI_OUT_OF_RESOURCES; - efi_status = gRT->GetVariable((CHAR16 *)var, &owner, attributes, len, *data); + efi_status = RT->GetVariable((CHAR16 *)var, &owner, attributes, len, *data); if (EFI_ERROR(efi_status)) { FreePool(*data); *data = NULL; @@ -341,7 +345,7 @@ EFI_STATUS set_variable(CHAR16 *var, EFI_GUID owner, UINT32 attributes, UINTN datasize, void *data) { - return gRT->SetVariable(var, &owner, attributes, datasize, data); + return RT->SetVariable(var, &owner, attributes, datasize, data); } EFI_STATUS @@ -394,8 +398,8 @@ variable_is_setupmode(int default_return) UINTN DataSize = sizeof(SetupMode); EFI_STATUS efi_status; - efi_status = gRT->GetVariable(L"SetupMode", &GV_GUID, NULL, - &DataSize, &SetupMode); + efi_status = RT->GetVariable(L"SetupMode", &GV_GUID, NULL, + &DataSize, &SetupMode); if (EFI_ERROR(efi_status)) return default_return; @@ -411,8 +415,8 @@ variable_is_secureboot(void) EFI_STATUS efi_status; DataSize = sizeof(SecureBoot); - efi_status = gRT->GetVariable(L"SecureBoot", &GV_GUID, NULL, - &DataSize, &SecureBoot); + efi_status = RT->GetVariable(L"SecureBoot", &GV_GUID, NULL, + &DataSize, &SecureBoot); if (EFI_ERROR(efi_status)) return 0; @@ -445,10 +449,10 @@ variable_enroll_hash(const CHAR16 * const var, EFI_GUID owner, efi_status = SetSecureVariable(var, sig, sizeof(sig), owner, EFI_VARIABLE_APPEND_WRITE, 0); else - efi_status = gRT->SetVariable((CHAR16 *)var, &owner, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS | - EFI_VARIABLE_APPEND_WRITE, - sizeof(sig), sig); + efi_status = RT->SetVariable((CHAR16 *)var, &owner, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS | + EFI_VARIABLE_APPEND_WRITE, + sizeof(sig), sig); return efi_status; } diff --git a/test.c b/test.c index 9da5cf5b..11e0c642 100644 --- a/test.c +++ b/test.c @@ -22,37 +22,6 @@ LogError_(const char *file, int line, const char *func, const CHAR16 *fmt, ...) return EFI_SUCCESS; } -#ifndef HAVE_STRCMP -INTN -StrCmp(CONST CHAR16 *s1, CONST CHAR16 *s2) { - assert(s1 != NULL); - assert(s2 != NULL); - - int i; - for (i = 0; s1[i] && s2[i]; i++) { - if (s1[i] != s2[i]) - return s2[i] - s1[i]; - } - return 0; -} -#endif - -#ifndef HAVE_STRNCMP -INTN -StrnCmp(CONST CHAR16 *s1, CONST CHAR16 *s2, UINTN len) { - assert(s1 != NULL); - assert(s2 != NULL); - - UINTN i; - for (i = 0; i < len && s1[i] && s2[i]; i++) { - if (s1[i] != s2[i]) - return s2[i] - s1[i]; - - } - return 0; -} -#endif - #ifndef HAVE_GET_VARIABLE_ATTR EFI_STATUS get_variable_attr(const CHAR16 * const var, UINT8 **data, UINTN *len, @@ -74,4 +43,10 @@ get_variable(const CHAR16 * const var, UINT8 **data, UINTN *len, EFI_GUID owner) EFI_GUID SHIM_LOCK_GUID = {0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23 } }; #endif +UINTN EFIAPI +console_print(const CHAR16 *fmt, ...) +{ + return 0; +} + // vim:fenc=utf-8:tw=75:noet -- cgit v1.2.3 From e13ac7386ea425c9222e05a2f9879d5af5cb91f6 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Wed, 4 Aug 2021 13:24:11 -0400 Subject: Make CopyMem() work with EFI's declaration EFI_BOOT_SERVICES includes CopyMem() and SetMem() functions which are marked EFIAPI, and in the case of CopyMem() does not mark the source argument as CONST. This patch makes all our invocations work with that, so (once gnu-efi's implementation is fixed to match) we can use the existing implementation as the implementation in a mock EFI_BOOT_SERVICES. Signed-off-by: Peter Jones --- Cryptlib/Hash/CryptMd5.c | 2 +- Cryptlib/Hash/CryptSha1.c | 2 +- Cryptlib/Hash/CryptSha256.c | 2 +- Cryptlib/Hash/CryptSha512.c | 4 ++-- Cryptlib/Include/OpenSslSupport.h | 4 ++-- Cryptlib/Pk/CryptPkcs7Verify.c | 2 +- httpboot.c | 6 +++--- lib/variables.c | 6 +++--- 8 files changed, 14 insertions(+), 14 deletions(-) (limited to 'lib') diff --git a/Cryptlib/Hash/CryptMd5.c b/Cryptlib/Hash/CryptMd5.c index ccf6ad00..b389f0e1 100644 --- a/Cryptlib/Hash/CryptMd5.c +++ b/Cryptlib/Hash/CryptMd5.c @@ -93,7 +93,7 @@ Md5Duplicate ( return FALSE; } - CopyMem (NewMd5Context, Md5Context, sizeof (MD5_CTX)); + CopyMem (NewMd5Context, (void *)Md5Context, sizeof (MD5_CTX)); return TRUE; } diff --git a/Cryptlib/Hash/CryptSha1.c b/Cryptlib/Hash/CryptSha1.c index 42cfd08a..3e67a805 100644 --- a/Cryptlib/Hash/CryptSha1.c +++ b/Cryptlib/Hash/CryptSha1.c @@ -92,7 +92,7 @@ Sha1Duplicate ( return FALSE; } - CopyMem (NewSha1Context, Sha1Context, sizeof (SHA_CTX)); + CopyMem (NewSha1Context, (void *)Sha1Context, sizeof (SHA_CTX)); return TRUE; } diff --git a/Cryptlib/Hash/CryptSha256.c b/Cryptlib/Hash/CryptSha256.c index 06ecb2e9..05bc6b0a 100644 --- a/Cryptlib/Hash/CryptSha256.c +++ b/Cryptlib/Hash/CryptSha256.c @@ -91,7 +91,7 @@ Sha256Duplicate ( return FALSE; } - CopyMem (NewSha256Context, Sha256Context, sizeof (SHA256_CTX)); + CopyMem (NewSha256Context, (void *)Sha256Context, sizeof (SHA256_CTX)); return TRUE; } diff --git a/Cryptlib/Hash/CryptSha512.c b/Cryptlib/Hash/CryptSha512.c index 3ce372a0..16063b23 100644 --- a/Cryptlib/Hash/CryptSha512.c +++ b/Cryptlib/Hash/CryptSha512.c @@ -93,7 +93,7 @@ Sha384Duplicate ( return FALSE; } - CopyMem (NewSha384Context, Sha384Context, sizeof (SHA512_CTX)); + CopyMem (NewSha384Context, (void *)Sha384Context, sizeof (SHA512_CTX)); return TRUE; } @@ -308,7 +308,7 @@ Sha512Duplicate ( return FALSE; } - CopyMem (NewSha512Context, Sha512Context, sizeof (SHA512_CTX)); + CopyMem (NewSha512Context, (void *)Sha512Context, sizeof (SHA512_CTX)); return TRUE; } diff --git a/Cryptlib/Include/OpenSslSupport.h b/Cryptlib/Include/OpenSslSupport.h index b97149e2..0c2fb8b0 100644 --- a/Cryptlib/Include/OpenSslSupport.h +++ b/Cryptlib/Include/OpenSslSupport.h @@ -262,11 +262,11 @@ extern FILE *stdout; // // Macros that directly map functions to BaseLib, BaseMemoryLib, and DebugLib functions // -#define memcpy(dest,source,count) ( {CopyMem(dest,source,(UINTN)(count)); dest; }) +#define memcpy(dest,source,count) ( {CopyMem(dest,(void *)source,(UINTN)(count)); dest; }) #define memset(dest,ch,count) SetMem(dest,(UINTN)(count),(UINT8)(ch)) #define memchr(buf,ch,count) ScanMem8((CHAR8 *)buf,(UINTN)(count),ch) #define memcmp(buf1,buf2,count) (int)(CompareMem(buf1,buf2,(UINTN)(count))) -#define memmove(dest,source,count) CopyMem(dest,source,(UINTN)(count)) +#define memmove(dest,source,count) CopyMem(dest,(void *)source,(UINTN)(count)) #define localtime(timer) NULL #define assert(expression) #define atoi(nptr) AsciiStrDecimalToUintn((const CHAR8 *)nptr) diff --git a/Cryptlib/Pk/CryptPkcs7Verify.c b/Cryptlib/Pk/CryptPkcs7Verify.c index 09895d8c..c1893848 100644 --- a/Cryptlib/Pk/CryptPkcs7Verify.c +++ b/Cryptlib/Pk/CryptPkcs7Verify.c @@ -216,7 +216,7 @@ WrapPkcs7Data ( // // Part7: P7Data. // - CopyMem (SignedData + 19, P7Data, P7Length); + CopyMem (SignedData + 19, (void *)P7Data, P7Length); } *WrapFlag = Wrapped; diff --git a/httpboot.c b/httpboot.c index 5d16bc1e..3340a7f9 100644 --- a/httpboot.c +++ b/httpboot.c @@ -179,8 +179,8 @@ generate_next_uri (CONST CHAR8 *current_uri, CONST CHAR8 *next_loader, if (!*uri) return EFI_OUT_OF_RESOURCES; - CopyMem(*uri, current_uri, path_len); - CopyMem(*uri + path_len, next_loader, next_len); + CopyMem(*uri, (void *)current_uri, path_len); + CopyMem(*uri + path_len, (void *)next_loader, next_len); (*uri)[path_len + next_len] = '\0'; return EFI_SUCCESS; @@ -209,7 +209,7 @@ extract_hostname (CONST CHAR8 *url, CHAR8 **hostname) if (!*hostname) return EFI_OUT_OF_RESOURCES; - CopyMem(*hostname, start, host_len); + CopyMem(*hostname, (void *)start, host_len); (*hostname)[host_len] = '\0'; return EFI_SUCCESS; diff --git a/lib/variables.c b/lib/variables.c index ff61d0e2..3ec05478 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -49,7 +49,7 @@ fill_esl(const EFI_SIGNATURE_DATA *first_sig, const size_t howmany, sl->SignatureListSize = needed; sd = (EFI_SIGNATURE_DATA *)(out + sizeof(EFI_SIGNATURE_LIST)); - CopyMem(sd, first_sig, data_len); + CopyMem(sd, (void *)first_sig, data_len); return EFI_SUCCESS; } @@ -69,8 +69,8 @@ fill_esl_with_one_signature(const uint8_t *data, const uint32_t data_len, if (out) { sd = AllocateZeroPool(sig_size); if (owner) - CopyMem(sd, owner, sizeof(EFI_GUID)); - CopyMem(sd->SignatureData, data, data_len); + CopyMem(sd, (void *)owner, sizeof(EFI_GUID)); + CopyMem(sd->SignatureData, (void *)data, data_len); } efi_status = fill_esl(sd, 1, type, sig_size, out, outlen); -- cgit v1.2.3 From 6ea93a28759d754778e483f86f95587a01c5fee8 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Fri, 23 Jul 2021 14:28:59 -0400 Subject: cleanup: always use BS and RT, not gBS and gRT This just makes one less thing we have to make sure is the same between the test harnesses and the runtime code. Signed-off-by: Peter Jones --- MokManager.c | 122 +++++++++++++++++++++++++------------------------- fallback.c | 56 +++++++++++------------ httpboot.c | 40 ++++++++--------- lib/console.c | 6 +-- lib/execute.c | 10 ++--- lib/security_policy.c | 2 +- lib/shell.c | 2 +- lib/simple_file.c | 20 ++++----- mok.c | 27 ++++++----- netboot.c | 4 +- pe.c | 8 ++-- replacements.c | 32 ++++++------- shim.c | 38 ++++++++-------- 13 files changed, 183 insertions(+), 184 deletions(-) (limited to 'lib') diff --git a/MokManager.c b/MokManager.c index cd1492f8..4b6ee146 100644 --- a/MokManager.c +++ b/MokManager.c @@ -735,7 +735,7 @@ done: static INTN reset_system() { - gRT->ResetSystem(EfiResetWarm, EFI_SUCCESS, 0, NULL); + RT->ResetSystem(EfiResetWarm, EFI_SUCCESS, 0, NULL); console_notify(L"Failed to reboot\n"); return -1; } @@ -883,10 +883,10 @@ static EFI_STATUS write_db(CHAR16 * db_name, void *MokNew, UINTN MokNewSize) CopyMem(new_data, old_data, old_size); CopyMem(new_data + old_size, MokNew, MokNewSize); - efi_status = gRT->SetVariable(db_name, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - new_size, new_data); + efi_status = RT->SetVariable(db_name, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + new_size, new_data); out: if (old_size > 0) { FreePool(old_data); @@ -918,8 +918,8 @@ static EFI_STATUS store_keys(void *MokNew, UINTN MokNewSize, int authenticate, } if (authenticate) { - efi_status = gRT->GetVariable(auth_name, &SHIM_LOCK_GUID, - &attributes, &auth_size, auth); + efi_status = RT->GetVariable(auth_name, &SHIM_LOCK_GUID, + &attributes, &auth_size, auth); if (EFI_ERROR(efi_status) || (auth_size != SHA256_DIGEST_SIZE && auth_size != PASSWORD_CRYPT_SIZE)) { @@ -945,10 +945,10 @@ static EFI_STATUS store_keys(void *MokNew, UINTN MokNewSize, int authenticate, if (!MokNewSize) { /* Delete MOK */ - efi_status = gRT->SetVariable(db_name, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - 0, NULL); + efi_status = RT->SetVariable(db_name, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + 0, NULL); } else { /* Write new MOK */ efi_status = write_db(db_name, MokNew, MokNewSize); @@ -1064,10 +1064,10 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num, } if (DataSize == 0) { dprint(L"DataSize = 0; deleting variable %s\n", db_name); - efi_status = gRT->SetVariable(db_name, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - DataSize, Data); + efi_status = RT->SetVariable(db_name, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + DataSize, Data); dprint(L"efi_status:%llu\n", efi_status); return EFI_SUCCESS; } @@ -1109,10 +1109,10 @@ static EFI_STATUS write_back_mok_list(MokListNode * list, INTN key_num, ptr = (uint8_t *) ptr + CertList->SignatureListSize; } - efi_status = gRT->SetVariable(db_name, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - DataSize, Data); + efi_status = RT->SetVariable(db_name, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + DataSize, Data); if (Data) FreePool(Data); @@ -1262,8 +1262,8 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX) auth_name = L"MokDelAuth"; } - efi_status = gRT->GetVariable(auth_name, &SHIM_LOCK_GUID, &attributes, - &auth_size, auth); + efi_status = RT->GetVariable(auth_name, &SHIM_LOCK_GUID, &attributes, + &auth_size, auth); if (EFI_ERROR(efi_status) || (auth_size != SHA256_DIGEST_SIZE && auth_size != PASSWORD_CRYPT_SIZE)) { @@ -1305,9 +1305,9 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX) err_strs[1] = L"Erase all keys in MokList!"; } console_alertbox(err_strs); - gRT->SetVariable(db_name, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, 0, NULL); + RT->SetVariable(db_name, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, 0, NULL); efi_status = EFI_ACCESS_DENIED; goto error; } @@ -1327,9 +1327,9 @@ static EFI_STATUS delete_keys(void *MokDel, UINTN MokDelSize, BOOLEAN MokX) err_strs[1] = L"Reset MokList!"; } console_alertbox(err_strs); - gRT->SetVariable(db_name, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, 0, NULL); + RT->SetVariable(db_name, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, 0, NULL); efi_status = EFI_ABORTED; goto error; } @@ -1541,19 +1541,19 @@ static EFI_STATUS mok_sb_prompt(void *MokSB, UINTN MokSBSize) } if (var->MokSBState == 0) { - efi_status = gRT->SetVariable(L"MokSBState", &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - 1, &sbval); + efi_status = RT->SetVariable(L"MokSBState", &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + 1, &sbval); if (EFI_ERROR(efi_status)) { console_notify(L"Failed to set Secure Boot state"); return efi_status; } } else { - efi_status = gRT->SetVariable(L"MokSBState", &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - 0, NULL); + efi_status = RT->SetVariable(L"MokSBState", &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + 0, NULL); if (EFI_ERROR(efi_status)) { console_notify(L"Failed to delete Secure Boot state"); return efi_status; @@ -1656,19 +1656,19 @@ static EFI_STATUS mok_db_prompt(void *MokDB, UINTN MokDBSize) } if (var->MokDBState == 0) { - efi_status = gRT->SetVariable(L"MokDBState", &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - 1, &dbval); + efi_status = RT->SetVariable(L"MokDBState", &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + 1, &dbval); if (EFI_ERROR(efi_status)) { console_notify(L"Failed to set DB state"); return efi_status; } } else { - efi_status = gRT->SetVariable(L"MokDBState", &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - 0, NULL); + efi_status = RT->SetVariable(L"MokDBState", &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + 0, NULL); if (EFI_ERROR(efi_status)) { console_notify(L"Failed to delete DB state"); return efi_status; @@ -1707,9 +1707,9 @@ static EFI_STATUS mok_pw_prompt(void *MokPW, UINTN MokPWSize) if (console_yes_no(clear_p) == 0) return EFI_ABORTED; - gRT->SetVariable(L"MokPWStore", &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, 0, NULL); + RT->SetVariable(L"MokPWStore", &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, 0, NULL); goto mokpw_done; } @@ -1729,10 +1729,10 @@ static EFI_STATUS mok_pw_prompt(void *MokPW, UINTN MokPWSize) if (console_yes_no(set_p) == 0) return EFI_ABORTED; - efi_status = gRT->SetVariable(L"MokPWStore", &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS, - MokPWSize, MokPW); + efi_status = RT->SetVariable(L"MokPWStore", &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS, + MokPWSize, MokPW); if (EFI_ERROR(efi_status)) { console_notify(L"Failed to set MOK password"); return efi_status; @@ -1994,8 +1994,8 @@ static BOOLEAN verify_pw(BOOLEAN * protected) *protected = FALSE; - efi_status = gRT->GetVariable(L"MokPWStore", &SHIM_LOCK_GUID, &attributes, - &size, pwhash); + efi_status = RT->GetVariable(L"MokPWStore", &SHIM_LOCK_GUID, &attributes, + &size, pwhash); /* * If anything can attack the password it could just set it to a * known value, so there's no safety advantage in failing to validate @@ -2122,29 +2122,29 @@ static EFI_STATUS enter_mok_menu(EFI_HANDLE image_handle UNUSED, UINT32 MokXAuth = 0; UINT32 MokXDelAuth = 0; - efi_status = gRT->GetVariable(L"MokAuth", &SHIM_LOCK_GUID, - &attributes, &auth_size, auth); + efi_status = RT->GetVariable(L"MokAuth", &SHIM_LOCK_GUID, + &attributes, &auth_size, auth); if (!EFI_ERROR(efi_status) && (auth_size == SHA256_DIGEST_SIZE || auth_size == PASSWORD_CRYPT_SIZE)) MokAuth = 1; - efi_status = gRT->GetVariable(L"MokDelAuth", &SHIM_LOCK_GUID, - &attributes, &auth_size, auth); + efi_status = RT->GetVariable(L"MokDelAuth", &SHIM_LOCK_GUID, + &attributes, &auth_size, auth); if (!EFI_ERROR(efi_status) && (auth_size == SHA256_DIGEST_SIZE || auth_size == PASSWORD_CRYPT_SIZE)) MokDelAuth = 1; - efi_status = gRT->GetVariable(L"MokXAuth", &SHIM_LOCK_GUID, - &attributes, &auth_size, auth); + efi_status = RT->GetVariable(L"MokXAuth", &SHIM_LOCK_GUID, + &attributes, &auth_size, auth); if (!EFI_ERROR(efi_status) && (auth_size == SHA256_DIGEST_SIZE || auth_size == PASSWORD_CRYPT_SIZE)) MokXAuth = 1; - efi_status = gRT->GetVariable(L"MokXDelAuth", &SHIM_LOCK_GUID, - &attributes, &auth_size, auth); + efi_status = RT->GetVariable(L"MokXDelAuth", &SHIM_LOCK_GUID, + &attributes, &auth_size, auth); if (!EFI_ERROR(efi_status) && (auth_size == SHA256_DIGEST_SIZE || auth_size == PASSWORD_CRYPT_SIZE)) @@ -2496,7 +2496,7 @@ static EFI_STATUS setup_rand(void) UINT64 seed; BOOLEAN status; - efi_status = gRT->GetTime(&time, NULL); + efi_status = RT->GetTime(&time, NULL); if (EFI_ERROR(efi_status)) return efi_status; diff --git a/fallback.c b/fallback.c index 302eeac1..ce907099 100644 --- a/fallback.c +++ b/fallback.c @@ -252,7 +252,7 @@ add_boot_option(EFI_DEVICE_PATH *hddp, EFI_DEVICE_PATH *fulldp, first_new_option_size = StrLen(arguments) * sizeof (CHAR16); } - efi_status = gRT->SetVariable(varname, &GV_GUID, + efi_status = RT->SetVariable(varname, &GV_GUID, EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS, @@ -431,8 +431,8 @@ find_boot_option(EFI_DEVICE_PATH *dp, EFI_DEVICE_PATH *fulldp, while (1) { UINTN varname_size = buffer_size; - efi_status = gRT->GetNextVariableName(&varname_size, varname, - &vendor_guid); + efi_status = RT->GetNextVariableName(&varname_size, varname, + &vendor_guid); if (EFI_ERROR(efi_status)) { if (efi_status == EFI_BUFFER_TOO_SMALL) { VerbosePrint(L"Buffer too small for next variable name, re-allocating it to be %d bytes and retrying\n", @@ -464,8 +464,8 @@ find_boot_option(EFI_DEVICE_PATH *dp, EFI_DEVICE_PATH *fulldp, continue; UINTN candidate_size = max_candidate_size; - efi_status = gRT->GetVariable(varname, &GV_GUID, NULL, - &candidate_size, candidate); + efi_status = RT->GetVariable(varname, &GV_GUID, NULL, + &candidate_size, candidate); if (EFI_ERROR(efi_status)) continue; @@ -543,15 +543,15 @@ update_boot_order(void) for (j = 0 ; j < size / sizeof (CHAR16); j++) VerbosePrintUnprefixed(L"%04x ", newbootorder[j]); VerbosePrintUnprefixed(L"\n"); - efi_status = gRT->GetVariable(L"BootOrder", &GV_GUID, NULL, &len, NULL); + efi_status = RT->GetVariable(L"BootOrder", &GV_GUID, NULL, &len, NULL); if (efi_status == EFI_BUFFER_TOO_SMALL) LibDeleteVariable(L"BootOrder", &GV_GUID); - efi_status = gRT->SetVariable(L"BootOrder", &GV_GUID, - EFI_VARIABLE_NON_VOLATILE | - EFI_VARIABLE_BOOTSERVICE_ACCESS | - EFI_VARIABLE_RUNTIME_ACCESS, - size, newbootorder); + efi_status = RT->SetVariable(L"BootOrder", &GV_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS | + EFI_VARIABLE_RUNTIME_ACCESS, + size, newbootorder); FreePool(newbootorder); return efi_status; } @@ -862,8 +862,8 @@ find_boot_options(EFI_HANDLE device) EFI_STATUS efi_status; EFI_FILE_IO_INTERFACE *fio = NULL; - efi_status = gBS->HandleProtocol(device, &FileSystemProtocol, - (void **) &fio); + efi_status = BS->HandleProtocol(device, &FileSystemProtocol, + (void **) &fio); if (EFI_ERROR(efi_status)) { console_print(L"Couldn't find file system: %r\n", efi_status); return efi_status; @@ -990,8 +990,8 @@ try_start_first_option(EFI_HANDLE parent_image_handle) return EFI_SUCCESS; } - efi_status = gBS->LoadImage(0, parent_image_handle, first_new_option, - NULL, 0, &image_handle); + efi_status = BS->LoadImage(0, parent_image_handle, first_new_option, + NULL, 0, &image_handle); if (EFI_ERROR(efi_status)) { CHAR16 *dps = DevicePathToStr(first_new_option); UINTN s = DevicePathSize(first_new_option); @@ -1011,14 +1011,14 @@ try_start_first_option(EFI_HANDLE parent_image_handle) } EFI_LOADED_IMAGE *image; - efi_status = gBS->HandleProtocol(image_handle, &LoadedImageProtocol, - (void *) &image); + efi_status = BS->HandleProtocol(image_handle, &LoadedImageProtocol, + (void *) &image); if (!EFI_ERROR(efi_status)) { image->LoadOptions = first_new_option_args; image->LoadOptionsSize = first_new_option_size; } - efi_status = gBS->StartImage(image_handle, NULL, NULL); + efi_status = BS->StartImage(image_handle, NULL, NULL); if (EFI_ERROR(efi_status)) { console_print(L"StartImage failed: %r\n", efi_status); msleep(500000000); @@ -1033,8 +1033,8 @@ get_fallback_no_reboot(void) UINT32 no_reboot; UINTN size = sizeof(UINT32); - efi_status = gRT->GetVariable(NO_REBOOT, &SHIM_LOCK_GUID, - NULL, &size, &no_reboot); + efi_status = RT->GetVariable(NO_REBOOT, &SHIM_LOCK_GUID, + NULL, &size, &no_reboot); if (!EFI_ERROR(efi_status)) { return no_reboot; } @@ -1047,11 +1047,11 @@ set_fallback_no_reboot(void) { EFI_STATUS efi_status; UINT32 no_reboot = 1; - efi_status = gRT->SetVariable(NO_REBOOT, &SHIM_LOCK_GUID, - EFI_VARIABLE_NON_VOLATILE - | EFI_VARIABLE_BOOTSERVICE_ACCESS - | EFI_VARIABLE_RUNTIME_ACCESS, - sizeof(UINT32), &no_reboot); + efi_status = RT->SetVariable(NO_REBOOT, &SHIM_LOCK_GUID, + EFI_VARIABLE_NON_VOLATILE | + EFI_VARIABLE_BOOTSERVICE_ACCESS | + EFI_VARIABLE_RUNTIME_ACCESS, + sizeof(UINT32), &no_reboot); return efi_status; } @@ -1129,8 +1129,8 @@ efi_main(EFI_HANDLE image, EFI_SYSTEM_TABLE *systab) */ debug_hook(); - efi_status = gBS->HandleProtocol(image, &LoadedImageProtocol, - (void *) &this_image); + efi_status = BS->HandleProtocol(image, &LoadedImageProtocol, + (void *) &this_image); if (EFI_ERROR(efi_status)) { console_print(L"Error: could not find loaded image: %r\n", efi_status); @@ -1191,7 +1191,7 @@ reset: msleep(fallback_verbose_wait); } - gRT->ResetSystem(EfiResetCold, EFI_SUCCESS, 0, NULL); + RT->ResetSystem(EfiResetCold, EFI_SUCCESS, 0, NULL); return EFI_SUCCESS; } diff --git a/httpboot.c b/httpboot.c index 3340a7f9..dfa493bf 100644 --- a/httpboot.c +++ b/httpboot.c @@ -232,9 +232,9 @@ get_nic_handle (EFI_MAC_ADDRESS *mac) /* Get the list of handles that support the HTTP service binding protocol */ - efi_status = gBS->LocateHandleBuffer(ByProtocol, - &EFI_HTTP_BINDING_GUID, - NULL, &NoHandles, &buffer); + efi_status = BS->LocateHandleBuffer(ByProtocol, + &EFI_HTTP_BINDING_GUID, + NULL, &NoHandles, &buffer); if (EFI_ERROR(efi_status)) return NULL; @@ -306,8 +306,8 @@ set_ip6(EFI_HANDLE *nic, IPv6_DEVICE_PATH *ip6node) EFI_IPv6_ADDRESS gateway; EFI_STATUS efi_status; - efi_status = gBS->HandleProtocol(nic, &EFI_IP6_CONFIG_GUID, - (VOID **)&ip6cfg); + efi_status = BS->HandleProtocol(nic, &EFI_IP6_CONFIG_GUID, + (VOID **)&ip6cfg); if (EFI_ERROR(efi_status)) return efi_status; @@ -367,8 +367,8 @@ set_ip4(EFI_HANDLE *nic, IPv4_DEVICE_PATH *ip4node) EFI_IPv4_ADDRESS gateway; EFI_STATUS efi_status; - efi_status = gBS->HandleProtocol(nic, &EFI_IP4_CONFIG2_GUID, - (VOID **)&ip4cfg2); + efi_status = BS->HandleProtocol(nic, &EFI_IP4_CONFIG2_GUID, + (VOID **)&ip4cfg2); if (EFI_ERROR(efi_status)) return efi_status; @@ -470,9 +470,9 @@ send_http_request (EFI_HTTP_PROTOCOL *http, CHAR8 *hostname, CHAR8 *uri) tx_token.Message = &tx_message; tx_token.Event = NULL; request_done = FALSE; - efi_status = gBS->CreateEvent(EVT_NOTIFY_SIGNAL, TPL_NOTIFY, - httpnotify, &request_done, - &tx_token.Event); + efi_status = BS->CreateEvent(EVT_NOTIFY_SIGNAL, TPL_NOTIFY, + httpnotify, &request_done, + &tx_token.Event); if (EFI_ERROR(efi_status)) { perror(L"Failed to Create Event for HTTP request: %r\n", efi_status); @@ -496,7 +496,7 @@ send_http_request (EFI_HTTP_PROTOCOL *http, CHAR8 *hostname, CHAR8 *uri) } error: - event_status = gBS->CloseEvent(tx_token.Event); + event_status = BS->CloseEvent(tx_token.Event); if (EFI_ERROR(event_status)) { perror(L"Failed to close Event for HTTP request: %r\n", event_status); @@ -534,9 +534,9 @@ receive_http_response(EFI_HTTP_PROTOCOL *http, VOID **buffer, UINT64 *buf_size) rx_token.Message = &rx_message; rx_token.Event = NULL; response_done = FALSE; - efi_status = gBS->CreateEvent(EVT_NOTIFY_SIGNAL, TPL_NOTIFY, - httpnotify, &response_done, - &rx_token.Event); + efi_status = BS->CreateEvent(EVT_NOTIFY_SIGNAL, TPL_NOTIFY, + httpnotify, &response_done, + &rx_token.Event); if (EFI_ERROR(efi_status)) { perror(L"Failed to Create Event for HTTP response: %r\n", efi_status); @@ -632,7 +632,7 @@ receive_http_response(EFI_HTTP_PROTOCOL *http, VOID **buffer, UINT64 *buf_size) } error: - event_status = gBS->CloseEvent(rx_token.Event); + event_status = BS->CloseEvent(rx_token.Event); if (EFI_ERROR(event_status)) { perror(L"Failed to close Event for HTTP response: %r\n", event_status); @@ -660,9 +660,9 @@ http_fetch (EFI_HANDLE image, EFI_HANDLE device, *buf_size = 0; /* Open HTTP Service Binding Protocol */ - efi_status = gBS->OpenProtocol(device, &EFI_HTTP_BINDING_GUID, - (VOID **) &service, image, NULL, - EFI_OPEN_PROTOCOL_GET_PROTOCOL); + efi_status = BS->OpenProtocol(device, &EFI_HTTP_BINDING_GUID, + (VOID **) &service, image, NULL, + EFI_OPEN_PROTOCOL_GET_PROTOCOL); if (EFI_ERROR(efi_status)) return efi_status; @@ -676,8 +676,8 @@ http_fetch (EFI_HANDLE image, EFI_HANDLE device, } /* Get the http protocol */ - efi_status = gBS->HandleProtocol(http_handle, &EFI_HTTP_PROTOCOL_GUID, - (VOID **) &http); + efi_status = BS->HandleProtocol(http_handle, &EFI_HTTP_PROTOCOL_GUID, + (VOID **) &http); if (EFI_ERROR(efi_status)) { perror(L"Failed to get http\n"); goto error; diff --git a/lib/console.c b/lib/console.c index c310d213..5193b578 100644 --- a/lib/console.c +++ b/lib/console.c @@ -35,7 +35,7 @@ console_get_keystroke(EFI_INPUT_KEY *key) EFI_STATUS efi_status; do { - gBS->WaitForEvent(1, &ci->WaitForKey, &EventIndex); + BS->WaitForEvent(1, &ci->WaitForKey, &EventIndex); efi_status = ci->ReadKeyStroke(ci, key); } while (efi_status == EFI_NOT_READY); @@ -495,7 +495,7 @@ console_mode_handle(VOID) UINTN rows = 0, columns = 0; EFI_STATUS efi_status = EFI_SUCCESS; - efi_status = gBS->LocateProtocol(&gop_guid, NULL, (void **)&gop); + efi_status = BS->LocateProtocol(&gop_guid, NULL, (void **)&gop); if (EFI_ERROR(efi_status)) { console_error(L"Locate graphic output protocol fail", efi_status); return; @@ -679,7 +679,7 @@ setup_verbosity(VOID) VOID msleep(unsigned long msecs) { - gBS->Stall(msecs); + BS->Stall(msecs); } /* This is used in various things to determine if we should print to the diff --git a/lib/execute.c b/lib/execute.c index 642f94a3..0eb872e4 100644 --- a/lib/execute.c +++ b/lib/execute.c @@ -63,8 +63,8 @@ execute(EFI_HANDLE image, CHAR16 *name) EFI_DEVICE_PATH *devpath; CHAR16 *PathName; - efi_status = gBS->HandleProtocol(image, &IMAGE_PROTOCOL, - (void **) &li); + efi_status = BS->HandleProtocol(image, &IMAGE_PROTOCOL, + (void **) &li); if (EFI_ERROR(efi_status)) return efi_status; @@ -72,12 +72,12 @@ execute(EFI_HANDLE image, CHAR16 *name) if (EFI_ERROR(efi_status)) return efi_status; - efi_status = gBS->LoadImage(FALSE, image, devpath, NULL, 0, &h); + efi_status = BS->LoadImage(FALSE, image, devpath, NULL, 0, &h); if (EFI_ERROR(efi_status)) goto out; - efi_status = gBS->StartImage(h, NULL, NULL); - gBS->UnloadImage(h); + efi_status = BS->StartImage(h, NULL, NULL); + BS->UnloadImage(h); out: FreePool(PathName); diff --git a/lib/security_policy.c b/lib/security_policy.c index 6c42cc14..0f2569b0 100644 --- a/lib/security_policy.c +++ b/lib/security_policy.c @@ -123,7 +123,7 @@ security_policy_authentication ( * EFI_SECURITY_VIOLATION */ fail_status = efi_status; - efi_status = gBS->LocateDevicePath(&SIMPLE_FS_PROTOCOL, &DevPath, &h); + efi_status = BS->LocateDevicePath(&SIMPLE_FS_PROTOCOL, &DevPath, &h); if (EFI_ERROR(efi_status)) goto out; diff --git a/lib/shell.c b/lib/shell.c index 146d9a21..8be4fe08 100644 --- a/lib/shell.c +++ b/lib/shell.c @@ -16,7 +16,7 @@ argsplit(EFI_HANDLE image, int *argc, CHAR16*** ARGV) *argc = 0; - efi_status = gBS->HandleProtocol(image, &LoadedImageProtocol, + efi_status = BS->HandleProtocol(image, &LoadedImageProtocol, (VOID **) &info); if (EFI_ERROR(efi_status)) { console_print(L"Failed to get arguments\n"); diff --git a/lib/simple_file.c b/lib/simple_file.c index 5fd3e1a6..f22852d4 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -11,8 +11,8 @@ simple_file_open_by_handle(EFI_HANDLE device, CHAR16 *name, EFI_FILE **file, UIN EFI_FILE_IO_INTERFACE *drive; EFI_FILE *root; - efi_status = gBS->HandleProtocol(device, &EFI_SIMPLE_FILE_SYSTEM_GUID, - (void **)&drive); + efi_status = BS->HandleProtocol(device, &EFI_SIMPLE_FILE_SYSTEM_GUID, + (void **)&drive); if (EFI_ERROR(efi_status)) { console_print(L"Unable to find simple file protocol (%d)\n", efi_status); @@ -40,8 +40,8 @@ simple_file_open(EFI_HANDLE image, CHAR16 *name, EFI_FILE **file, UINT64 mode) EFI_DEVICE_PATH *loadpath = NULL; CHAR16 *PathName = NULL; - efi_status = gBS->HandleProtocol(image, &IMAGE_PROTOCOL, - (void **) &li); + efi_status = BS->HandleProtocol(image, &IMAGE_PROTOCOL, + (void **) &li); if (EFI_ERROR(efi_status)) return simple_file_open_by_handle(image, name, file, mode); @@ -176,9 +176,9 @@ simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) CHAR16 **entries; int val; - efi_status = gBS->LocateHandleBuffer(ByProtocol, - &EFI_SIMPLE_FILE_SYSTEM_GUID, - NULL, &count, &vol_handles); + efi_status = BS->LocateHandleBuffer(ByProtocol, + &EFI_SIMPLE_FILE_SYSTEM_GUID, + NULL, &count, &vol_handles); if (EFI_ERROR(efi_status)) return efi_status; if (!count || !vol_handles) @@ -196,9 +196,9 @@ simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) CHAR16 *name; EFI_FILE_IO_INTERFACE *drive; - efi_status = gBS->HandleProtocol(vol_handles[i], - &EFI_SIMPLE_FILE_SYSTEM_GUID, - (void **) &drive); + efi_status = BS->HandleProtocol(vol_handles[i], + &EFI_SIMPLE_FILE_SYSTEM_GUID, + (void **) &drive); if (EFI_ERROR(efi_status) || !drive) continue; diff --git a/mok.c b/mok.c index 84e51f3e..af1756c2 100644 --- a/mok.c +++ b/mok.c @@ -16,8 +16,8 @@ static BOOLEAN check_var(CHAR16 *varname) UINT32 MokVar; UINT32 attributes; - efi_status = gRT->GetVariable(varname, &SHIM_LOCK_GUID, &attributes, - &size, (void *)&MokVar); + efi_status = RT->GetVariable(varname, &SHIM_LOCK_GUID, &attributes, + &size, (void *)&MokVar); if (!EFI_ERROR(efi_status) || efi_status == EFI_BUFFER_TOO_SMALL) return TRUE; @@ -27,7 +27,7 @@ static BOOLEAN check_var(CHAR16 *varname) #define SetVariable(name, guid, attrs, varsz, var) \ ({ \ EFI_STATUS efi_status_; \ - efi_status_ = gRT->SetVariable(name, guid, attrs, varsz, var); \ + efi_status_ = RT->SetVariable(name, guid, attrs, varsz, var); \ dprint_(L"%a:%d:%a() SetVariable(\"%s\", ... varsz=0x%llx) = %r\n", \ __FILE__, __LINE__ - 5, __func__, name, varsz, \ efi_status_); \ @@ -273,16 +273,16 @@ get_max_var_sz(UINT32 attrs, SIZE_T *max_var_szp) uint64_t max_var_sz = 0; *max_var_szp = 0; - if (EFI_MAJOR_VERSION(gRT) < 2) { + if (EFI_MAJOR_VERSION(RT) < 2) { dprint(L"EFI %d.%d; no RT->QueryVariableInfo(). Using 1024!\n", - EFI_MAJOR_VERSION(gRT), EFI_MINOR_VERSION(gRT)); + EFI_MAJOR_VERSION(RT), EFI_MINOR_VERSION(RT)); max_var_sz = remaining_sz = max_storage_sz = 1024; efi_status = EFI_SUCCESS; } else { dprint(L"calling RT->QueryVariableInfo() at 0x%lx\n", - gRT->QueryVariableInfo); - efi_status = gRT->QueryVariableInfo(attrs, &max_storage_sz, - &remaining_sz, &max_var_sz); + RT->QueryVariableInfo); + efi_status = RT->QueryVariableInfo(attrs, &max_storage_sz, + &remaining_sz, &max_var_sz); if (EFI_ERROR(efi_status)) { perror(L"Could not get variable storage info: %r\n", efi_status); @@ -1016,10 +1016,9 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle) config_sz += sizeof(config_template); npages = ALIGN_VALUE(config_sz, PAGE_SIZE) >> EFI_PAGE_SHIFT; config_table = NULL; - efi_status = gBS->AllocatePages(AllocateAnyPages, - EfiBootServicesData, - npages, - (EFI_PHYSICAL_ADDRESS *)&config_table); + efi_status = BS->AllocatePages( + AllocateAnyPages, EfiBootServicesData, npages, + (EFI_PHYSICAL_ADDRESS *)&config_table); if (EFI_ERROR(efi_status) || !config_table) { console_print(L"Allocating %lu pages for mok config table failed: %r\n", npages, efi_status); @@ -1050,8 +1049,8 @@ EFI_STATUS import_mok_state(EFI_HANDLE image_handle) ZeroMem(&config_template, sizeof(config_template)); CopyMem(p, &config_template, sizeof(config_template)); - efi_status = gBS->InstallConfigurationTable(&MOK_VARIABLE_STORE, - config_table); + efi_status = BS->InstallConfigurationTable(&MOK_VARIABLE_STORE, + config_table); if (EFI_ERROR(efi_status)) { console_print(L"Couldn't install MoK configuration table\n"); } diff --git a/netboot.c b/netboot.c index 3f5c5198..cf5882c1 100644 --- a/netboot.c +++ b/netboot.c @@ -36,8 +36,8 @@ BOOLEAN findNetboot(EFI_HANDLE device) { EFI_STATUS efi_status; - efi_status = gBS->HandleProtocol(device, &PxeBaseCodeProtocol, - (VOID **) &pxe); + efi_status = BS->HandleProtocol(device, &PxeBaseCodeProtocol, + (VOID **) &pxe); if (EFI_ERROR(efi_status)) { pxe = NULL; return FALSE; diff --git a/pe.c b/pe.c index 13bc3975..5db45086 100644 --- a/pe.c +++ b/pe.c @@ -949,8 +949,8 @@ handle_image (void *data, unsigned int datasize, PAGE_SIZE); *alloc_pages = alloc_size / PAGE_SIZE; - efi_status = gBS->AllocatePages(AllocateAnyPages, EfiLoaderCode, - *alloc_pages, alloc_address); + efi_status = BS->AllocatePages(AllocateAnyPages, EfiLoaderCode, + *alloc_pages, alloc_address); if (EFI_ERROR(efi_status)) { perror(L"Failed to allocate image buffer\n"); return EFI_OUT_OF_RESOURCES; @@ -963,7 +963,7 @@ handle_image (void *data, unsigned int datasize, *entry_point = ImageAddress(buffer, context.ImageSize, context.EntryPoint); if (!*entry_point) { perror(L"Entry point is invalid\n"); - gBS->FreePages(*alloc_address, *alloc_pages); + BS->FreePages(*alloc_address, *alloc_pages); return EFI_UNSUPPORTED; } @@ -1004,7 +1004,7 @@ handle_image (void *data, unsigned int datasize, if (end < base) { perror(L"Section %d has negative size\n", i); - gBS->FreePages(*alloc_address, *alloc_pages); + BS->FreePages(*alloc_address, *alloc_pages); return EFI_UNSUPPORTED; } diff --git a/replacements.c b/replacements.c index daa2e0f4..bf781a8b 100644 --- a/replacements.c +++ b/replacements.c @@ -50,7 +50,7 @@ unhook_system_services(void) #if !defined(DISABLE_EBS_PROTECTION) systab->BootServices->ExitBootServices = system_exit_boot_services; #endif /* !defined(DISABLE_EBS_PROTECTION) */ - gBS = systab->BootServices; + BS = systab->BootServices; } static EFI_STATUS EFIAPI @@ -61,8 +61,8 @@ load_image(BOOLEAN BootPolicy, EFI_HANDLE ParentImageHandle, EFI_STATUS efi_status; unhook_system_services(); - efi_status = gBS->LoadImage(BootPolicy, ParentImageHandle, DevicePath, - SourceBuffer, SourceSize, ImageHandle); + efi_status = BS->LoadImage(BootPolicy, ParentImageHandle, DevicePath, + SourceBuffer, SourceSize, ImageHandle); hook_system_services(systab); if (EFI_ERROR(efi_status)) last_loaded_image = NULL; @@ -81,7 +81,7 @@ replacement_start_image(EFI_HANDLE image_handle, UINTN *exit_data_size, CHAR16 * loader_is_participating = 1; uninstall_shim_protocols(); } - efi_status = gBS->StartImage(image_handle, exit_data_size, exit_data); + efi_status = BS->StartImage(image_handle, exit_data_size, exit_data); if (EFI_ERROR(efi_status)) { if (image_handle == last_loaded_image) { EFI_STATUS efi_status2 = install_shim_protocols(); @@ -91,9 +91,9 @@ replacement_start_image(EFI_HANDLE image_handle, UINTN *exit_data_size, CHAR16 * efi_status2); console_print(L"shim cannot continue, sorry.\n"); msleep(5000000); - gRT->ResetSystem(EfiResetShutdown, - EFI_SECURITY_VIOLATION, - 0, NULL); + RT->ResetSystem(EfiResetShutdown, + EFI_SECURITY_VIOLATION, + 0, NULL); } } hook_system_services(systab); @@ -110,7 +110,7 @@ exit_boot_services(EFI_HANDLE image_key, UINTN map_key) verification_method == VERIFIED_BY_HASH) { unhook_system_services(); EFI_STATUS efi_status; - efi_status = gBS->ExitBootServices(image_key, map_key); + efi_status = BS->ExitBootServices(image_key, map_key); if (EFI_ERROR(efi_status)) hook_system_services(systab); return efi_status; @@ -119,7 +119,7 @@ exit_boot_services(EFI_HANDLE image_key, UINTN map_key) console_print(L"Bootloader has not verified loaded image.\n"); console_print(L"System is compromised. halting.\n"); msleep(5000000); - gRT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL); + RT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL); return EFI_SECURITY_VIOLATION; } #endif /* !defined(DISABLE_EBS_PROTECTION) */ @@ -134,8 +134,8 @@ do_exit(EFI_HANDLE ImageHandle, EFI_STATUS ExitStatus, restore_loaded_image(); - efi_status = gBS->Exit(ImageHandle, ExitStatus, - ExitDataSize, ExitData); + efi_status = BS->Exit(ImageHandle, ExitStatus, + ExitDataSize, ExitData); if (EFI_ERROR(efi_status)) { EFI_STATUS efi_status2 = shim_init(); @@ -144,8 +144,8 @@ do_exit(EFI_HANDLE ImageHandle, EFI_STATUS ExitStatus, efi_status2); console_print(L"shim cannot continue, sorry.\n"); msleep(5000000); - gRT->ResetSystem(EfiResetShutdown, - EFI_SECURITY_VIOLATION, 0, NULL); + RT->ResetSystem(EfiResetShutdown, + EFI_SECURITY_VIOLATION, 0, NULL); } } return efi_status; @@ -155,7 +155,7 @@ void hook_system_services(EFI_SYSTEM_TABLE *local_systab) { systab = local_systab; - gBS = systab->BootServices; + BS = systab->BootServices; /* We need to hook various calls to make this work... */ @@ -186,14 +186,14 @@ void unhook_exit(void) { systab->BootServices->Exit = system_exit; - gBS = systab->BootServices; + BS = systab->BootServices; } void hook_exit(EFI_SYSTEM_TABLE *local_systab) { systab = local_systab; - gBS = local_systab->BootServices; + BS = local_systab->BootServices; /* we need to hook Exit() so that we can allow users to quit the * bootloader and still e.g. start a new one or run an internal diff --git a/shim.c b/shim.c index 1e774f71..19b78b1b 100644 --- a/shim.c +++ b/shim.c @@ -721,8 +721,8 @@ should_use_fallback(EFI_HANDLE image_handle) EFI_STATUS efi_status; int ret = 0; - efi_status = gBS->HandleProtocol(image_handle, &EFI_LOADED_IMAGE_GUID, - (void **)&li); + efi_status = BS->HandleProtocol(image_handle, &EFI_LOADED_IMAGE_GUID, + (void **)&li); if (EFI_ERROR(efi_status)) { perror(L"Could not get image for boot" EFI_ARCH L".efi: %r\n", efi_status); @@ -746,8 +746,8 @@ should_use_fallback(EFI_HANDLE image_handle) if (pathlen < 5 || StrCaseCmp(bootpath + pathlen - 4, L".EFI")) goto error; - efi_status = gBS->HandleProtocol(li->DeviceHandle, &FileSystemProtocol, - (void **) &fio); + efi_status = BS->HandleProtocol(li->DeviceHandle, &FileSystemProtocol, + (void **) &fio); if (EFI_ERROR(efi_status)) { perror(L"Could not get fio for li->DeviceHandle: %r\n", efi_status); @@ -803,8 +803,8 @@ static EFI_STATUS load_image (EFI_LOADED_IMAGE *li, void **data, /* * Open the device */ - efi_status = gBS->HandleProtocol(device, &EFI_SIMPLE_FILE_SYSTEM_GUID, - (void **) &drive); + efi_status = BS->HandleProtocol(device, &EFI_SIMPLE_FILE_SYSTEM_GUID, + (void **) &drive); if (EFI_ERROR(efi_status)) { perror(L"Failed to find fs: %r\n", efi_status); goto error; @@ -1004,8 +1004,8 @@ EFI_STATUS start_image(EFI_HANDLE image_handle, CHAR16 *ImagePath) * We need to refer to the loaded image protocol on the running * binary in order to find our path */ - efi_status = gBS->HandleProtocol(image_handle, &EFI_LOADED_IMAGE_GUID, - (void **)&shim_li); + efi_status = BS->HandleProtocol(image_handle, &EFI_LOADED_IMAGE_GUID, + (void **)&shim_li); if (EFI_ERROR(efi_status)) { perror(L"Unable to init protocol\n"); return efi_status; @@ -1156,8 +1156,8 @@ EFI_STATUS set_second_stage (EFI_HANDLE image_handle) load_options = NULL; load_options_size = 0; - efi_status = gBS->HandleProtocol(image_handle, &LoadedImageProtocol, - (void **) &li); + efi_status = BS->HandleProtocol(image_handle, &LoadedImageProtocol, + (void **) &li); if (EFI_ERROR(efi_status)) { perror (L"Failed to get load options: %r\n", efi_status); return efi_status; @@ -1245,10 +1245,10 @@ install_shim_protocols(void) /* * Install the protocol */ - efi_status = gBS->InstallProtocolInterface(&shim_lock_handle, - &SHIM_LOCK_GUID, - EFI_NATIVE_INTERFACE, - &shim_lock_interface); + efi_status = BS->InstallProtocolInterface(&shim_lock_handle, + &SHIM_LOCK_GUID, + EFI_NATIVE_INTERFACE, + &shim_lock_interface); if (EFI_ERROR(efi_status)) { console_error(L"Could not install security protocol", efi_status); @@ -1274,8 +1274,8 @@ uninstall_shim_protocols(void) /* * If we're back here then clean everything up before exiting */ - gBS->UninstallProtocolInterface(shim_lock_handle, &SHIM_LOCK_GUID, - &shim_lock_interface); + BS->UninstallProtocolInterface(shim_lock_handle, &SHIM_LOCK_GUID, + &shim_lock_interface); if (!secure_mode()) return; @@ -1429,7 +1429,7 @@ devel_egress(devel_egress_action action UNUSED) console_print(L"\ndoing %a\n", action); if (action == COLD_RESET) - gRT->ResetSystem(EfiResetCold, EFI_SECURITY_VIOLATION, 0, NULL); + RT->ResetSystem(EfiResetCold, EFI_SECURITY_VIOLATION, 0, NULL); #endif } @@ -1556,8 +1556,8 @@ die: devel_egress(COLD_RESET); #else msleep(5000000); - gRT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, - 0, NULL); + RT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, + 0, NULL); #endif } -- cgit v1.2.3 From cae5e2f7c100bc9e8f07de62353021d6737a50ee Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Fri, 23 Jul 2021 14:18:06 -0400 Subject: shim/mm/fb: move global state to its own source file This moves the globals from shim.c (and lib/console.c) into their own file, to make it so that unit tests can more easily link against code that uses that state. Signed-off-by: Peter Jones --- Makefile | 8 ++++---- globals.c | 31 +++++++++++++++++++++++++++++++ lib/console.c | 2 -- shim.c | 20 -------------------- 4 files changed, 35 insertions(+), 26 deletions(-) create mode 100644 globals.c (limited to 'lib') diff --git a/Makefile b/Makefile index 097cbd30..07936e52 100644 --- a/Makefile +++ b/Makefile @@ -38,12 +38,12 @@ CFLAGS += -DENABLE_SHIM_CERT else TARGETS += $(MMNAME) $(FBNAME) endif -OBJS = shim.o mok.o netboot.o cert.o replacements.o tpm.o version.o errlog.o sbat.o sbat_data.o pe.o httpboot.o csv.o load-options.o +OBJS = shim.o globals.o mok.o netboot.o cert.o replacements.o tpm.o version.o errlog.o sbat.o sbat_data.o pe.o httpboot.o csv.o load-options.o KEYS = shim_cert.h ocsp.* ca.* shim.crt shim.csr shim.p12 shim.pem shim.key shim.cer -ORIG_SOURCES = shim.c mok.c netboot.c replacements.c tpm.c errlog.c sbat.c pe.c httpboot.c shim.h version.h $(wildcard include/*.h) -MOK_OBJS = MokManager.o PasswordCrypt.o crypt_blowfish.o errlog.o sbat_data.o +ORIG_SOURCES = shim.c globals.c mok.c netboot.c replacements.c tpm.c errlog.c sbat.c pe.c httpboot.c shim.h version.h $(wildcard include/*.h) +MOK_OBJS = MokManager.o PasswordCrypt.o crypt_blowfish.o errlog.o sbat_data.o globals.o ORIG_MOK_SOURCES = MokManager.c PasswordCrypt.c crypt_blowfish.c shim.h $(wildcard include/*.h) -FALLBACK_OBJS = fallback.o tpm.o errlog.o sbat_data.o +FALLBACK_OBJS = fallback.o tpm.o errlog.o sbat_data.o globals.o ORIG_FALLBACK_SRCS = fallback.c SBATPATH = $(TOPDIR)/data/sbat.csv diff --git a/globals.c b/globals.c new file mode 100644 index 00000000..476e2e9c --- /dev/null +++ b/globals.c @@ -0,0 +1,31 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent +/* + * globals.c - global shim state + * Copyright Peter Jones + */ + +#include "shim.h" + +UINT32 vendor_authorized_size = 0; +UINT8 *vendor_authorized = NULL; + +UINT32 vendor_deauthorized_size = 0; +UINT8 *vendor_deauthorized = NULL; + +#if defined(ENABLE_SHIM_CERT) +UINT32 build_cert_size; +UINT8 *build_cert; +#endif /* defined(ENABLE_SHIM_CERT) */ + +/* + * indicator of how an image has been verified + */ +verification_method_t verification_method; +int loader_is_participating; + +UINT8 user_insecure_mode; +UINT8 ignore_db; + +UINT32 verbose = 0; + +// vim:fenc=utf-8:tw=75:noet diff --git a/lib/console.c b/lib/console.c index 5193b578..2a669228 100644 --- a/lib/console.c +++ b/lib/console.c @@ -655,8 +655,6 @@ console_reset(void) co->ClearScreen(co); } -UINT32 verbose = 0; - VOID setup_verbosity(VOID) { diff --git a/shim.c b/shim.c index 19b78b1b..65f51abc 100644 --- a/shim.c +++ b/shim.c @@ -52,28 +52,8 @@ extern struct { UINT32 vendor_deauthorized_offset; } cert_table; -UINT32 vendor_authorized_size = 0; -UINT8 *vendor_authorized = NULL; - -UINT32 vendor_deauthorized_size = 0; -UINT8 *vendor_deauthorized = NULL; - -#if defined(ENABLE_SHIM_CERT) -UINT32 build_cert_size; -UINT8 *build_cert; -#endif /* defined(ENABLE_SHIM_CERT) */ - -/* - * indicator of how an image has been verified - */ -verification_method_t verification_method; -int loader_is_participating; - #define EFI_IMAGE_SECURITY_DATABASE_GUID { 0xd719b2cb, 0x3d3a, 0x4596, { 0xa3, 0xbc, 0xda, 0xd0, 0x0e, 0x67, 0x65, 0x6f }} -UINT8 user_insecure_mode; -UINT8 ignore_db; - typedef enum { DATA_FOUND, DATA_NOT_FOUND, -- cgit v1.2.3 From 1872c929cc3a466c75336307901e67917bcc46bc Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 16 Sep 2021 16:43:24 -0400 Subject: console: check that ST->ConIn and ST->ConOut are non-NULL There's been some discussion on how to handle machines without console devices. The consensus so far has been that they should have dummy ConOut implementations, but that means the first vendor to build a machine without asking around is in for some surprises. This patch makes the places where our console library uses ST->ConIn or ST->ConOut check that they're present before doing so. Signed-off-by: Peter Jones --- lib/console.c | 30 +++++++++++++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) (limited to 'lib') diff --git a/lib/console.c b/lib/console.c index 2a669228..6b1e4c2f 100644 --- a/lib/console.c +++ b/lib/console.c @@ -34,6 +34,9 @@ console_get_keystroke(EFI_INPUT_KEY *key) UINTN EventIndex; EFI_STATUS efi_status; + if (!ci) + return EFI_UNSUPPORTED; + do { BS->WaitForEvent(1, &ci->WaitForKey, &EventIndex); efi_status = ci->ReadKeyStroke(ci, key); @@ -109,7 +112,8 @@ console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) if (!console_text_mode) setup_console(1); - co->SetCursorPosition(co, col, row); + if (co) + co->SetCursorPosition(co, col, row); ms_va_start(args, fmt); ret = VPrint(fmt, args); @@ -136,6 +140,9 @@ console_print_box_at(CHAR16 *str_arr[], int highlight, if (!console_text_mode) setup_console(1); + if (!co) + return; + co->QueryMode(co, co->Mode->Mode, &cols, &rows); /* last row on screen is unusable without scrolling, so ignore it */ @@ -241,6 +248,9 @@ console_print_box(CHAR16 *str_arr[], int highlight) if (!console_text_mode) setup_console(1); + if (!co) + return; + CopyMem(&SavedConsoleMode, co->Mode, sizeof(SavedConsoleMode)); co->EnableCursor(co, FALSE); co->SetAttribute(co, EFI_LIGHTGRAY | EFI_BACKGROUND_BLUE); @@ -274,6 +284,9 @@ console_select(CHAR16 *title[], CHAR16* selectors[], unsigned int start) if (!console_text_mode) setup_console(1); + if (!co) + return -1; + co->QueryMode(co, co->Mode->Mode, &cols, &rows); for (i = 0; i < selector_lines; i++) { @@ -413,6 +426,9 @@ console_save_and_set_mode(SIMPLE_TEXT_OUTPUT_MODE * SavedMode) return; } + if (!co) + return; + CopyMem(SavedMode, co->Mode, sizeof(SIMPLE_TEXT_OUTPUT_MODE)); co->EnableCursor(co, FALSE); co->SetAttribute(co, EFI_LIGHTGRAY | EFI_BACKGROUND_BLUE); @@ -423,6 +439,9 @@ console_restore_mode(SIMPLE_TEXT_OUTPUT_MODE * SavedMode) { SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut; + if (!co) + return; + co->EnableCursor(co, SavedMode->CursorVisible); co->SetCursorPosition(co, SavedMode->CursorColumn, SavedMode->CursorRow); @@ -441,6 +460,9 @@ console_countdown(CHAR16* title, const CHAR16* message, int timeout) CHAR16 *titles[2]; int wait = 10000000; + if (!co || !ci) + return -1; + console_save_and_set_mode(&SavedMode); titles[0] = title; @@ -495,6 +517,9 @@ console_mode_handle(VOID) UINTN rows = 0, columns = 0; EFI_STATUS efi_status = EFI_SUCCESS; + if (!co) + return; + efi_status = BS->LocateProtocol(&gop_guid, NULL, (void **)&gop); if (EFI_ERROR(efi_status)) { console_error(L"Locate graphic output protocol fail", efi_status); @@ -649,6 +674,9 @@ console_reset(void) if (!console_text_mode) setup_console(1); + if (!co) + return; + co->Reset(co, TRUE); /* set mode 0 - required to be 80x25 */ co->SetMode(co, 0); -- cgit v1.2.3 From 35ca373d20fbeeb80aff2202077d614bc89575c0 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 16 Sep 2021 16:46:55 -0400 Subject: console: add a clear_screen() primitive Several places in e.g. MokManager and our console library use ST->ConOut->ClearScreen directly, without checking for the existence of a console output device. This patch adds function to our console library to do that correctly, instead of using the bug-prone ad hoc implementation everywhere. Signed-off-by: Peter Jones --- MokManager.c | 10 +++++----- include/console.h | 3 +++ lib/console.c | 13 ++++++++++++- 3 files changed, 20 insertions(+), 6 deletions(-) (limited to 'lib') diff --git a/MokManager.c b/MokManager.c index 4b6ee146..08b15d6d 100644 --- a/MokManager.c +++ b/MokManager.c @@ -1005,7 +1005,7 @@ static EFI_STATUS mok_reset_prompt(BOOLEAN MokX) EFI_STATUS efi_status; CHAR16 *prompt[] = { NULL, NULL }; - ST->ConOut->ClearScreen(ST->ConOut); + clear_screen(); if (MokX) prompt[0] = L"Erase all stored keys in MokListX?"; @@ -1468,7 +1468,7 @@ static EFI_STATUS mok_sb_prompt(void *MokSB, UINTN MokSBSize) return EFI_INVALID_PARAMETER; } - ST->ConOut->ClearScreen(ST->ConOut); + clear_screen(); message[0] = L"Change Secure Boot state"; message[1] = NULL; @@ -1583,7 +1583,7 @@ static EFI_STATUS mok_db_prompt(void *MokDB, UINTN MokDBSize) return EFI_INVALID_PARAMETER; } - ST->ConOut->ClearScreen(ST->ConOut); + clear_screen(); message[0] = L"Change DB state"; message[1] = NULL; @@ -1691,7 +1691,7 @@ static EFI_STATUS mok_pw_prompt(void *MokPW, UINTN MokPWSize) return EFI_INVALID_PARAMETER; } - ST->ConOut->ClearScreen(ST->ConOut); + clear_screen(); SetMem(hash, PASSWORD_CRYPT_SIZE, 0); @@ -2008,7 +2008,7 @@ static BOOLEAN verify_pw(BOOLEAN * protected) if (attributes & EFI_VARIABLE_RUNTIME_ACCESS) return TRUE; - ST->ConOut->ClearScreen(ST->ConOut); + clear_screen(); /* Draw the background */ console_save_and_set_mode(&SavedMode); diff --git a/include/console.h b/include/console.h index c832b20e..0c4a5137 100644 --- a/include/console.h +++ b/include/console.h @@ -50,6 +50,9 @@ void console_reset(void); void console_mode_handle(void); +void +clear_screen(void); + #define NOSEL 0x7fffffff typedef struct _EFI_CONSOLE_CONTROL_PROTOCOL EFI_CONSOLE_CONTROL_PROTOCOL; diff --git a/lib/console.c b/lib/console.c index 6b1e4c2f..7be5d543 100644 --- a/lib/console.c +++ b/lib/console.c @@ -580,7 +580,7 @@ console_mode_handle(VOID) efi_status = co->SetMode(co, mode_set); } - co->ClearScreen(co); + clear_screen(); if (EFI_ERROR(efi_status)) { console_error(L"Console set mode fail", efi_status); @@ -683,6 +683,17 @@ console_reset(void) co->ClearScreen(co); } +void +clear_screen(void) +{ + SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut; + + if (!co) + return; + + co->ClearScreen(co); +} + VOID setup_verbosity(VOID) { -- cgit v1.2.3 From d0df9304c7a777557e1925dc9f75406ec00e6179 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 9 Dec 2021 17:21:45 -0500 Subject: Minor coverity fixes - one missing free - one minor deadcode issue - two unchecked allocations - one debug hexdump of a variable we just freed Signed-off-by: Peter Jones --- MokManager.c | 1 + fallback.c | 7 +++++-- include/hexdump.h | 7 ++++++- lib/variables.c | 2 ++ mok.c | 4 +++- 5 files changed, 17 insertions(+), 4 deletions(-) (limited to 'lib') diff --git a/MokManager.c b/MokManager.c index c195cadc..1359af83 100644 --- a/MokManager.c +++ b/MokManager.c @@ -339,6 +339,7 @@ static void show_x509_info(X509 * X509Cert, UINT8 * hash) for (i = 0; i < n; i++) { CatPrint(&serial_string, L"%02x:", hexbuf[i]); } + BN_free(bnser); } if (serial_string.str) diff --git a/fallback.c b/fallback.c index 5da867dd..8e6327be 100644 --- a/fallback.c +++ b/fallback.c @@ -230,8 +230,11 @@ add_boot_option(EFI_DEVICE_PATH *hddp, EFI_DEVICE_PATH *fulldp, StrLen(label)*2 + 2 + DevicePathSize(hddp) + StrLen(arguments) * 2; - CHAR8 *data = AllocateZeroPool(size + 2); - CHAR8 *cursor = data; + CHAR8 *data, *cursor; + cursor = data = AllocateZeroPool(size + 2); + if (!data) + return EFI_OUT_OF_RESOURCES; + *(UINT32 *)cursor = LOAD_OPTION_ACTIVE; cursor += sizeof (UINT32); *(UINT16 *)cursor = DevicePathSize(hddp); diff --git a/include/hexdump.h b/include/hexdump.h index 1a20339b..e8f4fe1a 100644 --- a/include/hexdump.h +++ b/include/hexdump.h @@ -71,7 +71,7 @@ prepare_text(const void *data, size_t size, char *buf, unsigned int position) else buf[offset++] = '.'; } - buf[offset++] = size > 0 ? '|' : 'X'; + buf[offset++] = '|'; buf[offset] = '\0'; } @@ -89,6 +89,11 @@ vhexdumpf(const char *file, int line, const char *func, const CHAR16 *const fmt, if (verbose == 0) return; + if (!data || !size) { + dprint(L"hexdump of a NULL pointer!\n"); + return; + } + while (offset < size) { char hexbuf[49]; char txtbuf[19]; diff --git a/lib/variables.c b/lib/variables.c index 3ec05478..8e63aa8f 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -68,6 +68,8 @@ fill_esl_with_one_signature(const uint8_t *data, const uint32_t data_len, if (out) { sd = AllocateZeroPool(sig_size); + if (!sd) + return EFI_OUT_OF_RESOURCES; if (owner) CopyMem(sd, (void *)owner, sizeof(EFI_GUID)); CopyMem(sd->SignatureData, (void *)data, data_len); diff --git a/mok.c b/mok.c index 52dffc3e..930e52a2 100644 --- a/mok.c +++ b/mok.c @@ -883,7 +883,9 @@ EFI_STATUS import_one_mok_state(struct mok_state_variable *v, } dprint(L"maybe mirroring \"%s\". original data:\n", v->name); - dhexdumpat(v->data, v->data_size, 0); + if (v->data && v->data_size) { + dhexdumpat(v->data, v->data_size, 0); + } ret = maybe_mirror_one_mok_variable(v, ret, only_first); dprint(L"returning %r\n", ret); -- cgit v1.2.3 From 448f096e5c3a139535f162dfbfe8c08c434ac742 Mon Sep 17 00:00:00 2001 From: "Lee, Chun-Yi" Date: Wed, 15 Dec 2021 19:44:58 +0800 Subject: MokManager: removed Locate graphic output protocol fail error message On some platform, like GCP or OVMF which does NOT provide EFI_GRAPHICS_OUTPUT_PROTOCOL when no display device (or the display device be disabled). It causes that the "Error: Locate graphic output protocol fail: (0xE) Not Found." always be showed on console when we enroll MOK through MokManager. The message box blocked the process of enrolling MOK and scared user. The error message is introduced by 55163bc82c517 since 15.2. This patch removed the error message. Signed-off-by: Lee, Chun-Yi --- lib/console.c | 1 - 1 file changed, 1 deletion(-) (limited to 'lib') diff --git a/lib/console.c b/lib/console.c index 7be5d543..cca9f0a2 100644 --- a/lib/console.c +++ b/lib/console.c @@ -522,7 +522,6 @@ console_mode_handle(VOID) efi_status = BS->LocateProtocol(&gop_guid, NULL, (void **)&gop); if (EFI_ERROR(efi_status)) { - console_error(L"Locate graphic output protocol fail", efi_status); return; } -- cgit v1.2.3 From 9af50c136aa2815e1ea2035a494a74cc1613a0da Mon Sep 17 00:00:00 2001 From: Tony Persson Date: Mon, 22 Feb 2021 22:15:28 +0100 Subject: Use ASCII as fallback if Unicode Box Drawing characters fail Many ASRock boards will not render MokManager correctly if the Unicode Box Drawing characters are used. Signed-off-by: Tony Persson --- lib/console.c | 47 +++++++++++++++++++++++++++++++++++++++-------- 1 file changed, 39 insertions(+), 8 deletions(-) (limited to 'lib') diff --git a/lib/console.c b/lib/console.c index cca9f0a2..c256ff23 100644 --- a/lib/console.c +++ b/lib/console.c @@ -122,6 +122,30 @@ console_print_at(UINTN col, UINTN row, const CHAR16 *fmt, ...) return ret; } +static struct { + CHAR16 up_left; + CHAR16 up_right; + CHAR16 down_left; + CHAR16 down_right; + CHAR16 horizontal; + CHAR16 vertical; +} boxdraw[2] = { + { + BOXDRAW_UP_LEFT, + BOXDRAW_UP_RIGHT, + BOXDRAW_DOWN_LEFT, + BOXDRAW_DOWN_RIGHT, + BOXDRAW_HORIZONTAL, + BOXDRAW_VERTICAL + }, { + '+', + '+', + '+', + '+', + '-', + '|' + } +}; void console_print_box_at(CHAR16 *str_arr[], int highlight, @@ -133,6 +157,7 @@ console_print_box_at(CHAR16 *str_arr[], int highlight, SIMPLE_TEXT_OUTPUT_INTERFACE *co = ST->ConOut; UINTN rows, cols; CHAR16 *Line; + bool char_set; if (lines == 0) return; @@ -181,10 +206,16 @@ console_print_box_at(CHAR16 *str_arr[], int highlight, return; } - SetMem16 (Line, size_cols * 2, BOXDRAW_HORIZONTAL); + /* test if boxdraw characters work */ + co->SetCursorPosition(co, start_col, start_row); + Line[0] = boxdraw[0].up_left; + Line[1] = L'\0'; + char_set = co->OutputString(co, Line) == 0 ? 0 : 1; + + SetMem16 (Line, size_cols * 2, boxdraw[char_set].horizontal); - Line[0] = BOXDRAW_DOWN_RIGHT; - Line[size_cols - 1] = BOXDRAW_DOWN_LEFT; + Line[0] = boxdraw[char_set].down_right; + Line[size_cols - 1] = boxdraw[char_set].down_left; Line[size_cols] = L'\0'; co->SetCursorPosition(co, start_col, start_row); co->OutputString(co, Line); @@ -204,8 +235,8 @@ console_print_box_at(CHAR16 *str_arr[], int highlight, int line = i - start; SetMem16 (Line, size_cols*2, L' '); - Line[0] = BOXDRAW_VERTICAL; - Line[size_cols - 1] = BOXDRAW_VERTICAL; + Line[0] = boxdraw[char_set].vertical; + Line[size_cols - 1] = boxdraw[char_set].vertical; Line[size_cols] = L'\0'; if (line >= 0 && line < lines) { CHAR16 *s = str_arr[line]; @@ -227,9 +258,9 @@ console_print_box_at(CHAR16 *str_arr[], int highlight, EFI_BACKGROUND_BLUE); } - SetMem16 (Line, size_cols * 2, BOXDRAW_HORIZONTAL); - Line[0] = BOXDRAW_UP_RIGHT; - Line[size_cols - 1] = BOXDRAW_UP_LEFT; + SetMem16 (Line, size_cols * 2, boxdraw[char_set].horizontal); + Line[0] = boxdraw[char_set].up_right; + Line[size_cols - 1] = boxdraw[char_set].up_left; Line[size_cols] = L'\0'; co->SetCursorPosition(co, start_col, i); co->OutputString(co, Line); -- cgit v1.2.3 From 803dc5c16e276c26f8400b469370f2a2ca39d7f3 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Wed, 27 Apr 2022 17:09:01 -0400 Subject: shim: use SHIM_DEVEL_VERBOSE when built in devel mode This makes SHIM_VERBOSE / SHIM_DEVEL_VERBOSE work the same way as SHIM_DEBUG / SHIM_DEVEL_DEBUG when shim is built with ENABLE_SHIM_DEVEL set. Signed-off-by: Peter Jones --- BUILDING | 3 ++- fallback.c | 4 ++-- lib/Makefile | 4 ++++ lib/console.c | 2 +- shim.c | 11 ++--------- shim.h | 10 ++++++++++ 6 files changed, 21 insertions(+), 13 deletions(-) (limited to 'lib') diff --git a/BUILDING b/BUILDING index 2da9b5f0..3b2e85d3 100644 --- a/BUILDING +++ b/BUILDING @@ -35,7 +35,8 @@ Variables you could set to customize the build: If this is set, we look for SHIM_DEVEL_DEBUG instead of SHIM_DEBUG in our debugger delay hook, thus meaning you can have it pause for a debugger only on the development branch and not the OS you need to boot - to scp in a new development build. + to scp in a new development build. Likewise, we look for + SHIM_DEVEL_VERBOSE rather than SHIM_VERBOSE. - DISABLE_EBS_PROTECTION On systems where a second stage bootloader is not used, and the Linux Kernel is embedded in the same EFI image as shim and booted directly diff --git a/fallback.c b/fallback.c index 8e6327be..da4b25cc 100644 --- a/fallback.c +++ b/fallback.c @@ -24,7 +24,7 @@ get_fallback_verbose(void) if (state != -1) return state; - efi_status = get_variable(L"FALLBACK_VERBOSE", + efi_status = get_variable(FALLBACK_VERBOSE_VAR_NAME, &data, &dataSize, SHIM_LOCK_GUID); if (EFI_ERROR(efi_status)) { state = 0; @@ -1130,7 +1130,7 @@ debug_hook(void) register volatile int x = 0; extern char _etext, _edata; - efi_status = get_variable(L"SHIM_DEBUG", &data, &dataSize, + efi_status = get_variable(DEBUG_VAR_NAME, &data, &dataSize, SHIM_LOCK_GUID); if (EFI_ERROR(efi_status)) { return; diff --git a/lib/Makefile b/lib/Makefile index a4a4855b..f81c5c9b 100644 --- a/lib/Makefile +++ b/lib/Makefile @@ -41,6 +41,10 @@ CFLAGS = $(FEATUREFLAGS) \ $(INCLUDES) \ $(DEFINES) +ifneq ($(origin ENABLE_SHIM_DEVEL),undefined) +CFLAGS += -DENABLE_SHIM_DEVEL +endif + lib.a: $(LIBFILES) $(AR) rcs lib.a $(LIBFILES) diff --git a/lib/console.c b/lib/console.c index c256ff23..6bbb8a7c 100644 --- a/lib/console.c +++ b/lib/console.c @@ -732,7 +732,7 @@ setup_verbosity(VOID) UINTN verbose_check_size; verbose_check_size = sizeof(verbose); - efi_status = get_variable(L"SHIM_VERBOSE", &verbose_check_ptr, + efi_status = get_variable(VERBOSE_VAR_NAME, &verbose_check_ptr, &verbose_check_size, SHIM_LOCK_GUID); if (!EFI_ERROR(efi_status)) { verbose = *(__typeof__(verbose) *)verbose_check_ptr; diff --git a/shim.c b/shim.c index 6d6b1e52..f60125d2 100644 --- a/shim.c +++ b/shim.c @@ -1450,17 +1450,10 @@ debug_hook(void) register volatile UINTN x = 0; extern char _text, _data; - const CHAR16 * const debug_var_name = -#ifdef ENABLE_SHIM_DEVEL - L"SHIM_DEVEL_DEBUG"; -#else - L"SHIM_DEBUG"; -#endif - if (x) return; - efi_status = get_variable(debug_var_name, &data, &dataSize, + efi_status = get_variable(DEBUG_VAR_NAME, &data, &dataSize, SHIM_LOCK_GUID); if (EFI_ERROR(efi_status)) { return; @@ -1474,7 +1467,7 @@ debug_hook(void) console_print(L"Pausing for debugger attachment.\n"); console_print(L"To disable this, remove the EFI variable %s-%g .\n", - debug_var_name, &SHIM_LOCK_GUID); + DEBUG_VAR_NAME, &SHIM_LOCK_GUID); x = 1; while (x++) { /* Make this so it can't /totally/ DoS us. */ diff --git a/shim.h b/shim.h index 69442da3..db264cb7 100644 --- a/shim.h +++ b/shim.h @@ -284,6 +284,16 @@ verify_buffer (char *data, int datasize, #define LogError(fmt, ...) #endif +#ifdef ENABLE_SHIM_DEVEL +#define FALLBACK_VERBOSE_VAR_NAME L"FALLBACK_DEVEL_VERBOSE" +#define VERBOSE_VAR_NAME L"SHIM_DEVEL_VERBOSE" +#define DEBUG_VAR_NAME L"SHIM_DEVEL_DEBUG" +#else +#define FALLBACK_VERBOSE_VAR_NAME L"FALLBACK_VERBOSE" +#define VERBOSE_VAR_NAME L"SHIM_VERBOSE" +#define DEBUG_VAR_NAME L"SHIM_DEBUG" +#endif + char *translate_slashes(char *out, const char *str); #endif /* SHIM_H_ */ -- cgit v1.2.3 From 226fee25ffcbd29988399ba080c7706eb1d52251 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Thu, 2 Dec 2021 18:29:50 -0500 Subject: PE Loader: support and require NX This adds support in our PE loader for NX support utilizing the EFI_MEMORY_ATTRIBUTE protocol. Specifically, it changes the loader such that: - binaries without the EFI_IMAGE_DLLCHARACTERISTICS_NX_COMPAT flag set in the Optional Header are rejected as EFI_UNSUPPORTED - binaries with non-discardable sections that have both the EFI_SCN_MEM_WRITE and EFI_SCN_MEM_EXECUTE flags set are rejected as EFI_UNSUPPORTED - if the EFI_MEMORY_ATTRIBUTE protocol is installed, then: - sections without the EFI_SCN_MEM_READ flag set will be marked with EFI_MEMORY_RP - sections without the EFI_SCN_MEM_WRITE flag set will be marked with EFI_MEMORY_RO - sections without the EFI_SCN_MEM_EXECUTE flag set will be marked with EFI_MEMORY_XP Signed-off-by: Peter Jones --- include/guid.h | 2 +- lib/guid.c | 2 +- pe.c | 203 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ shim.h | 4 ++ 4 files changed, 209 insertions(+), 2 deletions(-) (limited to 'lib') diff --git a/include/guid.h b/include/guid.h index 07a19a91..d9910ff1 100644 --- a/include/guid.h +++ b/include/guid.h @@ -33,8 +33,8 @@ extern EFI_GUID EFI_SECURE_BOOT_DB_GUID; extern EFI_GUID EFI_SIMPLE_FILE_SYSTEM_GUID; extern EFI_GUID SECURITY_PROTOCOL_GUID; extern EFI_GUID SECURITY2_PROTOCOL_GUID; +extern EFI_GUID EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID; extern EFI_GUID SHIM_LOCK_GUID; - extern EFI_GUID MOK_VARIABLE_STORE; #endif /* SHIM_GUID_H */ diff --git a/lib/guid.c b/lib/guid.c index 143e0bbd..e100c92e 100644 --- a/lib/guid.c +++ b/lib/guid.c @@ -32,6 +32,6 @@ EFI_GUID EFI_SECURE_BOOT_DB_GUID = { 0xd719b2cb, 0x3d3a, 0x4596, { 0xa3, 0xbc, EFI_GUID EFI_SIMPLE_FILE_SYSTEM_GUID = SIMPLE_FILE_SYSTEM_PROTOCOL; EFI_GUID SECURITY_PROTOCOL_GUID = { 0xA46423E3, 0x4617, 0x49f1, {0xB9, 0xFF, 0xD1, 0xBF, 0xA9, 0x11, 0x58, 0x39 } }; EFI_GUID SECURITY2_PROTOCOL_GUID = { 0x94ab2f58, 0x1438, 0x4ef1, {0x91, 0x52, 0x18, 0x94, 0x1a, 0x3a, 0x0e, 0x68 } }; - +EFI_GUID EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID = { 0xf4560cf6, 0x40ec, 0x4b4a, {0xa1, 0x92, 0xbf, 0x1d, 0x57, 0xd0, 0xb1, 0x89} }; EFI_GUID SHIM_LOCK_GUID = {0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23 } }; EFI_GUID MOK_VARIABLE_STORE = {0xc451ed2b, 0x9694, 0x45d3, {0xba, 0xba, 0xed, 0x9f, 0x89, 0x88, 0xa3, 0x89} }; diff --git a/pe.c b/pe.c index 535d463a..9fa6fffd 100644 --- a/pe.c +++ b/pe.c @@ -696,6 +696,7 @@ read_header(void *data, unsigned int datasize, EFI_IMAGE_OPTIONAL_HEADER_UNION *PEHdr = data; unsigned long HeaderWithoutDataDir, SectionHeaderOffset, OptHeaderSize; unsigned long FileAlignment = 0; + UINT16 DllFlags; if (datasize < sizeof (PEHdr->Pe32)) { perror(L"Invalid image\n"); @@ -790,13 +791,20 @@ read_header(void *data, unsigned int datasize, context->EntryPoint = PEHdr->Pe32Plus.OptionalHeader.AddressOfEntryPoint; context->RelocDir = &PEHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC]; context->SecDir = &PEHdr->Pe32Plus.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_SECURITY]; + DllFlags = PEHdr->Pe32Plus.OptionalHeader.DllCharacteristics; } else { context->ImageAddress = PEHdr->Pe32.OptionalHeader.ImageBase; context->EntryPoint = PEHdr->Pe32.OptionalHeader.AddressOfEntryPoint; context->RelocDir = &PEHdr->Pe32.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_BASERELOC]; context->SecDir = &PEHdr->Pe32.OptionalHeader.DataDirectory[EFI_IMAGE_DIRECTORY_ENTRY_SECURITY]; + DllFlags = PEHdr->Pe32.OptionalHeader.DllCharacteristics; } + if (!(DllFlags & EFI_IMAGE_DLLCHARACTERISTICS_NX_COMPAT)) { + perror(L"Image does not support NX\n"); + return EFI_UNSUPPORTED; + } + context->FirstSection = (EFI_IMAGE_SECTION_HEADER *)((char *)PEHdr + PEHdr->Pe32.FileHeader.SizeOfOptionalHeader + sizeof(UINT32) + sizeof(EFI_IMAGE_FILE_HEADER)); if (context->ImageSize < context->SizeOfHeaders) { @@ -878,6 +886,139 @@ err: return efi_status; } +static inline uint64_t +shim_mem_attrs_to_uefi_mem_attrs (uint64_t attrs) +{ + uint64_t ret = EFI_MEMORY_RP | + EFI_MEMORY_RO | + EFI_MEMORY_XP; + + if (attrs & MEM_ATTR_R) + ret &= ~EFI_MEMORY_RP; + + if (attrs & MEM_ATTR_W) + ret &= ~EFI_MEMORY_RO; + + if (attrs & MEM_ATTR_X) + ret &= ~EFI_MEMORY_XP; + + return ret; +} + +static inline uint64_t +uefi_mem_attrs_to_shim_mem_attrs (uint64_t attrs) +{ + uint64_t ret = MEM_ATTR_R | + MEM_ATTR_W | + MEM_ATTR_X; + + if (attrs & EFI_MEMORY_RP) + ret &= ~MEM_ATTR_R; + + if (attrs & EFI_MEMORY_RO) + ret &= ~MEM_ATTR_W; + + if (attrs & EFI_MEMORY_XP) + ret &= ~MEM_ATTR_X; + + return ret; +} + +static EFI_STATUS +get_mem_attrs (uintptr_t addr, size_t size, uint64_t *attrs) +{ + EFI_MEMORY_ATTRIBUTE_PROTOCOL *proto = NULL; + EFI_PHYSICAL_ADDRESS physaddr = addr; + EFI_STATUS efi_status; + + efi_status = LibLocateProtocol(&EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID, + (VOID **)&proto); + if (EFI_ERROR(efi_status) || !proto) + return efi_status; + + if (physaddr & 0xfff || size & 0xfff || size == 0 || attrs == NULL) { + dprint(L"%a called on 0x%llx-0x%llx and attrs 0x%llx\n", + __func__, (unsigned long long)physaddr, + (unsigned long long)(physaddr+size-1), + attrs); + return EFI_SUCCESS; + } + + efi_status = proto->GetMemoryAttributes(proto, physaddr, size, attrs); + *attrs = uefi_mem_attrs_to_shim_mem_attrs (*attrs); + + return efi_status; +} + +static EFI_STATUS +update_mem_attrs(uintptr_t addr, uint64_t size, + uint64_t set_attrs, uint64_t clear_attrs) +{ + EFI_MEMORY_ATTRIBUTE_PROTOCOL *proto = NULL; + EFI_PHYSICAL_ADDRESS physaddr = addr; + EFI_STATUS efi_status, ret; + uint64_t before = 0, after = 0, uefi_set_attrs, uefi_clear_attrs; + + efi_status = LibLocateProtocol(&EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID, + (VOID **)&proto); + if (EFI_ERROR(efi_status) || !proto) + return efi_status; + + efi_status = get_mem_attrs (addr, size, &before); + if (EFI_ERROR(efi_status)) + dprint(L"get_mem_attrs(0x%llx, 0x%llx, 0x%llx) -> 0x%lx\n", + (unsigned long long)addr, (unsigned long long)size, + &before, efi_status); + + if (physaddr & 0xfff || size & 0xfff || size == 0) { + dprint(L"%a called on 0x%llx-0x%llx (size 0x%llx) +%a%a%a -%a%a%a\n", + __func__, (unsigned long long)physaddr, + (unsigned long long)(physaddr + size - 1), + (unsigned long long)size, + (set_attrs & MEM_ATTR_R) ? "r" : "", + (set_attrs & MEM_ATTR_W) ? "w" : "", + (set_attrs & MEM_ATTR_X) ? "x" : "", + (clear_attrs & MEM_ATTR_R) ? "r" : "", + (clear_attrs & MEM_ATTR_W) ? "w" : "", + (clear_attrs & MEM_ATTR_X) ? "x" : ""); + return 0; + } + + uefi_set_attrs = shim_mem_attrs_to_uefi_mem_attrs (set_attrs); + dprint("translating set_attrs from 0x%lx to 0x%lx\n", set_attrs, uefi_set_attrs); + uefi_clear_attrs = shim_mem_attrs_to_uefi_mem_attrs (clear_attrs); + dprint("translating clear_attrs from 0x%lx to 0x%lx\n", clear_attrs, uefi_clear_attrs); + efi_status = EFI_SUCCESS; + if (uefi_set_attrs) + efi_status = proto->SetMemoryAttributes(proto, physaddr, size, uefi_set_attrs); + if (!EFI_ERROR(efi_status) && uefi_clear_attrs) + efi_status = proto->ClearMemoryAttributes(proto, physaddr, size, uefi_clear_attrs); + ret = efi_status; + + efi_status = get_mem_attrs (addr, size, &after); + if (EFI_ERROR(efi_status)) + dprint(L"get_mem_attrs(0x%llx, %llu, 0x%llx) -> 0x%lx\n", + (unsigned long long)addr, (unsigned long long)size, + &after, efi_status); + + dprint(L"set +%a%a%a -%a%a%a on 0x%llx-0x%llx before:%c%c%c after:%c%c%c\n", + (set_attrs & MEM_ATTR_R) ? "r" : "", + (set_attrs & MEM_ATTR_W) ? "w" : "", + (set_attrs & MEM_ATTR_X) ? "x" : "", + (clear_attrs & MEM_ATTR_R) ? "r" : "", + (clear_attrs & MEM_ATTR_W) ? "w" : "", + (clear_attrs & MEM_ATTR_X) ? "x" : "", + (unsigned long long)addr, (unsigned long long)(addr + size - 1), + (before & MEM_ATTR_R) ? 'r' : '-', + (before & MEM_ATTR_W) ? 'w' : '-', + (before & MEM_ATTR_X) ? 'x' : '-', + (after & MEM_ATTR_R) ? 'r' : '-', + (after & MEM_ATTR_W) ? 'w' : '-', + (after & MEM_ATTR_X) ? 'x' : '-'); + + return ret; +} + EFI_STATUS verify_image(void *data, unsigned int datasize, EFI_LOADED_IMAGE *li, PE_COFF_LOADER_IMAGE_CONTEXT *context) @@ -1013,6 +1154,11 @@ handle_image (void *data, unsigned int datasize, } buffer = (void *)ALIGN_VALUE((unsigned long)*alloc_address, alignment); + dprint(L"Loading 0x%llx bytes at 0x%llx\n", + (unsigned long long)context.ImageSize, + (unsigned long long)(uintptr_t)buffer); + update_mem_attrs((uintptr_t)buffer, alloc_size, MEM_ATTR_R|MEM_ATTR_W, + MEM_ATTR_X); CopyMem(buffer, data, context.SizeOfHeaders); @@ -1049,6 +1195,19 @@ handle_image (void *data, unsigned int datasize, !Section->Misc.VirtualSize) continue; + /* + * Skip sections that aren't marked readable. + */ + if (!(Section->Characteristics & EFI_IMAGE_SCN_MEM_READ)) + continue; + + if (!(Section->Characteristics & EFI_IMAGE_SCN_MEM_DISCARDABLE) && + (Section->Characteristics & EFI_IMAGE_SCN_MEM_WRITE) && + (Section->Characteristics & EFI_IMAGE_SCN_MEM_EXECUTE)) { + perror(L"Section %d is writable and executable\n", i); + return EFI_UNSUPPORTED; + } + base = ImageAddress (buffer, context.ImageSize, Section->VirtualAddress); end = ImageAddress (buffer, context.ImageSize, @@ -1159,6 +1318,50 @@ handle_image (void *data, unsigned int datasize, } } + /* + * Now set the page permissions appropriately. + */ + Section = context.FirstSection; + for (i = 0; i < context.NumberOfSections; i++, Section++) { + uint64_t set_attrs = MEM_ATTR_R; + uint64_t clear_attrs = MEM_ATTR_W|MEM_ATTR_X; + uintptr_t addr; + uint64_t length; + + /* + * Skip discardable sections with zero size + */ + if ((Section->Characteristics & EFI_IMAGE_SCN_MEM_DISCARDABLE) && + !Section->Misc.VirtualSize) + continue; + + /* + * Skip sections that aren't marked readable. + */ + if (!(Section->Characteristics & EFI_IMAGE_SCN_MEM_READ)) + continue; + + base = ImageAddress (buffer, context.ImageSize, + Section->VirtualAddress); + end = ImageAddress (buffer, context.ImageSize, + Section->VirtualAddress + + Section->Misc.VirtualSize - 1); + + addr = (uintptr_t)base; + length = (uintptr_t)end - (uintptr_t)base + 1; + + if (Section->Characteristics & EFI_IMAGE_SCN_MEM_WRITE) { + set_attrs |= MEM_ATTR_W; + clear_attrs &= ~MEM_ATTR_W; + } + if (Section->Characteristics & EFI_IMAGE_SCN_MEM_EXECUTE) { + set_attrs |= MEM_ATTR_X; + clear_attrs &= ~MEM_ATTR_X; + } + update_mem_attrs(addr, length, set_attrs, clear_attrs); + } + + /* * grub needs to know its location and size in memory, so fix up * the loaded image protocol values diff --git a/shim.h b/shim.h index 703c1145..dc3cda73 100644 --- a/shim.h +++ b/shim.h @@ -195,6 +195,10 @@ #include "Cryptlib/Include/OpenSslSupport.h" #endif +#define MEM_ATTR_R 4 +#define MEM_ATTR_W 2 +#define MEM_ATTR_X 1 + INTERFACE_DECL(_SHIM_LOCK); typedef -- cgit v1.2.3 From 4fd484e4c29364b4fdf4d043556fa0a210c5fdfc Mon Sep 17 00:00:00 2001 From: Lu Ken Date: Sun, 22 May 2022 16:02:20 +0800 Subject: Enable TDX measurement to RTMR register Intel Trust Domain Extensions (Intel TDX) extends Virtual Machine Extensions (VMX) and Multi-Key Total Memory Encryption (MK-TME) with a new kind of virtual machine guest called a Trust Domain(TD)[1]. A TD runs in a CPU mode that is designed to protect the confidentiality of its memory contents and its CPU state from any other software, including the hosting Virtual Machine Monitor (VMM). Trust Domain Virtual Firmware (TDVF) is required to provide Intel TDX implementation and service for EFI_CC_MEASUREMENT_PROTOCOL[2]. The bugzilla for TDVF is at https://bugzilla.tianocore.org/show_bug.cgi?id=3625. To support CC measurement/attestation with Intel TDX technology, these 4 RTMR registers will be extended by TDX service like TPM/TPM2 PCR: - RTMR[0] for TDVF configuration - RTMR[1] for the TD OS loader and kernel - RTMR[2] for the OS application - RTMR[3] reserved for special usage only Add a TDX Implementation for CC Measurement protocol along with TPM/TPM2 protocol. References: [1] https://software.intel.com/content/dam/develop/external/us/en/documents/tdx-whitepaper-v4.pdf [2] https://software.intel.com/content/dam/develop/external/us/en/documents/tdx-virtual-firmware-design-guide-rev-1.pdf [3] https://software.intel.com/content/dam/develop/external/us/en/documents/intel-tdx-guest-hypervisor-communication-interface-1.0-344426-002.pdf Signed-off-by: Lu Ken [rharwood: style pass on code and commit message] Signed-off-by: Robbie Harwood --- include/cc.h | 85 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ include/guid.h | 1 + lib/guid.c | 1 + shim.h | 1 + tpm.c | 48 +++++++++++++++++++++++++++++++++ 5 files changed, 136 insertions(+) create mode 100644 include/cc.h (limited to 'lib') diff --git a/include/cc.h b/include/cc.h new file mode 100644 index 00000000..8b127208 --- /dev/null +++ b/include/cc.h @@ -0,0 +1,85 @@ +// SPDX-License-Identifier: BSD-2-Clause-Patent + +#ifndef SHIM_CC_H +#define SHIM_CC_H + +typedef struct { + uint8_t Major; + uint8_t Minor; +} EFI_CC_VERSION; + +#define EFI_CC_TYPE_NONE 0 +#define EFI_CC_TYPE_SEV 1 +#define EFI_CC_TYPE_TDX 2 + +typedef struct { + uint8_t Type; + uint8_t SubType; +} EFI_CC_TYPE; + +typedef uint32_t EFI_CC_EVENT_LOG_BITMAP; +typedef uint32_t EFI_CC_EVENT_LOG_FORMAT; +typedef uint32_t EFI_CC_EVENT_ALGORITHM_BITMAP; +typedef uint32_t EFI_CC_MR_INDEX; + +#define TDX_MR_INDEX_MRTD 0 +#define TDX_MR_INDEX_RTMR0 1 +#define TDX_MR_INDEX_RTMR1 2 +#define TDX_MR_INDEX_RTMR2 3 +#define TDX_MR_INDEX_RTMR3 4 + +#define EFI_CC_EVENT_LOG_FORMAT_TCG_2 0x00000002 +#define EFI_CC_BOOT_HASH_ALG_SHA384 0x00000004 +#define EFI_CC_EVENT_HEADER_VERSION 1 + +typedef struct tdEFI_CC_EVENT_HEADER { + uint32_t HeaderSize; + uint16_t HeaderVersion; + EFI_CC_MR_INDEX MrIndex; + uint32_t EventType; +} __attribute__((packed)) EFI_CC_EVENT_HEADER; + +typedef struct tdEFI_CC_EVENT { + uint32_t Size; + EFI_CC_EVENT_HEADER Header; + uint8_t Event[1]; +} __attribute__((packed)) EFI_CC_EVENT; + +typedef struct tdEFI_CC_BOOT_SERVICE_CAPABILITY { + uint8_t Size; + EFI_CC_VERSION StructureVersion; + EFI_CC_VERSION ProtocolVersion; + EFI_CC_EVENT_ALGORITHM_BITMAP HashAlgorithmBitmap; + EFI_CC_EVENT_LOG_BITMAP SupportedEventLogs; + EFI_CC_TYPE CcType; +} EFI_CC_BOOT_SERVICE_CAPABILITY; + +struct efi_cc_protocol +{ + EFI_STATUS (EFIAPI *get_capability) ( + struct efi_cc_protocol *this, + EFI_CC_BOOT_SERVICE_CAPABILITY *ProtocolCapability); + EFI_STATUS (EFIAPI *get_event_log) ( + struct efi_cc_protocol *this, + EFI_CC_EVENT_LOG_FORMAT EventLogFormat, + EFI_PHYSICAL_ADDRESS *EventLogLocation, + EFI_PHYSICAL_ADDRESS *EventLogLastEntry, + BOOLEAN *EventLogTruncated); + EFI_STATUS (EFIAPI *hash_log_extend_event) ( + struct efi_cc_protocol *this, + uint64_t Flags, + EFI_PHYSICAL_ADDRESS DataToHash, + uint64_t DataToHashLen, + EFI_CC_EVENT *EfiCcEvent); + EFI_STATUS (EFIAPI *map_pcr_to_mr_index) ( + struct efi_cc_protocol *this, + uint32_t PcrIndex, + EFI_CC_MR_INDEX *MrIndex); +}; + +typedef struct efi_cc_protocol efi_cc_protocol_t; + +#define EFI_CC_FLAG_PE_COFF_IMAGE 0x0000000000000010 + +#endif /* SHIM_CC_H */ +// vim:fenc=utf-8:tw=75 diff --git a/include/guid.h b/include/guid.h index d9910ff1..dad63f0f 100644 --- a/include/guid.h +++ b/include/guid.h @@ -29,6 +29,7 @@ extern EFI_GUID EFI_IP6_CONFIG_GUID; extern EFI_GUID EFI_LOADED_IMAGE_GUID; extern EFI_GUID EFI_TPM_GUID; extern EFI_GUID EFI_TPM2_GUID; +extern EFI_GUID EFI_CC_MEASUREMENT_PROTOCOL_GUID; extern EFI_GUID EFI_SECURE_BOOT_DB_GUID; extern EFI_GUID EFI_SIMPLE_FILE_SYSTEM_GUID; extern EFI_GUID SECURITY_PROTOCOL_GUID; diff --git a/lib/guid.c b/lib/guid.c index e100c92e..904629eb 100644 --- a/lib/guid.c +++ b/lib/guid.c @@ -28,6 +28,7 @@ EFI_GUID EFI_IP6_CONFIG_GUID = { 0x937fe521, 0x95ae, 0x4d1a, {0x89, 0x29, 0x48, EFI_GUID EFI_LOADED_IMAGE_GUID = EFI_LOADED_IMAGE_PROTOCOL_GUID; EFI_GUID EFI_TPM_GUID = { 0xf541796d, 0xa62e, 0x4954, {0xa7, 0x75, 0x95, 0x84, 0xf6, 0x1b, 0x9c, 0xdd } }; EFI_GUID EFI_TPM2_GUID = { 0x607f766c, 0x7455, 0x42be, {0x93, 0x0b, 0xe4, 0xd7, 0x6d, 0xb2, 0x72, 0x0f } }; +EFI_GUID EFI_CC_MEASUREMENT_PROTOCOL_GUID = { 0x96751a3d, 0x72f4, 0x41a6, {0xa7, 0x94, 0xed, 0x5d, 0x0e, 0x67, 0xae, 0x6b } }; EFI_GUID EFI_SECURE_BOOT_DB_GUID = { 0xd719b2cb, 0x3d3a, 0x4596, { 0xa3, 0xbc, 0xda, 0xd0, 0x0e, 0x67, 0x65, 0x6f } }; EFI_GUID EFI_SIMPLE_FILE_SYSTEM_GUID = SIMPLE_FILE_SYSTEM_PROTOCOL; EFI_GUID SECURITY_PROTOCOL_GUID = { 0xA46423E3, 0x4617, 0x49f1, {0xB9, 0xFF, 0xD1, 0xBF, 0xA9, 0x11, 0x58, 0x39 } }; diff --git a/shim.h b/shim.h index 7e9d10eb..14824c67 100644 --- a/shim.h +++ b/shim.h @@ -186,6 +186,7 @@ #include "include/simple_file.h" #include "include/str.h" #include "include/tpm.h" +#include "include/cc.h" #include "include/ucs2.h" #include "include/variables.h" #include "include/hexdump.h" diff --git a/tpm.c b/tpm.c index 41f36651..388f8d12 100644 --- a/tpm.c +++ b/tpm.c @@ -108,6 +108,45 @@ static EFI_STATUS tpm_locate_protocol(efi_tpm_protocol_t **tpm, return EFI_NOT_FOUND; } +static EFI_STATUS cc_log_event_raw(EFI_PHYSICAL_ADDRESS buf, UINTN size, + UINT8 pcr, const CHAR8 *log, UINTN logsize, + UINT32 type, BOOLEAN is_pe_image) +{ + EFI_STATUS efi_status; + EFI_CC_EVENT *event; + efi_cc_protocol_t *cc; + EFI_CC_MR_INDEX mr; + uint64_t flags = is_pe_image ? EFI_CC_FLAG_PE_COFF_IMAGE : 0; + + efi_status = LibLocateProtocol(&EFI_CC_MEASUREMENT_PROTOCOL_GUID, + (VOID **)&cc); + if (EFI_ERROR(efi_status) || !cc) + return EFI_SUCCESS; + + efi_status = cc->map_pcr_to_mr_index(cc, pcr, &mr); + if (EFI_ERROR(efi_status)) + return EFI_NOT_FOUND; + + UINTN event_size = sizeof(*event) - sizeof(event->Event) + logsize; + + event = AllocatePool(event_size); + if (!event) { + perror(L"Unable to allocate event structure\n"); + return EFI_OUT_OF_RESOURCES; + } + + event->Header.HeaderSize = sizeof(EFI_CC_EVENT_HEADER); + event->Header.HeaderVersion = EFI_CC_EVENT_HEADER_VERSION; + event->Header.MrIndex = mr; + event->Header.EventType = type; + event->Size = event_size; + CopyMem(event->Event, (VOID *)log, logsize); + efi_status = cc->hash_log_extend_event(cc, flags, buf, (UINT64)size, + event); + FreePool(event); + return efi_status; +} + static EFI_STATUS tpm_log_event_raw(EFI_PHYSICAL_ADDRESS buf, UINTN size, UINT8 pcr, const CHAR8 *log, UINTN logsize, UINT32 type, CHAR8 *hash) @@ -118,6 +157,15 @@ static EFI_STATUS tpm_log_event_raw(EFI_PHYSICAL_ADDRESS buf, UINTN size, BOOLEAN old_caps; EFI_TCG2_BOOT_SERVICE_CAPABILITY caps; + /* CC guest like TDX or SEV will measure the buffer and log the event, + extend the result into a specific CC MR like TCG's PCR. It could + coexists with TCG's TPM 1.2 and TPM 2. + */ + efi_status = cc_log_event_raw(buf, size, pcr, log, logsize, type, + (hash != NULL)); + if (EFI_ERROR(efi_status)) + return efi_status; + efi_status = tpm_locate_protocol(&tpm, &tpm2, &old_caps, &caps); if (EFI_ERROR(efi_status)) { #ifdef REQUIRE_TPM -- cgit v1.2.3 From f7a4338f1b5ef03dca83ce44075e9d6e5897e037 Mon Sep 17 00:00:00 2001 From: Kamil Aronowski Date: Mon, 8 May 2023 09:28:24 +0200 Subject: Skip testing msleep() In preparation for renaming msleep() to usleep(), in some cases tests were failing due to a mismatch between our declaration of the usleep() function and what is being provided by unistd.h. This change simply makes our function declared only when not in a unit test environment. Signed-off-by: Kamil Aronowski --- include/console.h | 2 ++ lib/console.c | 2 ++ 2 files changed, 4 insertions(+) (limited to 'lib') diff --git a/include/console.h b/include/console.h index 0c4a5137..2a29c2dc 100644 --- a/include/console.h +++ b/include/console.h @@ -122,7 +122,9 @@ extern EFI_STATUS EFIAPI vdprint_(const CHAR16 *fmt, const char *file, int line, extern EFI_STATUS print_crypto_errors(EFI_STATUS rc, char *file, const char *func, int line); #define crypterr(rc) print_crypto_errors((rc), __FILE__, __func__, __LINE__) +#ifndef SHIM_UNIT_TEST extern VOID msleep(unsigned long msecs); +#endif /* This is used in various things to determine if we should print to the * console */ diff --git a/lib/console.c b/lib/console.c index 6bbb8a7c..c7ca3bc2 100644 --- a/lib/console.c +++ b/lib/console.c @@ -743,11 +743,13 @@ setup_verbosity(VOID) setup_console(-1); } +#ifndef SHIM_UNIT_TEST VOID msleep(unsigned long msecs) { BS->Stall(msecs); } +#endif /* This is used in various things to determine if we should print to the * console */ -- cgit v1.2.3 From 549d34691d68518e55c2edd6e759b19de7f8ddef Mon Sep 17 00:00:00 2001 From: Kamil Aronowski Date: Wed, 12 Apr 2023 18:50:12 +0200 Subject: Rename 'msecs' to 'usecs' to avoid potential confusion The function msleep uses gBS->Stall which waits for a specified number of microseconds. Reference: https://edk2-docs.gitbook.io/edk-ii-uefi-driver-writer-s-guide/5_uefi_services/51_services_that_uefi_drivers_commonly_use/517_stall This reference even mentions an example sleeping for 10 microseconds: // Wait 10 uS. Notice the letter 'u'. Therefore it's a good idea to call the function 'usleep' rather than 'msleep', so no one confuses it with milliseconds, and to change the argument name to match as well. Signed-off-by: Kamil Aronowski --- fallback.c | 8 ++++---- include/asm.h | 4 ++-- include/console.h | 2 +- lib/console.c | 4 ++-- model.c | 2 +- replacements.c | 6 +++--- shim.c | 12 ++++++------ 7 files changed, 19 insertions(+), 19 deletions(-) (limited to 'lib') diff --git a/fallback.c b/fallback.c index da4b25cc..ad70ccf1 100644 --- a/fallback.c +++ b/fallback.c @@ -1013,7 +1013,7 @@ try_start_first_option(EFI_HANDLE parent_image_handle) console_print(L"Verbose enabled, sleeping for %d mseconds... " L"Press the Pause key now to hold for longer.\n", fallback_verbose_wait); - msleep(fallback_verbose_wait); + usleep(fallback_verbose_wait); } if (!first_new_option) { @@ -1036,7 +1036,7 @@ try_start_first_option(EFI_HANDLE parent_image_handle) } console_print(L"\n"); - msleep(500000000); + usleep(500000000); return efi_status; } @@ -1051,7 +1051,7 @@ try_start_first_option(EFI_HANDLE parent_image_handle) efi_status = BS->StartImage(image_handle, NULL, NULL); if (EFI_ERROR(efi_status)) { console_print(L"StartImage failed: %r\n", efi_status); - msleep(500000000); + usleep(500000000); } return efi_status; } @@ -1218,7 +1218,7 @@ reset: console_print(L"Verbose enabled, sleeping for %d mseconds... " L"Press the Pause key now to hold for longer.\n", fallback_verbose_wait); - msleep(fallback_verbose_wait); + usleep(fallback_verbose_wait); } RT->ResetSystem(EfiResetCold, EFI_SUCCESS, 0, NULL); diff --git a/include/asm.h b/include/asm.h index 03b06557..f5118b23 100644 --- a/include/asm.h +++ b/include/asm.h @@ -40,11 +40,11 @@ static inline void wait_for_debug(void) { uint64_t a, b; int x; - extern void msleep(unsigned long msecs); + extern void usleep(unsigned long usecs); a = read_counter(); for (x = 0; x < 1000; x++) { - msleep(1000); + usleep(1000); b = read_counter(); if (a != b) break; diff --git a/include/console.h b/include/console.h index 2a29c2dc..8eb4b47f 100644 --- a/include/console.h +++ b/include/console.h @@ -123,7 +123,7 @@ extern EFI_STATUS print_crypto_errors(EFI_STATUS rc, char *file, const char *fun #define crypterr(rc) print_crypto_errors((rc), __FILE__, __func__, __LINE__) #ifndef SHIM_UNIT_TEST -extern VOID msleep(unsigned long msecs); +extern VOID usleep(unsigned long usecs); #endif /* This is used in various things to determine if we should print to the diff --git a/lib/console.c b/lib/console.c index c7ca3bc2..a751f79d 100644 --- a/lib/console.c +++ b/lib/console.c @@ -745,9 +745,9 @@ setup_verbosity(VOID) #ifndef SHIM_UNIT_TEST VOID -msleep(unsigned long msecs) +usleep(unsigned long usecs) { - BS->Stall(msecs); + BS->Stall(usecs); } #endif diff --git a/model.c b/model.c index e122ba9c..6052ff50 100644 --- a/model.c +++ b/model.c @@ -54,7 +54,7 @@ gcm_gmult_4bit(u64 Xi[2], u128 Htable[16]) } void -msleep(int n) +usleep(int n) { __coverity_sleep__(); } diff --git a/replacements.c b/replacements.c index 6066f9d6..469e73aa 100644 --- a/replacements.c +++ b/replacements.c @@ -109,7 +109,7 @@ replacement_start_image(EFI_HANDLE image_handle, UINTN *exit_data_size, CHAR16 * console_print(L"Something has gone seriously wrong: %r\n", efi_status2); console_print(L"shim cannot continue, sorry.\n"); - msleep(5000000); + usleep(5000000); RT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL); @@ -137,7 +137,7 @@ exit_boot_services(EFI_HANDLE image_key, UINTN map_key) console_print(L"Bootloader has not verified loaded image.\n"); console_print(L"System is compromised. halting.\n"); - msleep(5000000); + usleep(5000000); RT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL); return EFI_SECURITY_VIOLATION; } @@ -162,7 +162,7 @@ do_exit(EFI_HANDLE ImageHandle, EFI_STATUS ExitStatus, console_print(L"Something has gone seriously wrong: %r\n", efi_status2); console_print(L"shim cannot continue, sorry.\n"); - msleep(5000000); + usleep(5000000); RT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL); } diff --git a/shim.c b/shim.c index c31e97fb..17afcabb 100644 --- a/shim.c +++ b/shim.c @@ -1207,7 +1207,7 @@ EFI_STATUS init_grub(EFI_HANDLE image_handle) efi_status = start_image(image_handle, MOK_MANAGER); if (EFI_ERROR(efi_status)) { console_print(L"start_image() returned %r\n", efi_status); - msleep(2000000); + usleep(2000000); return efi_status; } @@ -1222,7 +1222,7 @@ EFI_STATUS init_grub(EFI_HANDLE image_handle) console_print( L"start_image() returned %r, falling back to default loader\n", efi_status); - msleep(2000000); + usleep(2000000); load_options = NULL; load_options_size = 0; efi_status = start_image(image_handle, DEFAULT_LOADER); @@ -1230,7 +1230,7 @@ EFI_STATUS init_grub(EFI_HANDLE image_handle) if (EFI_ERROR(efi_status)) { console_print(L"start_image() returned %r\n", efi_status); - msleep(2000000); + usleep(2000000); } return efi_status; @@ -1642,7 +1642,7 @@ devel_egress(devel_egress_action action UNUSED) console_print(L"Waiting to %a...", reasons[action]); for (size_t sleepcount = 0; sleepcount < 10; sleepcount++) { console_print(L"%d...", 10 - sleepcount); - msleep(1000000); + usleep(1000000); } console_print(L"\ndoing %a\n", action); @@ -1780,7 +1780,7 @@ die: #if defined(ENABLE_SHIM_DEVEL) devel_egress(COLD_RESET); #else - msleep(5000000); + usleep(5000000); RT->ResetSystem(EfiResetShutdown, EFI_SECURITY_VIOLATION, 0, NULL); #endif @@ -1803,7 +1803,7 @@ die: */ if (user_insecure_mode) { console_print(L"Booting in insecure mode\n"); - msleep(2000000); + usleep(2000000); } /* -- cgit v1.2.3 From 7dfb6871b8a54710d9e9d8d56146e7c083d2e6a8 Mon Sep 17 00:00:00 2001 From: Jan Setje-Eilers Date: Fri, 28 Apr 2023 19:54:14 -0700 Subject: BS Variables for bootmgr revocations This adds support for applying SkuSiPolicy UEFI BS variables. These varaibles are needed for non-dbx based Windows revocations and are described here: https://support.microsoft.com/en-us/topic/kb5027455-guidance-for-blocking-vulnerable-windows-boot-managers-522bb851-0a61-44ad-aa94-ad11119c5e91 Signed-off-by: Jan Setje-Eilers --- include/guid.h | 1 + include/sbat.h | 10 ++- include/sbat_var_defs.h | 1 - include/ssp.h | 14 ++++ include/ssp_var_defs.h | 19 +++++ lib/guid.c | 1 + sbat.c | 211 ++++++++++++++++++++++++++++++++++++++++++++++-- shim.c | 77 +++++++++++++----- shim.h | 1 + 9 files changed, 304 insertions(+), 31 deletions(-) create mode 100644 include/ssp.h create mode 100644 include/ssp_var_defs.h (limited to 'lib') diff --git a/include/guid.h b/include/guid.h index dad63f0f..898c4fad 100644 --- a/include/guid.h +++ b/include/guid.h @@ -37,5 +37,6 @@ extern EFI_GUID SECURITY2_PROTOCOL_GUID; extern EFI_GUID EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID; extern EFI_GUID SHIM_LOCK_GUID; extern EFI_GUID MOK_VARIABLE_STORE; +extern EFI_GUID SECUREBOOT_EFI_NAMESPACE_GUID; #endif /* SHIM_GUID_H */ diff --git a/include/sbat.h b/include/sbat.h index 84f5ef01..af4c1a8f 100644 --- a/include/sbat.h +++ b/include/sbat.h @@ -30,11 +30,13 @@ #define SBAT_POLICY L"SbatPolicy" #define SBAT_POLICY8 "SbatPolicy" +#define SSP_POLICY L"SSPPolicy" +#define SSP_POLICY8 "SSPPolicy" -#define SBAT_POLICY_LATEST 1 -#define SBAT_POLICY_PREVIOUS 2 -#define SBAT_POLICY_RESET 3 -#define SBAT_POLICY_NOTREAD 255 +#define POLICY_LATEST 1 +#define POLICY_PREVIOUS 2 +#define POLICY_RESET 3 +#define POLICY_NOTREAD 255 extern UINTN _sbat, _esbat; diff --git a/include/sbat_var_defs.h b/include/sbat_var_defs.h index 2ea98e4e..772df972 100644 --- a/include/sbat_var_defs.h +++ b/include/sbat_var_defs.h @@ -42,5 +42,4 @@ SBAT_VAR_SIG SBAT_VAR_VERSION SBAT_VAR_LATEST_DATE "\n" \ SBAT_VAR_LATEST_REVOCATIONS #endif /* ENABLE_SHIM_DEVEL */ - #endif /* !SBAT_VAR_DEFS_H_ */ diff --git a/include/ssp.h b/include/ssp.h new file mode 100644 index 00000000..f25590c6 --- /dev/null +++ b/include/ssp.h @@ -0,0 +1,14 @@ +#ifndef SSP_H_ +#define SSP_H_ + +#define SSPVER_VAR_NAME L"SkuSiPolicyVersion" +#define SSPSIG_VAR_NAME L"SkuSiPolicyUpdateSigners" +#define SSP_VAR_ATTRS UEFI_VAR_NV_BS + +#define SSPVER_SIZE 8 +#define SSPSIG_SIZE 131 + +EFI_STATUS set_ssp_uefi_variable_internal(void); +EFI_STATUS set_ssp_uefi_variable(uint8_t*, uint8_t*, uint8_t*, uint8_t*); + +#endif /* !SSP_H_ */ diff --git a/include/ssp_var_defs.h b/include/ssp_var_defs.h new file mode 100644 index 00000000..4bfad878 --- /dev/null +++ b/include/ssp_var_defs.h @@ -0,0 +1,19 @@ +/* + * variable definitions to enable bootmgr self revocation + */ +#ifndef SSP_VAR_DEFS_H_ +#define SSP_VAR_DEFS_H_ + +uint8_t SkuSiPolicyVersion[] = { 0x2,0x0,0x0,0x0,0x0,0x0,0x2,0x0 }; +uint8_t SkuSiPolicyUpdateSigners[] = { +0x01,0x00,0x00,0x00,0x06,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x01,0x00,0x00,0x00, +0x0b,0x00,0x00,0x00,0xd0,0x91,0x73,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x00, +0x00,0x00,0x00,0x00,0x54,0xa6,0x78,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x00, +0x00,0x00,0x00,0x00,0x5c,0xa6,0x78,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x02,0x00, +0x00,0x00,0x00,0x00,0x64,0xa6,0x78,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, +0x00,0x00,0x00,0x00,0x0a,0x2b,0x06,0x01,0x04,0x01,0x82,0x37,0x0a,0x03,0x06,0x00, +0x00,0x00,0x00 }; + +#endif /* !SSP_VAR_DEFS_H_ */ diff --git a/lib/guid.c b/lib/guid.c index 904629eb..6e92cea3 100644 --- a/lib/guid.c +++ b/lib/guid.c @@ -36,3 +36,4 @@ EFI_GUID SECURITY2_PROTOCOL_GUID = { 0x94ab2f58, 0x1438, 0x4ef1, {0x91, 0x52, 0x EFI_GUID EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID = { 0xf4560cf6, 0x40ec, 0x4b4a, {0xa1, 0x92, 0xbf, 0x1d, 0x57, 0xd0, 0xb1, 0x89} }; EFI_GUID SHIM_LOCK_GUID = {0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23 } }; EFI_GUID MOK_VARIABLE_STORE = {0xc451ed2b, 0x9694, 0x45d3, {0xba, 0xba, 0xed, 0x9f, 0x89, 0x88, 0xa3, 0x89} }; +EFI_GUID SECUREBOOT_EFI_NAMESPACE_GUID = {0x77fa9abd, 0x0359, 0x4d32, {0xbd, 0x60, 0x28, 0xf4, 0xe7, 0x8f, 0x78, 0x4b} }; diff --git a/sbat.c b/sbat.c index 60669ba1..b33fe85c 100644 --- a/sbat.c +++ b/sbat.c @@ -4,13 +4,16 @@ */ #include "shim.h" +#include "ssp.h" +#include "ssp_var_defs.h" extern struct { UINT32 previous_offset; UINT32 latest_offset; } sbat_var_payload_header; -static UINT8 sbat_policy = SBAT_POLICY_NOTREAD; +static UINT8 sbat_policy = POLICY_NOTREAD; +static UINT8 ssp_policy = POLICY_NOTREAD; EFI_STATUS parse_sbat_section(char *section_base, size_t section_size, @@ -398,6 +401,49 @@ preserve_sbat_uefi_variable(UINT8 *sbat, UINTN sbatsize, UINT32 attributes, return false; } +/* + * This looks kind of weird, but it comes directly from the MS + * documentation: + * https://support.microsoft.com/en-us/topic/kb5027455-guidance-for-blocking-vulnerable-windows-boot-managers-522bb851-0a61-44ad-aa94-ad11119c5e91 + */ +static UINT64 +ssp_ver_to_ull(UINT16 *ver) +{ + dprint("major: %u\n", ver[0]); + dprint("minor: %u\n", ver[1]); + dprint("rev: %u\n", ver[2]); + dprint("build: %u\n", ver[3]); + + return ((UINT64)ver[0] << 48) + + ((UINT64)ver[1] << 32) + + ((UINT64)ver[2] << 16) + + ver[3]; +} + +static bool +preserve_ssp_uefi_variable(UINT8 *ssp_applied, UINTN sspversize, UINT32 attributes, + uint8_t *ssp_candidate) +{ + UINT64 old, new; + + if (ssp_applied == NULL || ssp_candidate == NULL) + return false; + + if (sspversize != SSPVER_SIZE) + return false; + + if (!check_sbat_var_attributes(attributes)) + return false; + + old = ssp_ver_to_ull((UINT16 *)ssp_applied); + new = ssp_ver_to_ull((UINT16 *)ssp_candidate); + + if (new > old) + return false; + else + return true; +} + static void clear_sbat_policy() { @@ -422,7 +468,7 @@ set_sbat_uefi_variable(char *sbat_var_previous, char *sbat_var_latest) char *sbat_var = NULL; bool reset_sbat = false; - if (sbat_policy == SBAT_POLICY_NOTREAD) { + if (sbat_policy == POLICY_NOTREAD) { efi_status = get_variable_attr(SBAT_POLICY, &sbat_policyp, &sbat_policysize, SHIM_LOCK_GUID, &attributes); @@ -477,9 +523,6 @@ set_sbat_uefi_variable(char *sbat_var_previous, char *sbat_var_latest) SHIM_LOCK_GUID, &attributes); /* * Always set the SbatLevel UEFI variable if it fails to read. - * - * Don't try to set the SbatLevel UEFI variable if attributes match - * and the signature matches. */ if (EFI_ERROR(efi_status)) { dprint(L"SBAT read failed %r\n", efi_status); @@ -532,7 +575,6 @@ set_sbat_uefi_variable(char *sbat_var_previous, char *sbat_var_latest) } FreePool(sbat); - return efi_status; } @@ -550,4 +592,161 @@ set_sbat_uefi_variable_internal(void) return set_sbat_uefi_variable(sbat_var_previous, sbat_var_latest); } +static void +clear_ssp_policy(void) +{ + EFI_STATUS efi_status = EFI_SUCCESS; + + efi_status = del_variable(SSP_POLICY, SHIM_LOCK_GUID); + if (EFI_ERROR(efi_status)) + console_error(L"Could not reset SSP Policy", efi_status); +} + +static EFI_STATUS +clear_ssp_uefi_variables(void) +{ + EFI_STATUS efi_status, rc = EFI_SUCCESS; + + /* delete previous variable */ + dprint("Deleting %s variable.\n", SSPVER_VAR_NAME); + efi_status = del_variable(SSPVER_VAR_NAME, SECUREBOOT_EFI_NAMESPACE_GUID); + if (EFI_ERROR(efi_status)) { + dprint(L"%s variable delete failed %r\n", SSPVER_VAR_NAME, + efi_status); + rc = efi_status; + } + dprint("Deleting %s variable.\n", SSPSIG_VAR_NAME); + efi_status = del_variable(SSPSIG_VAR_NAME, SECUREBOOT_EFI_NAMESPACE_GUID); + if (EFI_ERROR(efi_status)) { + dprint(L"%s variable delete failed %r\n", SSPSIG_VAR_NAME, + efi_status); + rc = efi_status; + } + + return rc; +} + +EFI_STATUS +set_ssp_uefi_variable(uint8_t *ssp_ver_previous, uint8_t *ssp_sig_previous, + uint8_t *ssp_ver_latest, uint8_t *ssp_sig_latest) +{ + EFI_STATUS efi_status = EFI_SUCCESS; + UINT32 attributes = 0; + + UINT8 *sspver = NULL; + UINT8 *policyp = NULL; + UINTN sspversize = 0; + UINTN policysize = 0; + + uint8_t *ssp_ver = NULL; + uint8_t *ssp_sig = NULL; + bool reset_ssp = false; + + _Static_assert(sizeof(SkuSiPolicyVersion) == SSPVER_SIZE, + "SkuSiPolicyVersion has unexpected size"); + _Static_assert(sizeof(SkuSiPolicyUpdateSigners) == SSPSIG_SIZE, + "SkuSiPolicyUpdateSigners has unexpected size"); + + if (ssp_policy == POLICY_NOTREAD) { + efi_status = get_variable_attr(SSP_POLICY, &policyp, + &policysize, SHIM_LOCK_GUID, + &attributes); + if (!EFI_ERROR(efi_status)) { + ssp_policy = *policyp; + clear_ssp_policy(); + } + } + + if (EFI_ERROR(efi_status)) { + dprint("Default SSP policy: previous\n"); + ssp_ver = ssp_ver_previous; + ssp_sig = ssp_sig_previous; + } else { + switch (ssp_policy) { + case POLICY_LATEST: + dprint("Custom SSP policy: latest\n");\ + ssp_ver = ssp_ver_latest; + ssp_sig = ssp_sig_latest; + break; + case POLICY_PREVIOUS: + dprint("Custom SSP policy: previous\n"); + ssp_ver = ssp_ver_previous; + ssp_sig = ssp_sig_previous; + break; + case POLICY_RESET: + if (secure_mode()) { + console_print(L"Cannot reset SSP policy: Secure Boot is enabled.\n"); + ssp_ver = ssp_ver_previous; + ssp_sig = ssp_sig_previous; + } else { + dprint(L"Custom SSP policy: reset OK\n"); + reset_ssp = true; + } + break; + default: + console_error(L"SSP policy state %llu is invalid", + EFI_INVALID_PARAMETER); + ssp_ver = ssp_ver_previous; + ssp_sig = ssp_sig_previous; + break; + } + } + + if (!ssp_ver && !ssp_sig && !reset_ssp) { + dprint(L"No supplied SSP data, not setting variables\n"); + return EFI_SUCCESS; + } + + efi_status = get_variable_attr(SSPVER_VAR_NAME, &sspver, &sspversize, + SECUREBOOT_EFI_NAMESPACE_GUID, &attributes); + /* + * Since generally we want bootmgr to manage its own revocations, + * we are much less agressive trying to set those variables + */ + if (EFI_ERROR(efi_status)) { + dprint(L"SkuSiPolicyVersion read failed %r\n", efi_status); + } else if (preserve_ssp_uefi_variable(sspver, sspversize, attributes, ssp_ver) + && !reset_ssp) { + FreePool(sspver); + + dprint(L"preserving %s variable it is %d bytes, attributes are 0x%08x\n", + SSPVER_VAR_NAME, sspversize, attributes); + return EFI_SUCCESS; + } else { + FreePool(sspver); + + efi_status = clear_ssp_uefi_variables(); + } + + if (reset_ssp) + return efi_status; + + /* set variable */ + efi_status = set_variable(SSPVER_VAR_NAME, SECUREBOOT_EFI_NAMESPACE_GUID, + SSP_VAR_ATTRS, SSPVER_SIZE, ssp_ver); + if (EFI_ERROR(efi_status)) { + dprint(L"%s variable writing failed %r\n", SSPVER_VAR_NAME, + efi_status); + return efi_status; + } + dprint("done setting %s variable.\n", SSPSIG_VAR_NAME); + + efi_status = set_variable(SSPSIG_VAR_NAME, SECUREBOOT_EFI_NAMESPACE_GUID, + SSP_VAR_ATTRS, SSPSIG_SIZE, ssp_sig); + if (EFI_ERROR(efi_status)) { + dprint(L"%s variable writing failed %r\n", SSPSIG_VAR_NAME, + efi_status); + return efi_status; + } + dprint("done setting %s variable.\n", SSPSIG_VAR_NAME); + + return efi_status; +} + +EFI_STATUS +set_ssp_uefi_variable_internal(void) +{ + return set_ssp_uefi_variable(NULL, NULL, SkuSiPolicyVersion, + SkuSiPolicyUpdateSigners); +} // vim:fenc=utf-8:tw=75:noet diff --git a/shim.c b/shim.c index 12ce10d6..2ad1c063 100644 --- a/shim.c +++ b/shim.c @@ -1395,18 +1395,45 @@ uninstall_shim_protocols(void) #endif } +static void +check_section_helper(char *section_name, int len, void **pointer, + EFI_IMAGE_SECTION_HEADER *Section, void *data, + int datasize, size_t minsize) +{ + if (CompareMem(Section->Name, section_name, len) == 0) { + *pointer = ImageAddress(data, datasize, Section->PointerToRawData); + if (Section->SizeOfRawData < minsize) { + dprint(L"found and rejected %.*a bad size\n", len, section_name); + dprint(L"minsize: %d\n", minsize); + dprint(L"rawsize: %d\n", Section->SizeOfRawData); + return ; + } + if (!*pointer) { + return ; + } + dprint(L"found %.*a\n", len, section_name); + } +} + +#define check_section(section_name, pointer, section, data, datasize, minsize) \ + check_section_helper(section_name, sizeof(section_name) - 1, pointer, \ + section, data, datasize, minsize) + EFI_STATUS load_revocations_file(EFI_HANDLE image_handle, CHAR16 *PathName) { EFI_STATUS efi_status = EFI_SUCCESS; PE_COFF_LOADER_IMAGE_CONTEXT context; EFI_IMAGE_SECTION_HEADER *Section; - void *pointer; int datasize = 0; void *data = NULL; unsigned int i; char *sbat_var_previous = NULL; char *sbat_var_latest = NULL; + uint8_t *ssps_previous = NULL; + uint8_t *sspv_previous = NULL; + uint8_t *ssps_latest = NULL; + uint8_t *sspv_latest = NULL; efi_status = read_image(image_handle, L"revocations.efi", &PathName, &data, &datasize); @@ -1422,25 +1449,19 @@ load_revocations_file(EFI_HANDLE image_handle, CHAR16 *PathName) Section = context.FirstSection; for (i = 0; i < context.NumberOfSections; i++, Section++) { - dprint(L"checking section %a\n", (char *)Section->Name); - if (CompareMem(Section->Name, ".sbatl", 6) == 0) { - pointer = ImageAddress(data, datasize, - Section->PointerToRawData); - if (!pointer) { - continue; - } - sbat_var_latest = (char *)pointer; - dprint(L"found sbatl\n"); - } - if (CompareMem(Section->Name, ".sbatp", 6) == 0) { - pointer = ImageAddress(data, datasize, - Section->PointerToRawData); - if (!pointer) { - continue; - } - sbat_var_previous = (char *)pointer; - dprint(L"found sbatp\n"); - } + dprint(L"checking section \"%c%c%c%c%c%c%c%c\"\n", (char *)Section->Name); + check_section(".sbatp", (void **)&sbat_var_previous, Section, + data, datasize, sizeof(SBAT_VAR_ORIGINAL)); + check_section(".sbatl", (void **)&sbat_var_latest, Section, + data, datasize, sizeof(SBAT_VAR_ORIGINAL)); + check_section(".sspvp", (void **)&sspv_previous, Section, + data, datasize, SSPVER_SIZE); + check_section(".sspsp", (void **)&ssps_previous, Section, + data, datasize, SSPSIG_SIZE); + check_section(".sspvl", (void **)&sspv_latest, Section, + data, datasize, SSPVER_SIZE); + check_section(".sspsl", (void **)&ssps_latest, Section, + data, datasize, SSPSIG_SIZE); } if (sbat_var_latest && sbat_var_previous) { @@ -1450,6 +1471,16 @@ load_revocations_file(EFI_HANDLE image_handle, CHAR16 *PathName) } else { dprint(L"no data for SBAT_LEVEL\n"); } + + if ((sspv_previous && ssps_previous) || (sspv_latest && ssps_latest)) { + dprint(L"attempting to update SkuSiPolicy\n"); + efi_status = set_ssp_uefi_variable(sspv_previous, ssps_previous, + sspv_latest, ssps_latest); + + } else { + dprint(L"no data for SkuSiPolicy\n"); + } + FreePool(data); return efi_status; } @@ -1814,6 +1845,12 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab) dprint(L"%s variable initialization failed: %r\n", SBAT_VAR_NAME, efi_status); } + efi_status = set_ssp_uefi_variable_internal(); + if (EFI_ERROR(efi_status)) { + dprint(L"%s variable initialization failed: %r\n", + SSPVER_VAR_NAME, efi_status); + } + dprint(L"%s variable initialization done\n", SSPVER_VAR_NAME); if (secure_mode()) { char *sbat_start = (char *)&_sbat; diff --git a/shim.h b/shim.h index 652be45c..5791a031 100644 --- a/shim.h +++ b/shim.h @@ -180,6 +180,7 @@ #include "include/replacements.h" #include "include/sbat.h" #include "include/sbat_var_defs.h" +#include "include/ssp.h" #if defined(OVERRIDE_SECURITY_POLICY) #include "include/security_policy.h" #endif -- cgit v1.2.3 From d197220e834e7915326c6a99e17bafe0dcfb3f77 Mon Sep 17 00:00:00 2001 From: Dan Nicholson Date: Fri, 4 Oct 2024 11:00:32 -0600 Subject: Backport EFI_HTTP_ERROR status code The define can be dropped when gnu-efi is updated to include de6f9259e8476495c78babbc25250a59de7f3942. Signed-off-by: Dan Nicholson --- include/errors.h | 3 +++ lib/console.c | 1 + 2 files changed, 4 insertions(+) (limited to 'lib') diff --git a/include/errors.h b/include/errors.h index 67d821e0..eab58453 100644 --- a/include/errors.h +++ b/include/errors.h @@ -9,5 +9,8 @@ #ifndef EFI_SECURITY_VIOLATION #define EFI_SECURITY_VIOLATION EFIERR(26) #endif +#ifndef EFI_HTTP_ERROR +#define EFI_HTTP_ERROR EFIERR(35) +#endif #endif /* SHIM_ERRORS_H */ diff --git a/lib/console.c b/lib/console.c index a751f79d..f6038320 100644 --- a/lib/console.c +++ b/lib/console.c @@ -651,6 +651,7 @@ static struct { { EFI_PROTOCOL_ERROR, L"Protocol Error"}, { EFI_INCOMPATIBLE_VERSION, L"Incompatible Version"}, { EFI_SECURITY_VIOLATION, L"Security Violation"}, + { EFI_HTTP_ERROR, L"HTTP Error"}, // warnings { EFI_WARN_UNKNOWN_GLYPH, L"Warning Unknown Glyph"}, -- cgit v1.2.3 From dc45aa6b3ce0c54c20ed284222297cdb29baa5d5 Mon Sep 17 00:00:00 2001 From: Michał Żygowski Date: Sat, 16 Dec 2023 12:45:42 +0100 Subject: lib/simple_file.c: Allocate zeroed pool for SimpleFS entries MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The loop retrieving the SimpleFS volume labels and names may skip some volumes if either HandleProtocol or OpenVolume or GetInfo fails. Those skipped volumes would have uninitialized pointers to their names in the respective entries indices. This would lead to accessing random memory in console_select, because count_lines would not catch the holes with non-existing entries. On affected platforms the result is a hang of the MokManager while trying to enroll a key from disk. The issue has been triggered on a TianoCore EDK2 UEFIPayload based firmware for x86 platforms with additional filesystem drivers: ExFAT, NTFS, EXT2 and EXT4. Use AllocateZeroPool to ensure entries array will be initialized with NULL pointers. Handling the non-existing entries will be added in subsequent commits. Signed-off-by: Michał Żygowski --- lib/simple_file.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'lib') diff --git a/lib/simple_file.c b/lib/simple_file.c index f22852d4..43b2f87a 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -184,7 +184,7 @@ simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) if (!count || !vol_handles) return EFI_NOT_FOUND; - entries = AllocatePool(sizeof(CHAR16 *) * (count+1)); + entries = AllocateZeroPool(sizeof(CHAR16 *) * (count+1)); if (!entries) return EFI_OUT_OF_RESOURCES; -- cgit v1.2.3 From 9415d3cada09f8043bb9a2c1b32fd1f909cefab0 Mon Sep 17 00:00:00 2001 From: Michał Żygowski Date: Sat, 16 Dec 2023 12:58:47 +0100 Subject: simple_file: Allow to form a volume name from DevicePath MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit In case GetInfo of volume root fails, it is still possible to form a volume name from the DevicePath. Do not skip given SimpleFS volume handle and try to form a name from DevicePath. That way we do not lose some filesystems from file browser. This change already fixes the problem of a hanging platform when trying to enroll a key from disk. However, there is still a chance of having a non-contiguous array of entries, which will be fixed in next commit. Signed-off-by: Michał Żygowski --- lib/simple_file.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) (limited to 'lib') diff --git a/lib/simple_file.c b/lib/simple_file.c index 43b2f87a..fc082bed 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -208,10 +208,13 @@ simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) efi_status = root->GetInfo(root, &EFI_FILE_SYSTEM_INFO_GUID, &size, fi); - if (EFI_ERROR(efi_status)) - continue; + /* If GetInfo fails, try to form a name from DevicePath. */ + if (EFI_ERROR(efi_status)){ + name = NULL; + } else { + name = fi->VolumeLabel; + } - name = fi->VolumeLabel; if (!name || StrLen(name) == 0 || StrCmp(name, L" ") == 0) name = DevicePathToStr(DevicePathFromHandle(vol_handles[i])); -- cgit v1.2.3 From d6076cb61297c13a0c55c0b848b85b9f31a912ac Mon Sep 17 00:00:00 2001 From: Michał Żygowski Date: Sat, 16 Dec 2023 13:01:29 +0100 Subject: simple_file: Use second variable to create filesystem entries MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit If HandleProtocol or OpenVolume fails, the entries array will become non-contiguous, i.e. will have NULL pointers between valid volume names in the array. Because of that count_lines may return a lower number of entries than expected. As a result one may not browse all valid filesystems in the file explorer. Add a second index variable that will increment only on successfully created filesystem entries. As a result, count_lines should return proper length and there won't be any lost partitions or accesses to invalid entries. Signed-off-by: Michał Żygowski --- lib/simple_file.c | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) (limited to 'lib') diff --git a/lib/simple_file.c b/lib/simple_file.c index fc082bed..6057f883 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -170,7 +170,7 @@ simple_file_write_all(EFI_FILE *file, UINTN size, void *buffer) EFI_STATUS simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) { - UINTN count, i; + UINTN count, i, j; EFI_HANDLE *vol_handles = NULL; EFI_STATUS efi_status; CHAR16 **entries; @@ -188,7 +188,7 @@ simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) if (!entries) return EFI_OUT_OF_RESOURCES; - for (i = 0; i < count; i++) { + for (i = 0, j = 0; i < count; i++) { char buf[4096]; UINTN size = sizeof(buf); EFI_FILE_SYSTEM_INFO *fi = (void *)buf; @@ -218,12 +218,12 @@ simple_volume_selector(CHAR16 **title, CHAR16 **selected, EFI_HANDLE *h) if (!name || StrLen(name) == 0 || StrCmp(name, L" ") == 0) name = DevicePathToStr(DevicePathFromHandle(vol_handles[i])); - entries[i] = AllocatePool((StrLen(name) + 2) * sizeof(CHAR16)); - if (!entries[i]) + entries[j] = AllocatePool((StrLen(name) + 2) * sizeof(CHAR16)); + if (!entries[j]) break; - StrCpy(entries[i], name); + StrCpy(entries[j++], name); } - entries[i] = NULL; + entries[j] = NULL; val = console_select(title, entries, 0); -- cgit v1.2.3 From bb114a3b92a96875dc71e5e4925bedba5c02f958 Mon Sep 17 00:00:00 2001 From: Ard Biesheuvel Date: Thu, 29 Jun 2023 17:58:18 +0200 Subject: Implement shim image load protocol Define a new protocol for loading and starting images, encapsulating shim's PE loading facilities and verification/authentication against the same set of certificates that shim_lock::verify() authenticates against. This removes the need for loaders like GRUB to implement their own PE loader in order to be able to invoke loaded images as PE applications, rather than implementing a bespoke OS dependent handover protocol (e.g., invoke Linux via its EFI stub) Signed-off-by: Ard Biesheuvel --- include/guid.h | 2 ++ lib/guid.c | 2 ++ replacements.c | 11 ++++++ shim.c | 107 +++++++++++++++++++++++++++++++++++++++++++++++++++++---- shim.h | 18 ++++++++++ 5 files changed, 134 insertions(+), 6 deletions(-) (limited to 'lib') diff --git a/include/guid.h b/include/guid.h index 898c4fad..e32dfc07 100644 --- a/include/guid.h +++ b/include/guid.h @@ -36,6 +36,8 @@ extern EFI_GUID SECURITY_PROTOCOL_GUID; extern EFI_GUID SECURITY2_PROTOCOL_GUID; extern EFI_GUID EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID; extern EFI_GUID SHIM_LOCK_GUID; +extern EFI_GUID SHIM_IMAGE_LOADER_GUID; +extern EFI_GUID SHIM_LOADED_IMAGE_GUID; extern EFI_GUID MOK_VARIABLE_STORE; extern EFI_GUID SECUREBOOT_EFI_NAMESPACE_GUID; diff --git a/lib/guid.c b/lib/guid.c index 6e92cea3..1dc90ca9 100644 --- a/lib/guid.c +++ b/lib/guid.c @@ -35,5 +35,7 @@ EFI_GUID SECURITY_PROTOCOL_GUID = { 0xA46423E3, 0x4617, 0x49f1, {0xB9, 0xFF, 0xD EFI_GUID SECURITY2_PROTOCOL_GUID = { 0x94ab2f58, 0x1438, 0x4ef1, {0x91, 0x52, 0x18, 0x94, 0x1a, 0x3a, 0x0e, 0x68 } }; EFI_GUID EFI_MEMORY_ATTRIBUTE_PROTOCOL_GUID = { 0xf4560cf6, 0x40ec, 0x4b4a, {0xa1, 0x92, 0xbf, 0x1d, 0x57, 0xd0, 0xb1, 0x89} }; EFI_GUID SHIM_LOCK_GUID = {0x605dab50, 0xe046, 0x4300, {0xab, 0xb6, 0x3d, 0xd8, 0x10, 0xdd, 0x8b, 0x23 } }; +EFI_GUID SHIM_IMAGE_LOADER_GUID = {0x1f492041, 0xfadb, 0x4e59, {0x9e, 0x57, 0x7c, 0xaf, 0xe7, 0x3a, 0x55, 0xab } }; +EFI_GUID SHIM_LOADED_IMAGE_GUID = {0x6e6baeb8, 0x7108, 0x4179, {0x94, 0x9d, 0xa3, 0x49, 0x34, 0x15, 0xec, 0x97 } }; EFI_GUID MOK_VARIABLE_STORE = {0xc451ed2b, 0x9694, 0x45d3, {0xba, 0xba, 0xed, 0x9f, 0x89, 0x88, 0xa3, 0x89} }; EFI_GUID SECUREBOOT_EFI_NAMESPACE_GUID = {0x77fa9abd, 0x0359, 0x4d32, {0xbd, 0x60, 0x28, 0xf4, 0xe7, 0x8f, 0x78, 0x4b} }; diff --git a/replacements.c b/replacements.c index 469e73aa..d840616f 100644 --- a/replacements.c +++ b/replacements.c @@ -148,6 +148,17 @@ do_exit(EFI_HANDLE ImageHandle, EFI_STATUS ExitStatus, UINTN ExitDataSize, CHAR16 *ExitData) { EFI_STATUS efi_status; + SHIM_LOADED_IMAGE *image; + + efi_status = BS->HandleProtocol(ImageHandle, &SHIM_LOADED_IMAGE_GUID, + (void **)&image); + if (!EFI_ERROR(efi_status)) { + image->exit_status = ExitStatus; + image->exit_data_size = ExitDataSize; + image->exit_data = ExitData; + + longjmp(image->longjmp_buf, 1); + } shim_fini(); diff --git a/shim.c b/shim.c index 14355d27..60b5e720 100644 --- a/shim.c +++ b/shim.c @@ -1314,6 +1314,7 @@ init_openssl(void) } static SHIM_LOCK shim_lock_interface; +static SHIM_IMAGE_LOADER shim_image_loader_interface; static EFI_HANDLE shim_lock_handle; EFI_STATUS @@ -1346,10 +1347,12 @@ install_shim_protocols(void) /* * Install the protocol */ - efi_status = BS->InstallProtocolInterface(&shim_lock_handle, - &SHIM_LOCK_GUID, - EFI_NATIVE_INTERFACE, - &shim_lock_interface); + efi_status = BS->InstallMultipleProtocolInterfaces(&shim_lock_handle, + &SHIM_LOCK_GUID, + &shim_lock_interface, + &SHIM_IMAGE_LOADER_GUID, + &shim_image_loader_interface, + NULL); if (EFI_ERROR(efi_status)) { console_error(L"Could not install security protocol", efi_status); @@ -1375,8 +1378,12 @@ uninstall_shim_protocols(void) /* * If we're back here then clean everything up before exiting */ - BS->UninstallProtocolInterface(shim_lock_handle, &SHIM_LOCK_GUID, - &shim_lock_interface); + BS->UninstallMultipleProtocolInterfaces(shim_lock_handle, + &SHIM_LOCK_GUID, + &shim_lock_interface, + &SHIM_IMAGE_LOADER_GUID, + &shim_image_loader_interface, + NULL); if (!secure_mode()) return; @@ -1908,6 +1915,91 @@ devel_egress(devel_egress_action action UNUSED) #endif } +static EFI_STATUS EFIAPI +shim_load_image(IN BOOLEAN BootPolicy, IN EFI_HANDLE ParentImageHandle, + IN EFI_DEVICE_PATH *FilePath, IN VOID *SourceBuffer, + IN UINTN SourceSize, OUT EFI_HANDLE *ImageHandle) +{ + SHIM_LOADED_IMAGE *image; + EFI_STATUS efi_status; + + (void)FilePath; + + if (BootPolicy || !SourceBuffer || !SourceSize) + return EFI_UNSUPPORTED; + + image = AllocatePool(sizeof(*image)); + if (!image) + return EFI_OUT_OF_RESOURCES; + + SetMem(image, sizeof(*image), 0); + + image->li.Revision = 0x1000; + image->li.ParentHandle = ParentImageHandle; + image->li.SystemTable = systab; + + efi_status = handle_image(SourceBuffer, SourceSize, &image->li, + &image->entry_point, &image->alloc_address, + &image->alloc_pages); + if (EFI_ERROR(efi_status)) + goto free_image; + + *ImageHandle = NULL; + efi_status = BS->InstallMultipleProtocolInterfaces(ImageHandle, + &SHIM_LOADED_IMAGE_GUID, image, + &EFI_LOADED_IMAGE_GUID, &image->li, + NULL); + if (EFI_ERROR(efi_status)) + goto free_alloc; + + return EFI_SUCCESS; + +free_alloc: + BS->FreePages(image->alloc_address, image->alloc_pages); +free_image: + FreePool(image); + return efi_status; +} + +static EFI_STATUS EFIAPI +shim_start_image(IN EFI_HANDLE ImageHandle, OUT UINTN *ExitDataSize, + OUT CHAR16 **ExitData OPTIONAL) +{ + SHIM_LOADED_IMAGE *image; + EFI_STATUS efi_status; + + efi_status = BS->HandleProtocol(ImageHandle, &SHIM_LOADED_IMAGE_GUID, + (void **)&image); + if (EFI_ERROR(efi_status) || image->started) + return EFI_INVALID_PARAMETER; + + if (!setjmp(image->longjmp_buf)) { + image->started = true; + efi_status = + image->entry_point(ImageHandle, image->li.SystemTable); + } else { + if (ExitData) { + *ExitDataSize = image->exit_data_size; + *ExitData = (CHAR16 *)image->exit_data; + } + efi_status = image->exit_status; + } + + // + // We only support EFI applications, so we can unload and free the + // image unconditionally. + // + BS->UninstallMultipleProtocolInterfaces(ImageHandle, + &EFI_LOADED_IMAGE_GUID, image, + &SHIM_LOADED_IMAGE_GUID, &image->li, + NULL); + + BS->FreePages(image->alloc_address, image->alloc_pages); + FreePool(image); + + return efi_status; +} + EFI_STATUS efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab) { @@ -1951,6 +2043,9 @@ efi_main (EFI_HANDLE passed_image_handle, EFI_SYSTEM_TABLE *passed_systab) shim_lock_interface.Hash = shim_hash; shim_lock_interface.Context = shim_read_header; + shim_image_loader_interface.LoadImage = shim_load_image; + shim_image_loader_interface.StartImage = shim_start_image; + systab = passed_systab; image_handle = global_image_handle = passed_image_handle; diff --git a/shim.h b/shim.h index 43fcb191..704e34ea 100644 --- a/shim.h +++ b/shim.h @@ -55,6 +55,7 @@ #ifndef SHIM_UNIT_TEST #include #include +#include #undef uefi_call_wrapper #include #include @@ -237,6 +238,11 @@ typedef struct _SHIM_LOCK { EFI_SHIM_LOCK_CONTEXT Context; } SHIM_LOCK; +typedef struct _SHIM_IMAGE_LOADER { + EFI_IMAGE_LOAD LoadImage; + EFI_IMAGE_START StartImage; +} SHIM_IMAGE_LOADER; + extern EFI_STATUS shim_init(void); extern void shim_fini(void); extern EFI_STATUS EFIAPI LogError_(const char *file, int line, const char *func, @@ -326,4 +332,16 @@ verify_buffer (char *data, int datasize, char *translate_slashes(char *out, const char *str); +typedef struct { + EFI_LOADED_IMAGE li; + EFI_IMAGE_ENTRY_POINT entry_point; + EFI_PHYSICAL_ADDRESS alloc_address; + UINTN alloc_pages; + EFI_STATUS exit_status; + CONST CHAR16 *exit_data; + UINTN exit_data_size; + jmp_buf longjmp_buf; + BOOLEAN started; +} SHIM_LOADED_IMAGE; + #endif /* SHIM_H_ */ -- cgit v1.2.3 From d45c610ba558c1b1673ff94590b71a156dd2fd3c Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Wed, 12 Mar 2025 13:43:46 -0400 Subject: SetSecureVariable(): free Cert on failure If variable_create_esl_with_one_signature() succeeds but CreateTimeBasedPayload() fails, we leak the allocation for our certificate. This patch frees it. Resolves: Coverity CID 457504 Signed-off-by: Peter Jones --- lib/variables.c | 2 ++ 1 file changed, 2 insertions(+) (limited to 'lib') diff --git a/lib/variables.c b/lib/variables.c index 8e63aa8f..1a2c7d48 100644 --- a/lib/variables.c +++ b/lib/variables.c @@ -226,6 +226,8 @@ SetSecureVariable(const CHAR16 * const var, UINT8 *Data, UINTN len, } efi_status = CreateTimeBasedPayload(&DataSize, (UINT8 **)&Cert); if (EFI_ERROR(efi_status)) { + if (Cert && Cert != (EFI_SIGNATURE_LIST *)Data) + FreePool(Cert); console_print(L"Failed to create time based payload %d\n", efi_status); return efi_status; -- cgit v1.2.3 From 7b753820e79b5b38be59c40aaa7960eab0aae119 Mon Sep 17 00:00:00 2001 From: Peter Jones Date: Wed, 12 Mar 2025 16:11:58 -0400 Subject: simple_dir_filter(): test our 'next' pointer "gcc -fanalyzer" thinks that in simple_dir_filter(), we can get "next" to be a NULL pointer even when simple_dir_read_all() return success and we're iterating the total number of entries it claimed it returned. I don't think this is true, but to make it stop complaining I've added tests to that pointer that'll make it stop if it gets to the end of the list. Signed-off-by: Peter Jones --- lib/simple_file.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'lib') diff --git a/lib/simple_file.c b/lib/simple_file.c index 6057f883..abbc4975 100644 --- a/lib/simple_file.c +++ b/lib/simple_file.c @@ -288,7 +288,7 @@ simple_dir_filter(EFI_HANDLE image, CHAR16 *name, CHAR16 *filter, goto out; ptr = next = *entries; - for (i = 0; i < tot; i++) { + for (i = 0; next && i < tot; i++) { int len = StrLen(next->FileName); for (c = 0; c < filtercount; c++) { @@ -311,7 +311,7 @@ simple_dir_filter(EFI_HANDLE image, CHAR16 *name, CHAR16 *filter, *count = 0; ptr = next = *entries; - for (i = 0; i < tot; i++) { + for (i = 0; next && i < tot; i++) { int len = StrLen(next->FileName); if (StrCmp(next->FileName, L".") == 0) -- cgit v1.2.3