support booting EFI application on x86_64 architecture

Co-authored-by: Daniele Lacamera <daniele@wolfssl.com>
pull/156/head
Marco Oliverio 2021-11-24 09:59:47 +01:00
parent 62132201bf
commit a187442455
24 changed files with 5443 additions and 27 deletions

1
.gitignore vendored
View File

@ -37,6 +37,7 @@
*.hex
*.rom
*.bin
*.efi
# Debug files
*.dSYM/

View File

@ -39,10 +39,12 @@ CFLAGS+= \
-D"PLATFORM_$(TARGET)"
# Setup default optimizations (for GCC)
ifeq ($(USE_GCC),1)
ifneq ($(TARGET),x86_64_efi)
ifeq ($(USE_GCC),1)
CFLAGS+=-Wall -Wextra -Wno-main -ffreestanding -Wno-unused -nostartfiles
CFLAGS+=-ffunction-sections -fdata-sections
LDFLAGS+=-T $(LSCRIPT) -Wl,-gc-sections -Wl,-Map=wolfboot.map -ffreestanding -nostartfiles
endif
endif
MAIN_TARGET=factory.bin
@ -52,12 +54,27 @@ ifeq ($(TARGET),stm32l5)
MAIN_TARGET:=wolfboot.bin test-app/image_v1_signed.bin
endif
ifeq ($(TARGET),x86_64_efi)
MAIN_TARGET:=wolfboot.efi
endif
ASFLAGS:=$(CFLAGS)
BOOTLOADER_PARTITION_SIZE?=$$(( $(WOLFBOOT_PARTITION_BOOT_ADDRESS) - $(ARCH_FLASH_OFFSET)))
all: $(MAIN_TARGET)
wolfboot.efi: wolfboot.elf
@echo "\t[BIN] $@"
$(Q)$(OBJCOPY) -j .text -j .sdata -j .data \
-j .dynamic -j .dynsym -j .rel \
-j .rela -j .reloc -j .eh_frame \
--target=efi-app-x86_64 --subsystem=10 $^ $@
@echo
@echo "\t[SIZE]"
$(Q)$(SIZE) wolfboot.efi
@echo
wolfboot.bin: wolfboot.elf
@echo "\t[BIN] $@"
$(Q)$(OBJCOPY) -O binary $^ $@

22
arch.mk
View File

@ -21,6 +21,13 @@ UART_TARGET=$(TARGET)
# Include SHA256 module because it's implicitly needed by RSA
WOLFCRYPT_OBJS+=./lib/wolfssl/wolfcrypt/src/sha256.o
ifeq ($(ARCH),x86_64)
OBJS+=src/boot_x86_64.o
ifeq ($(DEBUG),1)
CFLAGS+=-DWOLFBOOT_DEBUG_EFI=1
endif
endif
## ARM
ifeq ($(ARCH),AARCH64)
CROSS_COMPILE:=aarch64-none-elf-
@ -299,6 +306,21 @@ ifeq ($(USE_GCC),1)
OUTPUT_FLAG=-o
endif
ifeq ($(TARGET),x86_64_efi)
GNU_EFI_LIB_PATH?=/usr/lib
GNU_EFI_CRT0=$(GNU_EFI_LIB_PATH)/crt0-efi-x86_64.o
GNU_EFI_LSCRIPT=$(GNU_EFI_LIB_PATH)/elf_x86_64_efi.lds
CFLAGS += -fpic -ffreestanding -fno-stack-protector -fno-stack-check \
-fshort-wchar -mno-red-zone -maccumulate-outgoing-args
CFLAGS += -I/usr/include/efi -DPLATFORM_X86_64_EFI
LDFLAGS = -shared -Bsymbolic -L/usr/lib -T$(GNU_EFI_LSCRIPT)
LD_START_GROUP = $(GNU_EFI_CRT0)
LD_END_GROUP = -lgnuefi -lefi
LD = ld
UPDATE_OBJS:=src/update_ram.o
endif
BOOT_IMG?=test-app/image.bin
## Update mechanism

View File

