ra8-firmware 0.1.0
Bare-metal firmware for the Renesas RA8 family (RA8D2 / RA8P1)
Loading...
Searching...
No Matches
main.c
Go to the documentation of this file.
1
56
57#include <stddef.h>
58#include <stdint.h>
59
60#include "ra8_board_ek_ra8d2.h"
61#include "ra8_boot_entry.h"
62#include "ra8_cache.h"
63#include "ra8_cgc.h"
64#include "ra8_err.h"
65#include "ra8_log.h"
66#include "ra8_system_regs.h"
67
75typedef enum : uint32_t {
76 k_cache_mpu_baud = 115200U,
82
90typedef enum : uint8_t {
94
102typedef enum : uint8_t {
105
119
120static_assert((uint32_t)k_cache_mpu_buf_bytes >= (uint32_t)k_cache_mpu_buf_min,
121 "cacheable self-test buffer must be at least 4 KiB");
122
133alignas(32) static uint8_t s_cache_mpu_buf[k_cache_mpu_buf_bytes];
134
144 0x11111111U,
145 0x22222222U,
146 0x33333333U,
147 0x44444444U,
148};
149
159static const uint8_t k_cache_mpu_pass_banner[] = "cache_mpu_hil: cache+mpu PASS\r\n";
160
168static const uint8_t k_cache_mpu_fail_setup[] = "cache_mpu_hil: setup FAIL\r\n";
169
176static const uint8_t k_cache_mpu_fail_sram[] = "cache_mpu_hil: cacheable-SRAM FAIL\r\n";
177
184static const uint8_t k_cache_mpu_fail_mram[] = "cache_mpu_hil: MRAM-const FAIL\r\n";
185
192static const uint8_t k_cache_mpu_fail_mmio[] = "cache_mpu_hil: device-MMIO FAIL\r\n";
193
212[[noreturn]] static void cache_mpu_wfi_forever(void)
213{
214 while (1) {
215 __asm volatile("wfi");
216 }
217}
218
238[[gnu::noinline]] static uint32_t cache_mpu_mram_const_sum(void)
239{
240 const volatile uint32_t* p = k_cache_mpu_mram_table;
241 uint32_t sum = 0U;
242 for (uint8_t i = 0U; i < (uint8_t)k_cache_mpu_mram_words; i++) {
243 sum += p[i];
244 }
245 return sum;
246}
247
268{
269 for (uint32_t i = 0U; i < (uint32_t)k_cache_mpu_buf_bytes; i++) {
270 s_cache_mpu_buf[i] =
271 (uint8_t)((i * (uint32_t)k_cache_mpu_pat_mul) + (uint32_t)k_cache_mpu_pat_add);
272 }
273
274 /* Force the freshly written (dirty) lines back to SRAM and drop them, so the
275 * verify pass below must refill from memory -- the full write-back + refill
276 * round-trip with the D-cache on. */
278 (uint32_t)sizeof(s_cache_mpu_buf)) != k_ra8_ok) {
279 return false;
280 }
281
282 for (uint32_t i = 0U; i < (uint32_t)k_cache_mpu_buf_bytes; i++) {
283 const uint8_t expected =
284 (uint8_t)((i * (uint32_t)k_cache_mpu_pat_mul) + (uint32_t)k_cache_mpu_pat_add);
285 if (s_cache_mpu_buf[i] != expected) {
286 return false;
287 }
288 }
289 return true;
290}
291
313{
314 const uint32_t sum1 = cache_mpu_mram_const_sum();
315 const uint32_t sum2 = cache_mpu_mram_const_sum();
316 if (sum1 != (uint32_t)k_cache_mpu_mram_sum_exp) {
317 return false;
318 }
319 if (sum1 != sum2) {
320 return false;
321 }
322 return true;
323}
324
348{
349 /* HUM Ch 9.2.2 "SCKDIVCR : System Clock Division Control Register" p 326 */
350 const uint32_t sckdivcr = *ra8_sys_sckdivcr();
351 if (sckdivcr == 0U) {
352 return false;
353 }
354 if (sckdivcr != (uint32_t)k_cache_mpu_sckdivcr_exp) {
355 return false;
356 }
357 return true;
358}
359
393
414static bool cache_mpu_setup(void)
415{
416 if (ra8_cgc_init() != k_ra8_ok) {
417 return false;
418 }
420 return false;
421 }
422 return true;
423}
424
446static void cache_mpu_emit(const uint8_t* line, size_t len)
447{
448 if (line == nullptr) {
449 return;
450 }
451 if (len == 0U) {
452 return;
453 }
454 (void)ra8_board_uart_console_write(line, len);
456}
457
475void main(void)
476{
477 ra8_log_init();
478 ra8_log_info("CACHE_MPU", "==== cache_mpu_hil: M85 L1 cache + MPU self-test ====");
479
480 if (!cache_mpu_setup()) {
481 ra8_log_info("CACHE_MPU", "setup FAILED (CGC / console) -- halting");
484 }
485
487
488 switch (result) {
490 ra8_log_info("CACHE_MPU", "cache+mpu PASS (cacheable RW + MRAM const + Device MMIO)");
492 break;
494 ra8_log_info("CACHE_MPU", "cacheable-SRAM step FAILED");
496 break;
498 ra8_log_info("CACHE_MPU", "MRAM-const step FAILED");
500 break;
502 default:
503 ra8_log_info("CACHE_MPU", "device-MMIO step FAILED");
505 break;
506 }
507
509}
void main(void)
Secure fallback main entry point.
Definition main.c:37
static void cache_mpu_wfi_forever(void)
Park the Cortex-M85 forever in a WFI idle loop.
Definition main.c:212
cache_mpu_mram_t
Geometry of the read-only MRAM const table summed in MPU region 0.
Definition main.c:102
@ k_cache_mpu_mram_words
Number of 32-bit words in the const table.
Definition main.c:103
static bool cache_mpu_test_device_mmio(void)
Step 3 – prove Device-nGnRE peripheral MMIO is accessible (region 3).
Definition main.c:347
cache_mpu_config_t
Compile-time scalar parameters for the cache + MPU self-test.
Definition main.c:75
@ k_cache_mpu_sckdivcr_exp
SCKDIVCR readback after ra8_cgc_init().
Definition main.c:79
@ k_cache_mpu_buf_min
Self-test buffer floor (4 KiB minimum).
Definition main.c:78
@ k_cache_mpu_baud
VCOM console line rate (8N1).
Definition main.c:76
@ k_cache_mpu_mram_sum_exp
Expected sum of the MRAM const table.
Definition main.c:80
@ k_cache_mpu_buf_bytes
Cacheable self-test buffer size (>= 4 KiB).
Definition main.c:77
static const uint8_t k_cache_mpu_fail_sram[]
Failure banner: the cacheable-SRAM (region 1) readback mismatched.
Definition main.c:176
static cache_mpu_result_t cache_mpu_run_selftest(void)
Run all three self-test steps in order, naming the first failure.
Definition main.c:380
static bool cache_mpu_setup(void)
Bring up the clock tree and the VCOM console for the banner.
Definition main.c:414
static void cache_mpu_emit(const uint8_t *line, size_t len)
Emit one banner line over the VCOM console and flush it.
Definition main.c:446
cache_mpu_pattern_t
Affine byte-pattern coefficients: buf[i] = i * MUL + ADD.
Definition main.c:90
@ k_cache_mpu_pat_add
Pattern addend.
Definition main.c:92
@ k_cache_mpu_pat_mul
Pattern multiplier.
Definition main.c:91
static bool cache_mpu_test_cacheable_rw(void)
Step 1 – prove cacheable RW works in M85-private SRAM (region 1).
Definition main.c:267
cache_mpu_result_t
Verdict of the self-test, naming which step failed (if any).
Definition main.c:113
@ k_cache_mpu_result_pass
All three steps passed.
Definition main.c:114
@ k_cache_mpu_result_fail_mram
RO-MRAM-const (region 0) step failed.
Definition main.c:116
@ k_cache_mpu_result_fail_mmio
Device-MMIO (region 3) step failed.
Definition main.c:117
@ k_cache_mpu_result_fail_sram
Cacheable-RW (region 1) step failed.
Definition main.c:115
static const uint8_t k_cache_mpu_fail_mmio[]
Failure banner: the Device-nGnRE MMIO (region 3) readback mismatched.
Definition main.c:192
static const uint32_t k_cache_mpu_mram_table[k_cache_mpu_mram_words]
Read-only word table placed in MRAM .rodata (MPU region 0).
Definition main.c:143
static const uint8_t k_cache_mpu_fail_setup[]
Failure banner: clock / console bring-up failed before the self-test.
Definition main.c:168
static uint32_t cache_mpu_mram_const_sum(void)
Sum the read-only MRAM const table (executes from MRAM, region 0).
Definition main.c:238
static uint8_t s_cache_mpu_buf[k_cache_mpu_buf_bytes]
4 KiB cacheable scratch buffer in M85-private SRAM (MPU region 1).
Definition main.c:133
static bool cache_mpu_test_mram_const(void)
Step 2 – prove RO MRAM const + MRAM code execution (region 0).
Definition main.c:312
static const uint8_t k_cache_mpu_fail_mram[]
Failure banner: the RO-MRAM-const (region 0) sum mismatched.
Definition main.c:184
static const uint8_t k_cache_mpu_pass_banner[]
Deterministic one-shot HIL success banner (uart_scrape gate).
Definition main.c:159
Board-support layer for the Renesas EK-RA8D2 v1 evaluation kit.
ra8_err_t ra8_board_uart_console_write(const uint8_t *data, size_t len)
Polled blocking write to the J-Link OB VCOM console.
ra8_err_t ra8_board_uart_console_init(uint32_t baud)
Configure SCI8 + PD02/PD03 as the debug-console UART.
ra8_err_t ra8_board_uart_console_flush(void)
Block until every byte queued on the J-Link OB VCOM console has finished clocking out on the wire.
Boot entry points shared between a vector table and its startup code.
Cortex-M85 L1 cache maintenance, enable/disable, and I-cache invalidate.
ra8_err_t ra8_cache_dcache_clean_invalidate_by_addr(const void *addr, uint32_t size)
Clean and invalidate the D-cache lines covering a byte range.
Definition ra8_cache.c:190
High-level Clock Generation Circuit driver.
ra8_err_t ra8_cgc_init(void)
Configure the clock tree to a safe default.
Definition ra8_cgc.c:727
Error Code Definitions for ra8-firmware.
@ k_ra8_ok
Success – operation completed with all postconditions satisfied.
Definition ra8_err.h:119
Lightweight Logging Interface for ra8-firmware.
void ra8_log_init(void)
Initialise the logging backend.
Definition ra8_log.c:379
#define ra8_log_info(tag, message)
RA8 log info.
Definition ra8_log.h:364
System Control (SYSC) register layout for the Renesas RA8D2.
static volatile uint32_t * ra8_sys_sckdivcr(void)
Get pointer to the 32-bit SCKDIVCR register.