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
47
48#include <stdint.h>
49
50#include "ra8_board_ek_ra8d2.h"
51#include "ra8_boot_entry.h"
52#include "ra8_cgc.h"
53#include "ra8_err.h"
54#include "ra8_gpio_constants.h"
55#include "ra8_gpt.h"
56#include "ra8_gpt_capture.h"
57#include "ra8_isr.h"
58#include "ra8_mstp.h"
59#include "ra8_port_constants.h"
60#include "ra8_port_utils.h"
61#include "ra8_time.h"
62
76typedef enum : uint32_t {
77 k_gpt_ecc_period = 0xFFFFFFFFUL,
81
86typedef enum : uint16_t {
89
98
114
126
137volatile uint32_t g_gpt_ecc_last_period = 0U;
138
147volatile uint32_t g_gpt_ecc_capture_events = 0U;
148
159volatile uint32_t g_gpt_ecc_pulse_count = 0U;
160
173volatile uint32_t g_gpt_ecc_tick = 0U;
174
186static void gpt_ecc_panic_halt(void)
187{
188 while (1) {
189 __asm__ volatile("wfi");
190 }
191}
192
218static bool gpt_ecc_period_valid(uint32_t delta_ticks)
219{
220 return (delta_ticks >= (uint32_t)k_gpt_ecc_min_valid_ticks) &&
221 (delta_ticks <= (uint32_t)k_gpt_ecc_max_valid_ticks);
222}
223
236static void gpt_ecc_clocks_or_halt(void)
237{
238 uint32_t cpuclk0_hz = 0U;
239 if (ra8_cgc_init() != k_ra8_ok) {
241 }
244 }
245 if (ra8_time_init(cpuclk0_hz) != k_ra8_ok) {
247 }
250 }
251 if (ra8_mstp_init() != k_ra8_ok) {
253 }
254}
255
269{
271 k_ra8_ok) {
273 }
275 k_ra8_ok) {
277 }
278}
279
295static void gpt_ecc_timers_or_halt(void)
296{
297 const ra8_gpt_cfg_t cfg = {
299 .prescaler = k_ra8_gpt_ps_div_1,
300 .period = (uint32_t)k_gpt_ecc_period,
301 .duty_a = 0U,
302 .duty_b = 0U,
303 .auto_start = true,
304 };
305 if (ra8_gpt_init((uint8_t)k_gpt_ecc_capture_channel, &cfg) != k_ra8_ok) {
307 }
308 /* #185 input capture: latch GTCNT into GTCCRA on each GTIOC0A rising edge. */
313 }
314 if (ra8_gpt_init((uint8_t)k_gpt_ecc_count_channel, &cfg) != k_ra8_ok) {
316 }
317 /* #186 pulse counting: GTCNT counts GTIOC1A rising edges (up source only).
318 * Quadrature variant: pass k_ra8_gpt_cnt_src_ioca_falling as the down
319 * source instead of k_ra8_gpt_cnt_src_none for an encoder up/down count. */
322 (uint32_t)k_ra8_gpt_cnt_src_none) != k_ra8_ok) {
324 }
325}
326
345static bool gpt_ecc_service_capture(uint32_t* prev_latch)
346{
347 uint32_t status = 0U;
348 if (ra8_gpt_get_status((uint8_t)k_gpt_ecc_capture_channel, &status) != k_ra8_ok) {
349 return false;
350 }
351 if ((status & (uint32_t)k_ra8_gpt_status_ccra) == 0U) {
352 return false;
353 }
354 uint32_t latch = 0U;
356 k_ra8_ok) {
357 const uint32_t delta = latch - *prev_latch;
358 *prev_latch = latch;
359 if (gpt_ecc_period_valid(delta)) {
360 g_gpt_ecc_last_period = delta;
363 }
364 }
366 return true;
367}
368
369void main(void)
370{
375
376 uint32_t prev_latch = 0U;
377 uint32_t prev_free = 0U;
378 bool have_prev = false;
379
380 while (1) {
381 /* #185 input capture: hardware edge timestamp -> period. */
382 (void)gpt_ecc_service_capture(&prev_latch);
383
384 /* #186 external event counting: accumulated GTIOC1A edge count. */
385 uint32_t pulses = 0U;
386 if (ra8_gpt_read((uint8_t)k_gpt_ecc_count_channel, &pulses) == k_ra8_ok) {
387 g_gpt_ecc_pulse_count = pulses;
388 }
389
390 /* Pin-independent liveness: capture-channel free-run counter alive. */
391 uint32_t now_free = 0U;
392 if (ra8_gpt_read((uint8_t)k_gpt_ecc_capture_channel, &now_free) == k_ra8_ok) {
393 if (have_prev) {
394 if (now_free != prev_free) {
396 }
397 }
398 prev_free = now_free;
399 have_prev = true;
400 }
402 }
404}
void main(void)
Secure fallback main entry point.
Definition main.c:37
gpt_ecc_layout_t
GPT channel + LED selection for the demo.
Definition main.c:94
@ k_gpt_ecc_capture_channel
GPT0: input-capture channel.
Definition main.c:95
@ k_gpt_ecc_count_channel
GPT1: event-count channel.
Definition main.c:96
static void gpt_ecc_clocks_or_halt(void)
Bring up the core clocks, SysTick, and LED1.
Definition main.c:236
static const ra8_port_pin_t k_gpt_ecc_pin_capture
GTIOC0A input pad for the capture channel (placeholder).
Definition main.c:113
volatile uint32_t g_gpt_ecc_last_period
Most recent valid input-capture delta, in GPT counter ticks.
Definition main.c:137
static void gpt_ecc_panic_halt(void)
Park the CPU after a fatal init failure.
Definition main.c:186
volatile uint32_t g_gpt_ecc_capture_events
Count of valid input-capture edges observed so far.
Definition main.c:147
volatile uint32_t g_gpt_ecc_tick
Pin-independent liveness counter.
Definition main.c:173
static bool gpt_ecc_period_valid(uint32_t delta_ticks)
Classify a captured delta as a genuine signal period.
Definition main.c:218
volatile uint32_t g_gpt_ecc_pulse_count
Latest accumulated external pulse count (GPT1 GTCNT).
Definition main.c:159
static bool gpt_ecc_service_capture(uint32_t *prev_latch)
Service one input-capture poll: latch delta -> globals.
Definition main.c:345
gpt_ecc_poll_const_t
Main-loop poll cadence in milliseconds.
Definition main.c:86
@ k_gpt_ecc_poll_period_ms
Sample GTST / GTCNT every 5 ms.
Definition main.c:87
static void gpt_ecc_timers_or_halt(void)
Configure the capture (GPT0) and count (GPT1) timer channels.
Definition main.c:295
gpt_ecc_period_const_t
32-bit counter tunables (free-run period + capture window).
Definition main.c:76
@ k_gpt_ecc_period
GTPR full-scale.
Definition main.c:77
@ k_gpt_ecc_min_valid_ticks
100: glitch-reject floor.
Definition main.c:78
@ k_gpt_ecc_max_valid_ticks
Wrap / stale-latch ceiling.
Definition main.c:79
static const ra8_port_pin_t k_gpt_ecc_pin_count
GTIOC1A input pad for the event-count channel (placeholder).
Definition main.c:125
static void gpt_ecc_route_pins_or_halt(void)
Route the two GTIOCnA edge-input pins to the GPT peripheral.
Definition main.c:268
Board-support layer for the Renesas EK-RA8D2 v1 evaluation kit.
ra8_err_t ra8_board_led_toggle(ra8_board_led_id_t led)
Toggle led's output state.
ra8_err_t ra8_board_led_init(ra8_board_led_id_t led)
Configure led as a digital output, initial level low (off).
@ k_ra8_board_led1
LED1, BLUE, P600 (jumper E27).
Boot entry points shared between a vector table and its startup code.
High-level Clock Generation Circuit driver.
ra8_err_t ra8_cgc_get_clock_hz(ra8_clock_id_t id, uint32_t *out_hz)
Query the current frequency of a clock-tree domain.
Definition ra8_cgc.c:132
@ k_ra8_clock_id_cpuclk0
Cortex-M85 CPUCLK0.
Definition ra8_cgc.h:70
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
PSEL codes for peripheral pin routing on the RA8D2.
@ k_ra8_psel_gpt0
00011b: GPT timer I/O (GTIOCnA/B).
Full-featured General PWM Timer (GPT) driver.
@ k_ra8_gpt_ccr_a
GTCCRA.
Definition ra8_gpt.h:114
@ k_ra8_gpt_status_ccra
GTST.TCFA (bit 0).
Definition ra8_gpt.h:103
@ k_ra8_gpt_mode_saw_pwm
Saw-wave PWM (up-count).
Definition ra8_gpt.h:54
ra8_err_t ra8_gpt_clear_status(uint8_t channel, uint32_t mask)
Clear GTST flag bits (write-0 to clear).
Definition ra8_gpt.c:418
ra8_err_t ra8_gpt_init(uint8_t channel, const ra8_gpt_cfg_t *cfg)
Initialise a GPT channel with a full config descriptor.
Definition ra8_gpt.c:329
ra8_err_t ra8_gpt_get_status(uint8_t channel, uint32_t *out_mask)
Read GTST overflow / underflow / compare flags.
Definition ra8_gpt.c:408
ra8_err_t ra8_gpt_read(uint8_t channel, uint32_t *out)
Read the current counter value.
Definition ra8_gpt.c:314
@ k_ra8_gpt_ps_div_1
PCLKD / 1.
Definition ra8_gpt.h:66
GPT input-capture + external event / pulse-count extension.
ra8_err_t ra8_gpt_capture_read(uint8_t channel, ra8_gpt_ccr_sel_t which, uint32_t *out_value)
Read the value latched by the last input capture.
Definition ra8_gpt.c:553
@ k_ra8_gpt_cnt_src_ioca_rising
bits 8,9 GTIOCnA rising.
@ k_ra8_gpt_cnt_src_none
No count source (disable).
ra8_err_t ra8_gpt_capture_configure(uint8_t channel, ra8_gpt_ccr_sel_t which, uint32_t source_mask)
Arm a GPT channel for input capture on GTCCRA or GTCCRB.
Definition ra8_gpt.c:528
@ k_ra8_gpt_cap_src_ioca_rising
bits 8,9 GTIOCnA rising.
ra8_err_t ra8_gpt_event_count_configure(uint8_t channel, uint32_t up_source, uint32_t down_source)
Configure external event (edge) counting on GTCNT.
Definition ra8_gpt.c:569
NVIC + ICU IELSR allocator.
void ra8_isr_globals_enable(void)
Globally enable maskable interrupts (PRIMASK = 0).
Definition ra8_isr.c:439
Ref-counted Module Stop Control wrapper for the RA8D2.
ra8_err_t ra8_mstp_init(void)
Re-establish the ra8_mstp ref-count table from current hardware state.
Definition ra8_mstp.c:291
Typed Port / Pin Constants for the RA8D2 IOPORT Module.
ra8_port_pin_t
Packed (port << 8) | pin pin identifier.
@ k_ra8_port_4
RA8 port 4.
#define RA8_PIN(port, pin)
Build a ra8_port_pin_t from explicit port / pin indices.
@ k_ra8_pin_9
RA8 pin 9.
@ k_ra8_pin_8
RA8 pin 8.
High-level GPIO helpers on top of the PORT + PFS register layer.
ra8_err_t ra8_pfs_route_peripheral(ra8_port_pin_t pin, ra8_psel_t psel, const char *owner)
Route a pin to a non-IRQ peripheral function via PFS.PSEL.
Definition gpio.c:238
SysTick-based tick counter, delay and timestamp helpers.
ra8_err_t ra8_time_init(uint32_t cpu_hz)
Initialise SysTick for a 1 kHz tick interrupt.
Definition ra8_time.c:59
void ra8_delay_ms(uint32_t ms)
Busy-wait for at least ms milliseconds.
Definition ra8_time.c:129
Configuration descriptor for ra8_gpt_init.
Definition ra8_gpt.h:83