mirror of
https://github.com/trezor/trezor-firmware.git
synced 2026-02-20 00:33:30 +01:00
refactor(core): remove coreapp specific logic from applets
[no changelog]
This commit is contained in:
@@ -17,6 +17,7 @@
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include <trezor_model.h>
|
||||
#include <trezor_rtl.h>
|
||||
|
||||
#include <gfx/gfx_bitblt.h>
|
||||
@@ -24,8 +25,8 @@
|
||||
#include <sec/random_delays.h>
|
||||
#include <sec/secret.h>
|
||||
#include <sec/secure_aes.h>
|
||||
#include <sys/applet.h>
|
||||
#include <sys/bootutils.h>
|
||||
#include <sys/coreapp.h>
|
||||
#include <sys/mpu.h>
|
||||
#include <sys/syscall_ipc.h>
|
||||
#include <sys/sysevent.h>
|
||||
@@ -33,7 +34,6 @@
|
||||
#include <sys/systick.h>
|
||||
#include <util/board_capabilities.h>
|
||||
#include <util/boot_image.h>
|
||||
#include <util/image.h>
|
||||
#include <util/option_bytes.h>
|
||||
#include <util/rsod.h>
|
||||
#include <util/unit_properties.h>
|
||||
@@ -54,6 +54,10 @@
|
||||
#include <io/haptic.h>
|
||||
#endif
|
||||
|
||||
#ifdef USE_HASH_PROCESSOR
|
||||
#include <sec/hash_processor.h>
|
||||
#endif
|
||||
|
||||
#ifdef USE_OPTIGA
|
||||
#include <sec/optiga_init.h>
|
||||
#endif
|
||||
@@ -212,42 +216,6 @@ static void kernel_loop(applet_t *coreapp) {
|
||||
} while (applet_is_alive(coreapp));
|
||||
}
|
||||
|
||||
// defined in linker script
|
||||
extern uint32_t _kernel_flash_end;
|
||||
#define KERNEL_END COREAPP_CODE_ALIGN((uint32_t) & _kernel_flash_end)
|
||||
|
||||
// Initializes coreapp applet
|
||||
static void coreapp_init(applet_t *applet) {
|
||||
const uint32_t CODE1_START = KERNEL_END;
|
||||
|
||||
#ifdef FIRMWARE_P1_START
|
||||
const uint32_t CODE1_END = FIRMWARE_P1_START + FIRMWARE_P1_MAXSIZE;
|
||||
#else
|
||||
const uint32_t CODE1_END = FIRMWARE_START + FIRMWARE_MAXSIZE;
|
||||
#endif
|
||||
|
||||
const applet_layout_t coreapp_layout = {
|
||||
.data1.start = (uint32_t)AUX1_RAM_START,
|
||||
.data1.size = (uint32_t)AUX1_RAM_SIZE,
|
||||
#ifdef AUX2_RAM_START
|
||||
.data2.start = (uint32_t)AUX2_RAM_START,
|
||||
.data2.size = (uint32_t)AUX2_RAM_SIZE,
|
||||
#endif
|
||||
.code1.start = CODE1_START,
|
||||
.code1.size = CODE1_END - CODE1_START,
|
||||
#ifdef FIRMWARE_P2_START
|
||||
.code2.start = FIRMWARE_P2_START,
|
||||
.code2.size = FIRMWARE_P2_MAXSIZE,
|
||||
#endif
|
||||
};
|
||||
|
||||
applet_privileges_t coreapp_privileges = {
|
||||
.assets_area_access = true,
|
||||
};
|
||||
|
||||
applet_init(applet, &coreapp_layout, &coreapp_privileges);
|
||||
}
|
||||
|
||||
#ifndef USE_BOOTARGS_RSOD
|
||||
|
||||
// Shows RSOD (Red Screen of Death)
|
||||
@@ -257,7 +225,7 @@ static void show_rsod(const systask_postmortem_t *pminfo) {
|
||||
coreapp_init(&coreapp);
|
||||
|
||||
// Reset and run the coreapp in RSOD mode
|
||||
if (applet_reset(&coreapp, 1, pminfo, sizeof(systask_postmortem_t))) {
|
||||
if (coreapp_reset(&coreapp, 1, pminfo, sizeof(systask_postmortem_t))) {
|
||||
// Run the applet & wait for it to finish
|
||||
applet_run(&coreapp);
|
||||
// Loop until the coreapp is terminated
|
||||
@@ -320,12 +288,13 @@ int main(void) {
|
||||
coreapp_init(&coreapp);
|
||||
|
||||
// Reset and run the coreapp
|
||||
if (!applet_reset(&coreapp, 0, NULL, 0)) {
|
||||
if (!coreapp_reset(&coreapp, 0, NULL, 0)) {
|
||||
error_shutdown("Cannot start coreapp");
|
||||
}
|
||||
|
||||
// Run the applet
|
||||
applet_run(&coreapp);
|
||||
|
||||
// Loop until the coreapp is terminated
|
||||
kernel_loop(&coreapp);
|
||||
// Release the coreapp resources
|
||||
|
||||
@@ -110,6 +110,7 @@ __attribute((no_stack_protector)) void saes_unpriv_callback(void) {
|
||||
|
||||
#ifdef KERNEL
|
||||
|
||||
#include <sys/coreapp.h>
|
||||
#include <sys/mpu.h>
|
||||
#include <sys/systask.h>
|
||||
|
||||
@@ -144,11 +145,12 @@ secbool secure_aes_unpriv_encrypt(const uint8_t *input, size_t size,
|
||||
|
||||
applet_t *applet = secure_aes_unpriv_applet;
|
||||
|
||||
const applet_header_t *header = (applet_header_t *)applet->layout.code1.start;
|
||||
const coreapp_header_t *header =
|
||||
(coreapp_header_t *)applet->layout.code1.start;
|
||||
|
||||
void *unpriv_input = header->coreapp.saes_input;
|
||||
void *unpriv_output = header->coreapp.saes_output;
|
||||
void *unpriv_callback = header->coreapp.saes_callback;
|
||||
void *unpriv_input = header->saes_input;
|
||||
void *unpriv_output = header->saes_output;
|
||||
void *unpriv_callback = header->saes_callback;
|
||||
|
||||
memzero(unpriv_input, SAES_DATA_SIZE_WITH_UNPRIV_KEY);
|
||||
memzero(unpriv_output, SAES_DATA_SIZE_WITH_UNPRIV_KEY);
|
||||
|
||||
@@ -25,28 +25,6 @@
|
||||
|
||||
#include <sys/systask.h>
|
||||
|
||||
// Applet entry point
|
||||
typedef void (*applet_startup_t)(const char* args, uint32_t random);
|
||||
|
||||
// Applet header found at the beginning of the applet binary
|
||||
typedef struct {
|
||||
// Applet entry point
|
||||
applet_startup_t startup;
|
||||
// Stack area
|
||||
mpu_area_t stack;
|
||||
// TLS area
|
||||
mpu_area_t tls;
|
||||
// Coreapp specific data
|
||||
struct {
|
||||
// Unprivileged SAES input buffer
|
||||
void* saes_input;
|
||||
// Unprivileged SAES output buffer
|
||||
void* saes_output;
|
||||
// Unprivileged SAES callback
|
||||
void* saes_callback;
|
||||
} coreapp;
|
||||
} applet_header_t;
|
||||
|
||||
// Applet privileges
|
||||
typedef struct {
|
||||
bool assets_area_access;
|
||||
@@ -68,15 +46,6 @@ typedef struct {
|
||||
void applet_init(applet_t* applet, const applet_layout_t* layout,
|
||||
const applet_privileges_t* privileges);
|
||||
|
||||
// Resets the applet and prepares it for execution from its entry point.
|
||||
//
|
||||
// Applet does not start immediately, it needs to be run by
|
||||
// `applet_run()` after calling this function.
|
||||
//
|
||||
// Returns `true` if the applet was successfully reset.
|
||||
bool applet_reset(applet_t* applet, uint32_t cmd, const void* arg,
|
||||
size_t arg_size);
|
||||
|
||||
// Runs the applet and waits until it finishes.
|
||||
void applet_run(applet_t* applet);
|
||||
|
||||
|
||||
64
core/embed/sys/task/inc/sys/coreapp.h
Normal file
64
core/embed/sys/task/inc/sys/coreapp.h
Normal file
@@ -0,0 +1,64 @@
|
||||
/*
|
||||
* This file is part of the Trezor project, https://trezor.io/
|
||||
*
|
||||
* Copyright (c) SatoshiLabs
|
||||
*
|
||||
* This program 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 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program 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, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifdef KERNEL_MODE
|
||||
|
||||
#include <trezor_types.h>
|
||||
|
||||
#include <sys/applet.h>
|
||||
#include <sys/mpu.h>
|
||||
|
||||
// Coreapp entry point
|
||||
typedef void (*coreapp_startup_t)(const char* args, uint32_t random);
|
||||
|
||||
// Applet header found at the beginning of the coreapp binary
|
||||
typedef struct {
|
||||
// Applet entry point
|
||||
coreapp_startup_t startup;
|
||||
// Stack area
|
||||
mpu_area_t stack;
|
||||
// TLS area
|
||||
mpu_area_t tls;
|
||||
// Unprivileged SAES input buffer
|
||||
void* saes_input;
|
||||
// Unprivileged SAES output buffer
|
||||
void* saes_output;
|
||||
// Unprivileged SAES callback
|
||||
void* saes_callback;
|
||||
} coreapp_header_t;
|
||||
|
||||
// Initializes the coreapp applet structure
|
||||
void coreapp_init(applet_t* applet);
|
||||
|
||||
// Resets the coreapp and prepares it for execution from its entry point.
|
||||
//
|
||||
// Coreapp does not start immediately, it needs to be run by
|
||||
// `applet_run()` after calling this function.
|
||||
//
|
||||
// Returns `true` if the applet was successfully reset.
|
||||
bool coreapp_reset(applet_t* applet, uint32_t cmd, const void* arg,
|
||||
size_t arg_size);
|
||||
|
||||
mpu_area_t coreapp_get_code_area(void);
|
||||
|
||||
mpu_area_t coreapp_get_tls_area(void);
|
||||
|
||||
#endif // KERNEL_MODE
|
||||
@@ -40,47 +40,6 @@ void applet_init(applet_t* applet, const applet_layout_t* layout,
|
||||
applet->privileges = *privileges;
|
||||
}
|
||||
|
||||
static void applet_clear_memory(applet_t* applet) {
|
||||
mpu_set_active_applet(&applet->layout);
|
||||
|
||||
if (applet->layout.data1.size > 0) {
|
||||
memset((void*)applet->layout.data1.start, 0, applet->layout.data1.size);
|
||||
}
|
||||
if (applet->layout.data2.size > 0) {
|
||||
memset((void*)applet->layout.data2.start, 0, applet->layout.data2.size);
|
||||
}
|
||||
}
|
||||
|
||||
bool applet_reset(applet_t* applet, uint32_t cmd, const void* arg,
|
||||
size_t arg_size) {
|
||||
// Clear all memory the applet is allowed to use
|
||||
applet_clear_memory(applet);
|
||||
|
||||
const applet_header_t* header = (applet_header_t*)applet->layout.code1.start;
|
||||
|
||||
// Reset the applet task (stack pointer, etc.)
|
||||
if (!systask_init(&applet->task, header->stack.start, header->stack.size, 0,
|
||||
applet)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Copy the arguments onto the applet stack
|
||||
void* arg_copy = NULL;
|
||||
if (arg != NULL && arg_size > 0) {
|
||||
arg_copy = systask_push_data(&applet->task, arg, arg_size);
|
||||
if (arg_copy == NULL) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Schedule the applet task run
|
||||
uint32_t arg1 = cmd;
|
||||
uint32_t arg2 = (uint32_t)arg_copy;
|
||||
uint32_t arg3 = rng_get();
|
||||
|
||||
return systask_push_call(&applet->task, header->startup, arg1, arg2, arg3);
|
||||
}
|
||||
|
||||
#ifdef USE_TRUSTZONE
|
||||
// Sets unprivileged access to the applet memory regions
|
||||
// and allows applet to use some specific peripherals.
|
||||
|
||||
124
core/embed/sys/task/stm32/coreapp.c
Normal file
124
core/embed/sys/task/stm32/coreapp.c
Normal file
@@ -0,0 +1,124 @@
|
||||
/*
|
||||
* This file is part of the Trezor project, https://trezor.io/
|
||||
*
|
||||
* Copyright (c) SatoshiLabs
|
||||
*
|
||||
* This program 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 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program 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, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifdef KERNEL
|
||||
|
||||
#include <trezor_rtl.h>
|
||||
|
||||
#include <sec/rng.h>
|
||||
#include <sys/applet.h>
|
||||
#include <sys/coreapp.h>
|
||||
#include <sys/mpu.h>
|
||||
#include <sys/systask.h>
|
||||
#include <util/image.h>
|
||||
|
||||
static mpu_area_t coreapp_code_area;
|
||||
static mpu_area_t coreapp_tls_area;
|
||||
|
||||
// defined in linker script
|
||||
extern uint32_t _kernel_flash_end;
|
||||
#define KERNEL_END COREAPP_CODE_ALIGN((uint32_t) & _kernel_flash_end)
|
||||
|
||||
// Initializes coreapp applet
|
||||
void coreapp_init(applet_t* applet) {
|
||||
const uint32_t CODE1_START = KERNEL_END;
|
||||
|
||||
#ifdef FIRMWARE_P1_START
|
||||
const uint32_t CODE1_END = FIRMWARE_P1_START + FIRMWARE_P1_MAXSIZE;
|
||||
#else
|
||||
const uint32_t CODE1_END = FIRMWARE_START + FIRMWARE_MAXSIZE;
|
||||
#endif
|
||||
|
||||
const applet_layout_t coreapp_layout = {
|
||||
.data1.start = (uint32_t)AUX1_RAM_START,
|
||||
.data1.size = (uint32_t)AUX1_RAM_SIZE,
|
||||
#ifdef AUX2_RAM_START
|
||||
.data2.start = (uint32_t)AUX2_RAM_START,
|
||||
.data2.size = (uint32_t)AUX2_RAM_SIZE,
|
||||
#endif
|
||||
.code1.start = CODE1_START,
|
||||
.code1.size = CODE1_END - CODE1_START,
|
||||
#ifdef FIRMWARE_P2_START
|
||||
.code2.start = FIRMWARE_P2_START,
|
||||
.code2.size = FIRMWARE_P2_MAXSIZE,
|
||||
#endif
|
||||
};
|
||||
|
||||
applet_privileges_t coreapp_privileges = {
|
||||
.assets_area_access = true,
|
||||
};
|
||||
|
||||
applet_init(applet, &coreapp_layout, &coreapp_privileges);
|
||||
}
|
||||
|
||||
static void coreapp_clear_memory(applet_t* applet) {
|
||||
if (applet->layout.data1.size > 0) {
|
||||
memset((void*)applet->layout.data1.start, 0, applet->layout.data1.size);
|
||||
}
|
||||
if (applet->layout.data2.size > 0) {
|
||||
memset((void*)applet->layout.data2.start, 0, applet->layout.data2.size);
|
||||
}
|
||||
}
|
||||
|
||||
bool coreapp_reset(applet_t* applet, uint32_t cmd, const void* arg,
|
||||
size_t arg_size) {
|
||||
// Enable access to coreapp memory regions
|
||||
mpu_set_active_applet(&applet->layout);
|
||||
|
||||
// Clear all memory the applet is allowed to use
|
||||
coreapp_clear_memory(applet);
|
||||
|
||||
const coreapp_header_t* header =
|
||||
(coreapp_header_t*)applet->layout.code1.start;
|
||||
|
||||
// Remember code and TLS areas
|
||||
// (we will need then later for extension applets)
|
||||
coreapp_tls_area = header->tls;
|
||||
coreapp_code_area = applet->layout.code1;
|
||||
|
||||
// Reset the applet task (stack pointer, etc.)
|
||||
if (!systask_init(&applet->task, header->stack.start, header->stack.size, 0,
|
||||
applet)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
systask_enable_tls(&applet->task, header->tls);
|
||||
|
||||
// Copy the arguments onto the applet stack
|
||||
void* arg_copy = NULL;
|
||||
if (arg != NULL && arg_size > 0) {
|
||||
arg_copy = systask_push_data(&applet->task, arg, arg_size);
|
||||
if (arg_copy == NULL) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// Schedule the applet task run
|
||||
uint32_t arg1 = cmd;
|
||||
uint32_t arg2 = (uint32_t)arg_copy;
|
||||
uint32_t arg3 = rng_get();
|
||||
|
||||
return systask_push_call(&applet->task, header->startup, arg1, arg2, arg3);
|
||||
}
|
||||
|
||||
mpu_area_t coreapp_get_code_area(void) { return coreapp_code_area; }
|
||||
|
||||
mpu_area_t coreapp_get_tls_area(void) { return coreapp_tls_area; }
|
||||
|
||||
#endif // KERNEL
|
||||
@@ -91,6 +91,7 @@ def stm32f4_common_files(env, features_wanted, defines, sources, paths):
|
||||
"embed/sys/syscall/stm32/syscall_stubs.c",
|
||||
"embed/sys/syscall/stm32/syscall_verifiers.c",
|
||||
"embed/sys/task/stm32/applet.c",
|
||||
"embed/sys/task/stm32/coreapp.c",
|
||||
"embed/sys/task/stm32/systask.c",
|
||||
"embed/sys/task/stm32/system.c",
|
||||
"embed/sys/time/stm32/systick.c",
|
||||
|
||||
@@ -152,6 +152,7 @@ def stm32u5_common_files(env, features_wanted, defines, sources, paths):
|
||||
|
||||
if "applet" in features_wanted:
|
||||
sources += ["embed/sys/task/stm32/applet.c"]
|
||||
sources += ["embed/sys/task/stm32/coreapp.c"]
|
||||
|
||||
if "usb" in features_wanted:
|
||||
sources += [
|
||||
|
||||
Reference in New Issue
Block a user