@ -0,0 +1,8 @@
ARCH=x86_64
TARGET=x86_64_efi
WOLFBOOT_SMALL_STACK=1
SIGN?=ED25519
HASH?=SHA256
IMAGE_HEADER_SIZE?=0x100
DEBUG=0
SPMATH=0

View File

@ -21,6 +21,7 @@ This README describes configuration of supported targets.
* [STM32WB55](#stm32wb55)
* [TI Hercules TMS570LC435](#ti-hercules-tms570lc435)
* [Xilinx Zynq UltraScale](#xilinx-zynq-ultrascale)
* [Qemu x86_64 UEFI](#qemu-x86_64-uefi)
## STM32F4
@ -930,3 +931,52 @@ to compile.
## TI Hercules TMS570LC435
See [/config/examples/ti-tms570lc435.config](/config/examples/ti-tms570lc435.config) for example configuration.
## Qemu x86-64 UEFI
x86-64bit machine with UEFI bios can run wolfBoot as EFI application.
### Prerequisites:
* qemu-system-x86_64
* [GNU-EFI] (https://sourceforge.net/projects/gnu-efi/)
* Open Virtual Machine firmware bios images (OVMF) by [Tianocore](https://tianocore.org)
On a debian-like system it is sufficient to install the packages as follows:
`apt install qemu ovmf gnu-efi`
### Configuration
An example configuration is provided in [config/examples/x86_64_efi.config](config/examples/x86_64_efi.config)
### Building and running on qemu
The bootloader and the initialization script `startup.nsh` for execution in the EFI environment are stored in a loopback FAT partition.
The script [tools/efi/prepare_uefi_partition.sh](tools/efi/prepare_uefi_partition.sh) creates a new empty
FAT loopback partitions and adds `startup.nsh`.
A kernel with an embedded rootfs partition can be now created and added to the image, via the
script [tools/efi/compile_efi_linux.sh](tools/efi/compile_efi_linux.sh). The script actually adds two instances
of the target systems: `kernel.img` and `update.img`, both signed for authentication, and tagged with version
`1` and `2` respectively.
Compiling with `make` will produce the bootloader image in `wolfboot.efi`.
The script [tools/efi/run_efi.sh](tools/efi/run_efi.sh) will add `wolfboot.efi` to the bootloader loopback
partition, and run the system on qemu. If both kernel images are present and valid, wolfBoot will choose the image
with the higher version number, so `update.img` will be staged as it's tagged with version `2`.
The sequence is summarized below:
```
cp config/examples/x86_64_efi.config .config
tools/efi/prepare_efi_partition.sh
make
tools/efi/compile_efi_linux.sh
tools/efi/run_efi.sh
```

258
hal/x86_64_efi.c 100644
View File

@ -0,0 +1,258 @@
/* x86_64_efi.c
*
* Copyright (C) 2021 wolfSSL Inc.
*
* This file is part of wolfBoot.
*
* wolfBoot is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfBoot is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#include <stdint.h>
#include <target.h>
#include "image.h"
#include "loader.h"
#include "printf.h"
#ifdef PLATFORM_X86_64_EFI
#include <efi/efi.h>
#include <efi/efilib.h>
#ifdef __WOLFBOOT
void hal_init(void)
{
}
void hal_prepare_boot(void)
{
}
#endif
#define PAGE_SIZE 0x1000
#define EFI_DEVICE_PATH_PROTOCOL_HW_TYPE 0x01
#define EFI_DEVICE_PATH_PROTOCOL_MEM_SUBTYPE 0x03
static EFI_SYSTEM_TABLE *gSystemTable;
static EFI_HANDLE *gImageHandle;
EFI_PHYSICAL_ADDRESS kernel_addr;
EFI_PHYSICAL_ADDRESS update_addr;
int RAMFUNCTION hal_flash_write(uint32_t address, const uint8_t *data, int len)
{
return 0;
}
void RAMFUNCTION hal_flash_unlock(void)
{
}
void RAMFUNCTION hal_flash_lock(void)
{
}
int RAMFUNCTION hal_flash_erase(uint32_t address, int len)
{
return 0;
}
static void panic()
{
while(1) {}
}
void RAMFUNCTION x86_64_efi_do_boot(uint8_t *kernel)
{
MEMMAP_DEVICE_PATH mem_path_device[2];
EFI_HANDLE kernelImageHandle;
EFI_STATUS status;
uint32_t *size;
size = (uint32_t *)(kernel + 4);
kernel += IMAGE_HEADER_SIZE;
mem_path_device->Header.Type = EFI_DEVICE_PATH_PROTOCOL_HW_TYPE;
mem_path_device->Header.SubType = EFI_DEVICE_PATH_PROTOCOL_MEM_SUBTYPE;
mem_path_device->MemoryType = EfiLoaderData;
mem_path_device->StartingAddress = (EFI_PHYSICAL_ADDRESS)kernel;
mem_path_device->EndingAddress = (EFI_PHYSICAL_ADDRESS)(kernel+*size);
SetDevicePathNodeLength(&mem_path_device->Header,
sizeof(MEMMAP_DEVICE_PATH));
SetDevicePathEndNode(&mem_path_device[1].Header);
wolfBoot_printf("Staging kernel at address %x, size: %u\n", kernel, *size);
status = uefi_call_wrapper(gSystemTable->BootServices->LoadImage,
6,
0, /* bool */
gImageHandle,
(EFI_DEVICE_PATH*)mem_path_device,
kernel,
*size,
&kernelImageHandle);
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't load kernel image from memory\n");
panic();
}
status = uefi_call_wrapper(gSystemTable->BootServices->StartImage,
3,
kernelImageHandle, 0, NULL);
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't load kernel image from memory\n");
panic();
}
}
static UINT64 FileSize(EFI_FILE_HANDLE FileHandle)
{
EFI_FILE_INFO *FileInfo;
UINT64 ret;
FileInfo = LibFileInfo(FileHandle);
if (FileInfo == NULL)
panic();
ret = FileInfo->FileSize;
FreePool(FileInfo);
return ret;
}
static EFI_FILE_HANDLE GetVolume(EFI_HANDLE image)
{
EFI_GUID fsGuid = EFI_SIMPLE_FILE_SYSTEM_PROTOCOL_GUID;
EFI_GUID lipGuid = EFI_LOADED_IMAGE_PROTOCOL_GUID;
EFI_LOADED_IMAGE *loaded_image = NULL;
EFI_FILE_IO_INTERFACE *IOVolume;
EFI_FILE_HANDLE Volume;
EFI_STATUS status;
status = uefi_call_wrapper(BS->HandleProtocol, 3,
image, &lipGuid, (void **) &loaded_image);
if (status != EFI_SUCCESS)
panic();
status = uefi_call_wrapper(BS->HandleProtocol, 3,
loaded_image->DeviceHandle,
&fsGuid, (VOID*)&IOVolume);
if (status != EFI_SUCCESS)
panic();
status = uefi_call_wrapper(IOVolume->OpenVolume, 2, IOVolume, &Volume);
if (status != EFI_SUCCESS)
panic();
return Volume;
}
static EFI_FILE_HANDLE openFile(CHAR16 *file, EFI_FILE_HANDLE volume)
{
EFI_FILE_HANDLE file_handle;
EFI_STATUS status;
status = uefi_call_wrapper(volume->Open, 5,
volume,
&file_handle,
file,
EFI_FILE_MODE_READ,
EFI_FILE_READ_ONLY | EFI_FILE_HIDDEN | EFI_FILE_SYSTEM);
if (status != EFI_SUCCESS)
file_handle = NULL;
return file_handle;
}
static int open_kernel_image(EFI_FILE_HANDLE vol, CHAR16 *filename,
EFI_PHYSICAL_ADDRESS *_addr, uint32_t *sz)
{
EFI_FILE_HANDLE file;
EFI_STATUS status;
file = openFile(filename, vol);
if (file == NULL)
return -1;
*sz = FileSize(file);
wolfBoot_printf("Opening file: %s, size: %u\n", filename, *sz);
status = uefi_call_wrapper(BS->AllocatePages,
4,
AllocateAnyPages,
EfiLoaderData,
(*sz/PAGE_SIZE) + 1, _addr);
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't get memory at specified address %d\n", status);
return status;
}
status = uefi_call_wrapper(file->Read, 3, file, sz, *_addr);
if (status != EFI_SUCCESS) {
wolfBoot_printf("can't read kernel image %d\n", status);
return status;
}
if (*sz < IMAGE_HEADER_SIZE) {
wolfBoot_printf("Image smaller than the header\n");
return -1;
}
return 0;
}
EFI_STATUS
EFIAPI
efi_main (EFI_HANDLE ImageHandle, EFI_SYSTEM_TABLE *SystemTable)
{
CHAR16 *kernel_filename = L"kernel.img";
CHAR16 *update_filename = L"update.img";
EFI_LOADED_IMAGE *loaded_image = NULL;
EFI_FILE_HANDLE vol;
EFI_STATUS status;
uint8_t *mem;
UINT64 size;
UINT64 r;
uint32_t kernel_size, update_size;
InitializeLib(ImageHandle, SystemTable);
gSystemTable = SystemTable;
gImageHandle = ImageHandle;
status = uefi_call_wrapper(SystemTable->BootServices->HandleProtocol,
3,
ImageHandle,
&LoadedImageProtocol,
(void **)&loaded_image);
if (status == EFI_SUCCESS)
wolfBoot_printf("Image base: 0x%lx\n", loaded_image->ImageBase);
vol = GetVolume(ImageHandle);
open_kernel_image(vol, kernel_filename, &kernel_addr, &kernel_size);
open_kernel_image(vol, update_filename, &update_addr, &update_size);
if (kernel_addr == 0 && update_addr == 0) {
wolfBoot_printf("No image to load\n");
panic();
}
wolfBoot_start();
return EFI_SUCCESS;
}
#endif /* PLATFORM_X86_64_EFI */

View File

@ -0,0 +1 @@
# efi target uses the linker script provided by gnu-efi. This is an empty file to appease Makefile.

View File

@ -28,11 +28,18 @@
# define PRINTF_ENABLED
#endif
#if defined(WOLFBOOT_DEBUG_EFI) && !defined(PRINTF_ENABLED)
# define PRINTF_ENABLED
#endif
#ifdef PRINTF_ENABLED
# include <stdio.h>
# if defined(DEBUG_ZYNQ) && !defined(USE_QNX)
# include "xil_printf.h"
# define wolfBoot_printf(_f_, ...) xil_printf(_f_, ##__VA_ARGS__)
# elif defined(WOLFBOOT_DEBUG_EFI)
/* NOTE: %s arguments will not work as EFI uses widechar string */
# define wolfBoot_printf(_f_, ...) Print(L##_f_, ##__VA_ARGS__)
# else
# define wolfBoot_printf(_f_, ...) printf(_f_, ##__VA_ARGS__)
# endif

View File

@ -27,16 +27,27 @@
#ifndef H_TARGETS_TARGET_
#define H_TARGETS_TARGET_
#define WOLFBOOT_SECTOR_SIZE ##WOLFBOOT_SECTOR_SIZE##
#define WOLFBOOT_PARTITION_BOOT_ADDRESS ##WOLFBOOT_PARTITION_BOOT_ADDRESS##
#define WOLFBOOT_PARTITION_SIZE ##WOLFBOOT_PARTITION_SIZE##
#define WOLFBOOT_PARTITION_UPDATE_ADDRESS ##WOLFBOOT_PARTITION_UPDATE_ADDRESS##
#define WOLFBOOT_PARTITION_SWAP_ADDRESS ##WOLFBOOT_PARTITION_SWAP_ADDRESS##
#ifndef PLATFORM_X86_64_EFI
#define WOLFBOOT_SECTOR_SIZE ##WOLFBOOT_SECTOR_SIZE##
#define WOLFBOOT_PARTITION_BOOT_ADDRESS ##WOLFBOOT_PARTITION_BOOT_ADDRESS##
#define WOLFBOOT_PARTITION_SIZE ##WOLFBOOT_PARTITION_SIZE##
#define WOLFBOOT_PARTITION_UPDATE_ADDRESS ##WOLFBOOT_PARTITION_UPDATE_ADDRESS##
#define WOLFBOOT_PARTITION_SWAP_ADDRESS ##WOLFBOOT_PARTITION_SWAP_ADDRESS##
/* Load address in RAM for staged OS (update_ram only) */
#define WOLFBOOT_DTS_BOOT_ADDRESS ##WOLFBOOT_DTS_BOOT_ADDRESS##
#define WOLFBOOT_DTS_UPDATE_ADDRESS ##WOLFBOOT_DTS_UPDATE_ADDRESS##
#define WOLFBOOT_LOAD_ADDRESS ##WOLFBOOT_LOAD_ADDRESS##
#define WOLFBOOT_LOAD_DTS_ADDRESS ##WOLFBOOT_LOAD_DTS_ADDRESS##
/* Load address in RAM for staged OS (update_ram only) */
#define WOLFBOOT_DTS_BOOT_ADDRESS ##WOLFBOOT_DTS_BOOT_ADDRESS##
#define WOLFBOOT_DTS_UPDATE_ADDRESS ##WOLFBOOT_DTS_UPDATE_ADDRESS##
#define WOLFBOOT_LOAD_ADDRESS ##WOLFBOOT_LOAD_ADDRESS##
#define WOLFBOOT_LOAD_DTS_ADDRESS ##WOLFBOOT_LOAD_DTS_ADDRESS##
#else
#include "efi/efi.h"
extern EFI_PHYSICAL_ADDRESS kernel_addr;
extern EFI_PHYSICAL_ADDRESS update_addr;
#define WOLFBOOT_PARTITION_BOOT_ADDRESS (kernel_addr)
#define WOLFBOOT_PARTITION_UPDATE_ADDRESS (update_addr)
#define WOLFBOOT_PARTITION_SWAP_ADDRESS 0
#define WOLFBOOT_SECTOR_SIZE 0x1000
#define WOLFBOOT_PARTITION_SIZE (2 * 1024 * 1024 * 1024ULL)
#endif
#endif /* !H_TARGETS_TARGET_ */

View File

@ -185,7 +185,7 @@ endif
ifeq ($(DEBUG),1)
CFLAGS+=-O0 -g -ggdb3 -D"DEBUG=1"
CFLAGS+=-O0 -g -ggdb3
else
ifeq ($(OPTIMIZATION_LEVEL),)
CFLAGS+=-Os
@ -247,6 +247,9 @@ ifeq ($(WOLFTPM),1)
endif
WOLFCRYPT_OBJS+=./lib/wolfssl/wolfcrypt/src/aes.o
WOLFCRYPT_OBJS+=./lib/wolfssl/wolfcrypt/src/hmac.o
ifeq ($(DEBUG),1)
CFLAGS+=-DWOLFBOOT_DEBUG_TPM=1
endif
endif
## Hash settings

48
src/boot_x86_64.c 100644
View File

@ -0,0 +1,48 @@
/* boot_x86_64.c
*
* Copyright (C) 2021 wolfSSL Inc.
*
* This file is part of wolfBoot.
*
* wolfBoot is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* wolfBoot is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1335, USA
*/
#include <stdint.h>
#include "image.h"
#include "loader.h"
#include "wolfboot/wolfboot.h"
#ifdef PLATFORM_X86_64_EFI
#include <efi/efi.h>
#include <efi/efilib.h>
extern unsigned int __bss_start__;
extern unsigned int __bss_end__;
static volatile unsigned int cpu_id;
extern unsigned int *END_STACK;
extern void RAMFUNCTION x86_64_efi_do_boot(uint8_t *kernel);
#ifdef MMU
void RAMFUNCTION do_boot(const uint32_t *app_offset, const uint32_t* dts_offset)
#else
void RAMFUNCTION do_boot(const uint32_t *app_offset)
#endif
{
x86_64_efi_do_boot((uint8_t *)app_offset);
}
#endif /* PLATFORM_X86_64_EFI */

View File

@ -69,7 +69,7 @@ static int wolfBoot_verify_signature(uint8_t *hash, uint8_t *sig)
int ret, verify_res = 0;
#ifdef WOLFBOOT_TPM
WOLFTPM2_KEY tpmKey;
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
const char* errStr;
#endif
@ -87,7 +87,7 @@ static int wolfBoot_verify_signature(uint8_t *hash, uint8_t *sig)
verify_res = 1; /* TPM does hash verify compare */
}
else {
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
/* retrieve error string (for debugging) */
errStr = wolfTPM2_GetRCString(ret);
(void)errStr;
@ -212,7 +212,7 @@ static int wolfBoot_verify_signature(uint8_t *hash, uint8_t *sig)
WOLFTPM2_KEY tpmKey;
const byte *n = NULL, *e = NULL;
word32 nSz = 0, eSz = 0, inOutIdx = 0;
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
const char* errStr;
#endif
@ -226,7 +226,7 @@ static int wolfBoot_verify_signature(uint8_t *hash, uint8_t *sig)
ret = wolfTPM2_LoadRsaPublicKey_ex(&wolftpm_dev, &tpmKey, n, nSz,
*((word32*)e), TPM_ALG_NULL, TPM_ALG_SHA256);
if (ret != 0) {
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
/* retrieve error string (for debugging) */
errStr = wolfTPM2_GetRCString(ret);
(void)errStr;
@ -240,7 +240,7 @@ static int wolfBoot_verify_signature(uint8_t *hash, uint8_t *sig)
sig, IMAGE_SIGNATURE_SIZE,
output, &output_sz);
if (ret != 0) {
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
/* retrieve error string (for debugging) */
errStr = wolfTPM2_GetRCString(ret);
(void)errStr;
@ -564,7 +564,7 @@ static int measure_boot(uint8_t *hash)
{
int rc = -1;
PCR_Extend_In pcrExtend;
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
PCR_Read_In pcrReadCmd;
PCR_Read_Out pcrReadResp;
#endif
@ -580,7 +580,7 @@ static int measure_boot(uint8_t *hash)
rc = 0;
}
#ifdef DEBUG
#ifdef WOLFBOOT_DEBUG_TPM
/* Test prcRead helps debug TPM communication and print PCR value in gdb */
XMEMSET(&pcrReadCmd, 0, sizeof(pcrReadCmd));
TPM2_SetupPCRSel(&pcrReadCmd.pcrSelectionIn, TPM_ALG_SHA256,

View File

@ -646,7 +646,8 @@ uint16_t wolfBoot_get_image_type(uint8_t part)
return 0;
}
#if defined(ARCH_AARCH64) || defined(DUALBANK_SWAP)
#if defined(ARCH_AARCH64) || defined(DUALBANK_SWAP) || defined(PLATFORM_X86_64_EFI)
int wolfBoot_fallback_is_possible(void)
{
uint32_t boot_v, update_v;

View File

@ -51,7 +51,7 @@ int isalpha(int c)
return (isupper(c) || islower(c));
}
#ifndef __IAR_SYSTEMS_ICC__
#if !defined(__IAR_SYSTEMS_ICC__) && !defined(PLATFORM_X86_64_EFI)
void *memset(void *s, int c, size_t n)
{
unsigned char *d = (unsigned char *)s;
@ -168,7 +168,7 @@ int strncmp(const char *s1, const char *s2, size_t n)
return diff;
}
#ifndef __IAR_SYSTEMS_ICC__
#if !defined(__IAR_SYSTEMS_ICC__) && !defined(PLATFORM_X86_64_EFI)
void *memcpy(void *dst, const void *src, size_t n)
{
size_t i;

View File

@ -30,6 +30,13 @@
#include "wolfboot/wolfboot.h"
#include <string.h>
#ifdef PLATFORM_X86_64_EFI
#include "efi/efi.h"
#include "efi/efilib.h"
extern EFI_PHYSICAL_ADDRESS kernel_addr;
extern EFI_PHYSICAL_ADDRESS update_addr;
#endif
extern void hal_flash_dualbank_swap(void);
static inline void boot_panic(void)
@ -42,7 +49,12 @@ void RAMFUNCTION wolfBoot_start(void)
{
int active, ret = 0;
struct wolfBoot_image os_image;
#ifdef PLATFORM_X86_64_EFI
uint32_t* load_address = (uint32_t*)kernel_addr;
#else
uint32_t* load_address = (uint32_t*)WOLFBOOT_LOAD_ADDRESS;
#endif
uint8_t* image_ptr;
uint8_t p_state;
#ifdef MMU
@ -56,6 +68,11 @@ void RAMFUNCTION wolfBoot_start(void)
if (active < 0) /* panic if no images available */
boot_panic();
#ifdef PLATFORM_X86_64_EFI
if (active == 1)
load_address = (uint32_t *)update_addr;
#endif
/* Check current status for failure (image still in TESTING), and fall-back
* if an alternative is available
*/
@ -143,11 +160,14 @@ void RAMFUNCTION wolfBoot_start(void)
}
#endif
hal_prepare_boot();
wolfBoot_printf("Booting at %08lx\n", load_address);
hal_prepare_boot();
#ifdef MMU
#ifdef PLATFORM_X86_64_EFI
extern void x86_64_efi_do_boot(uint8_t *);
x86_64_efi_do_boot((uint8_t*)load_address);
#elif defined MMU
do_boot((uint32_t*)load_address, (uint32_t*)dts_address);
#else
do_boot((uint32_t*)load_address);

View File

View File

@ -0,0 +1,14 @@
BR2_x86_64=y
BR2_x86_corei7=y
# BR2_STRIP_strip is not set
# BR2_COMPILER_PARANOID_UNSAFE_PATH is not set
BR2_TOOLCHAIN_EXTERNAL=y
# BR2_TARGET_GENERIC_REMOUNT_ROOTFS_RW is not set
# BR2_ENABLE_LOCALE_PURGE is not set
BR2_LINUX_KERNEL=y
BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG=y
BR2_LINUX_KERNEL_CUSTOM_CONFIG_FILE="$(BR2_EXTERNAL_TINY_PATH)/linux.config"
# BR2_PACKAGE_IFUPDOWN_SCRIPTS is not set
# BR2_PACKAGE_URANDOM_SCRIPTS is not set
BR2_TARGET_ROOTFS_INITRAMFS=y
# BR2_TARGET_ROOTFS_TAR is not set

View File

@ -0,0 +1,2 @@
name: TINY
desc: configuration for building a tiny kernel+initramfs image

View File

View File

@ -0,0 +1,31 @@
CONFIG_BLK_DEV_INITRD=y
CONFIG_INITRAMFS_SOURCE="${BR_BINARIES_DIR}/rootfs.cpio"
CONFIG_EXPERT=y
CONFIG_EFI=y
CONFIG_EFI_STUB=y
CONFIG_CMDLINE_BOOL=y
CONFIG_CMDLINE="console=ttyS0"
# CONFIG_EFI_CUSTOM_SSDT_OVERLAYS is not set
# CONFIG_GCC_PLUGINS is not set
# CONFIG_BLOCK is not set
CONFIG_PCI=y
CONFIG_PCIEPORTBUS=y
CONFIG_DEVTMPFS=y
CONFIG_DEVTMPFS_MOUNT=y
CONFIG_SERIAL_8250=y
CONFIG_SERIAL_8250_CONSOLE=y
CONFIG_TTY_PRINTK=y
CONFIG_TCG_TPM=y
CONFIG_TCG_TIS=y
CONFIG_TCG_TIS_SPI=y
CONFIG_TCG_TIS_SPI_CR50=y
CONFIG_TCG_NSC=y
CONFIG_TCG_ATMEL=y
CONFIG_TCG_INFINEON=y
CONFIG_TCG_CRB=y
CONFIG_TCG_VTPM_PROXY=y
CONFIG_TCG_TIS_ST33ZP24_SPI=y
CONFIG_SPI=y
# CONFIG_SECURITYFS is not set
CONFIG_CRYPTO_SHA1=y
CONFIG_UNWINDER_GUESS=y

View File

@ -0,0 +1,35 @@
#!/bin/sh
WORK_DIR=/tmp/wolfBoot_efi
BR_VER=2021.08.2
BR_DIR=buildroot-$BR_VER
IMAGE_DIR=$WORK_DIR/output
if (test ! -d $WORK_DIR);then
mkdir -p $WORK_DIR
fi
if (test ! -d $WORK_DIR/$BR_DIR);then
curl https://buildroot.org/downloads/$BR_DIR.tar.gz -o $WORK_DIR/$BR_DIR.tar.gz
tar xvf $WORK_DIR/$BR_DIR.tar.gz -C $WORK_DIR
fi
BR2_EXTERNAL=$(pwd)/tools/efi/br_ext_dir make -C $WORK_DIR/$BR_DIR tiny_defconfig O=$IMAGE_DIR
make -C $WORK_DIR/$BR_DIR O=$IMAGE_DIR
SIGN_TOOL="python3 ./tools/keytools/sign.py"
if [ -f "./tools/keytools/sign" ]; then
SIGN_TOOL="./tools/keytools/sign"
fi
$SIGN_TOOL --ed25519 $IMAGE_DIR/images/bzImage ed25519.der 1
$SIGN_TOOL --ed25519 $IMAGE_DIR/images/bzImage ed25519.der 2
mkdir -p /tmp/efi
sudo mount /tmp/efi.disk /tmp/efi
sudo cp $IMAGE_DIR/images/bzImage_v1_signed.bin /tmp/efi/kernel.img
sudo cp $IMAGE_DIR/images/bzImage_v2_signed.bin /tmp/efi/update.img
sudo cp wolfboot.efi /tmp/efi
sudo umount /tmp/efi

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,14 @@
#!/bin/sh
dd if=/dev/zero of=/tmp/efi.disk bs=256M count=1
sudo mkfs.vfat /tmp/efi.disk
mkdir -p /tmp/efi
sudo mount /tmp/efi.disk /tmp/efi -oloop
cat <<EOF > /tmp/startup.nsh
@echo -off
echo Starting wolfBoot EFI...
fs0:
wolfboot.efi
EOF
sudo mv /tmp/startup.nsh /tmp/efi/ 2>/dev/null
sudo umount /tmp/efi

View File

@ -0,0 +1,50 @@
#!/bin/sh
## TPM emulator:
# https://github.com/stefanberger/swtpm
if (test -z $OVMF_PATH); then
if (test -f /usr/share/edk2-ovmf/x64/OVMF.fd); then
OVMF_PATH=/usr/share/edk2-ovmf/x64
elif (test -f /usr/share/qemu/OVMF.fd); then
OVMF_PATH=/usr/share/qemu
else
OVMF_PATH=/
fi
fi
QEMU_OPTIONS=" \
-m 256M \
-net none \
-bios ${OVMF_PATH}/OVMF.fd \
-drive file=/tmp/efi.disk,index=0,media=disk,format=raw \
-vga none \
-serial stdio \
-display none"
QEMU_TPM_OPTIONS=" \
-chardev socket,id=chrtpm,path=/tmp/swtpm/swtpm-sock \
-tpmdev emulator,id=tpm0,chardev=chrtpm \
-device tpm-tis,tpmdev=tpm0"
if (which swtpm); then
killall swtpm
sleep 1
QEMU_EXTRA=$QEMU_TPM_OPTIONS
echo TPM Emulation ON
mkdir -p /tmp/swtpm
swtpm socket --tpm2 --tpmstate dir=/tmp/swtpm \
--ctrl type=unixio,path=/tmp/swtpm/swtpm-sock --log level=20 &
else
echo TPM Emulation OFF
fi
mkdir -p /tmp/efi
sudo mount /tmp/efi.disk /tmp/efi
sudo cp wolfboot.efi /tmp/efi
sudo umount /tmp/efi
echo $QEMU_OPTIONS $QEMU_EXTRA
qemu-system-x86_64 $QEMU_OPTIONS $QEMU_EXTRA