ra8-firmware 0.1.0
Bare-metal firmware for the Renesas RA8 family (RA8D2 / RA8P1)
Loading...
Searching...
No Matches
ra8_dmac.c File Reference

DMAC0 channel driver implementation. More...

#include "ra8_dmac.h"
#include <stdint.h>
#include "ra8_attributes.h"
#include "ra8_check.h"
#include "ra8_dmac_internal.h"
#include "ra8_dmac_regs.h"
#include "ra8_err.h"
#include "ra8_log.h"
#include "ra8_mstp.h"
Include dependency graph for ra8_dmac.c:

Go to the source code of this file.

Data Structures

struct  ra8_dmac_cb_slot_t
 Per-channel callback slot pair (full-complete + half-complete). More...

Functions

bool priv_ra8_dmac_internal_mode_disables_dts (uint32_t mode_normal_val, uint32_t mode_repeat_block_val, uint32_t mode)
 Pure DTS-disabled predicate – see header for full contract.
bool priv_ra8_dmac_internal_dmint_extra_irq (bool irq_each, uint32_t mode_repeat_block_val, uint32_t mode)
 Pure extra-IRQ predicate – see header for full contract.
static uint16_t internal_sz_code (ra8_dmac_width_t width)
 Translate cfg->width -> DMTMD.SZ 2-bit code.
static uint16_t internal_md_code (ra8_dmac_mode_t mode)
 Translate cfg->mode -> DMTMD.MD 2-bit code.
static uint16_t internal_dts_code (ra8_dmac_mode_t mode, ra8_dmac_repeat_area_t area)
 Translate cfg->repeat_area -> DMTMD.DTS 2-bit code.
static uint16_t internal_dmamd_value (bool src_inc, bool dst_inc)
 Compose the DMAMD register value from the increment flags.
static uint16_t internal_dmtmd_value (const ra8_dmac_config_t *cfg)
 Compose the DMTMD register value.
static uint8_t internal_dmint_value (const ra8_dmac_config_t *cfg)
 Compose the DMINT register value.
static uint32_t internal_dmcra_value (const ra8_dmac_config_t *cfg)
 Compose the DMCRA register value.
static ra8_err_t internal_validate_cfg (const ra8_dmac_config_t *cfg)
static void internal_program_channel (volatile r_dmac_channel_regs_t *reg, const ra8_dmac_config_t *cfg)
 Programme every per-channel register from cfg.
ra8_err_t ra8_dmac_start (uint8_t channel, const ra8_dmac_config_t *cfg)
 Programme and enable a DMAC0 channel.
ra8_err_t ra8_dmac_stop (uint8_t channel)
 Disable a DMAC0 channel and drop its MSTP reference.
static ra8_err_t internal_start_with_mode (uint8_t channel, const ra8_dmac_config_t *cfg, ra8_dmac_mode_t forced_mode)
ra8_err_t ra8_dmac_start_repeat (uint8_t channel, const ra8_dmac_config_t *cfg)
 Programme a DMAC channel in repeat-area transfer mode.
ra8_err_t ra8_dmac_start_block (uint8_t channel, const ra8_dmac_config_t *cfg)
 Programme a DMAC channel in block-transfer mode.
ra8_err_t ra8_dmac_set_address_mode (uint8_t channel, ra8_dmac_addr_mode_t src_mode, ra8_dmac_addr_mode_t dest_mode)
 Override the DMAMD.SM / DMAMD.DM address-update modes.
ra8_err_t ra8_dmac_attach_half_complete_handler (uint8_t channel, ra8_dmac_callback_fn_t fn, void *ctx)
 Attach a half-block IRQ callback to a DMAC channel.
ra8_err_t ra8_dmac_attach_callback (uint8_t channel, ra8_dmac_callback_fn_t fn, void *ctx)
 Attach a transfer-end IRQ callback to a DMAC channel.
void ra8_dmac_dispatch (uint8_t channel)
 Fire the per-channel completion callback (DMINT.DTIE path).
void ra8_dmac_dispatch_half (uint8_t channel)
 Fire the per-channel half-complete callback (DMINT.RPTIE path).
ra8_err_t ra8_dmac_software_trigger (uint8_t channel)
 Software-trigger one transfer request on a DMAC0 channel.
ra8_err_t ra8_dmac_is_active (uint8_t channel, bool *out_active)
 Query whether a DMAC0 channel is mid-transfer.
ra8_err_t ra8_dmac_wait_idle (uint8_t channel, uint32_t poll_limit)
 Spin until a DMAC0 channel goes idle or a poll bound expires.

Variables

static const char * s_tag = "DMAC"
static ra8_dmac_cb_slot_t s_dmac_cb_slots [k_ra8_dmac_channel_count]
 One slot per DMAC0 channel.

Detailed Description

DMAC0 channel driver implementation.

Tag
[Ring 3 / HAL] {World: S}

FSP-aligned DMAC0 channel programming. The mapping from FSP's r_dmac_config_transfer_info (r_dmac.c lines 551-682) is:

  • DMTMD.SZ <- cfg->width (HUM 17.2.10 p 738)
  • DMTMD.MD <- cfg->mode (HUM 17.2.10 p 738)
  • DMTMD.DTS <- cfg->repeat_area (HUM 17.2.10 p 738)
  • DMTMD.DCTG <- 0 (software request – ELC trigger lives in DELSR)
  • DMAMD.SM <- cfg->src_inc ? 10b : 00b (HUM 17.2.12 p 741)
  • DMAMD.DM <- cfg->dst_inc ? 10b : 00b
  • DMINT.DTIE <- cfg->enable_dtie (HUM 17.2.11 p 739)
  • DMAST.DMST <- 1 (HUM 17.2.20 p 749 – shared activation gate)
  • DMCNT.DTE <- 1 (HUM 17.2.14 p 743)

Intentional gaps versus FSP:

  • No DELSR programming – ELC routing is owned by the higher- level ra8_dma substrate / individual driver wrappers.
  • No DMSRR / DMDRR / DMSBS / DMDBS programming – repeat-block mode is selectable via cfg->mode but the repeat-area buffers must be zero-extended by the caller (config struct is the minimum the project uses today).
  • No DMOFR (offset-addition mode) – always written 0.
  • No 64-bit transfer width.

Definition in file ra8_dmac.c.

Function Documentation

◆ internal_dmamd_value()

uint16_t internal_dmamd_value ( bool src_inc,
bool dst_inc )
inlinestatic

Compose the DMAMD register value from the increment flags.

Incrementing -> SM/DM = 10b; clear -> 00b (fixed). HUM 17.2.12 p 741. Offset-addition (01b) and decrement (11b) are not exposed by ra8_dmac_config_t today.

Parameters
[in,out]dst_incSee function signature.
[in,out]src_incSee function signature.
Returns
Result code or value; see implementation.
Return values
0Success or default value.
Precondition
Module has been initialized.
Caller has validated arguments.
Postcondition
Side effects bounded to documented state.
State reflects operation result.
Note
Not thread-safe unless documented otherwise.
Since
0.1.0

Definition at line 235 of file ra8_dmac.c.

References k_ra8_dmamd_addr_increment, k_ra8_dmamd_dm_pos, k_ra8_dmamd_sm_pos, and RA8_INTERNAL.

Referenced by internal_program_channel().

◆ internal_dmcra_value()

uint32_t internal_dmcra_value ( const ra8_dmac_config_t * cfg)
inlinestatic

Compose the DMCRA register value.

Low half is the running count; the FSP repeat / block / repeat- block path also copies the same value into the high reload field (r_dmac.c line 582). HUM 17.2.8.

Parameters
[in,out]cfgSee function signature.
Returns
Result code or value; see implementation.
Return values
0Success or default value.
Precondition
Module has been initialized.
Caller has validated arguments.
Postcondition
Side effects bounded to documented state.
State reflects operation result.
Note
Not thread-safe unless documented otherwise.
Since
0.1.0

Definition at line 323 of file ra8_dmac.c.

References ra8_dmac_config_t::count, k_ra8_dmac_mode_normal, k_ra8_dmcra_high_mask, k_ra8_dmcra_high_pos, k_ra8_dmcra_low_mask, ra8_dmac_config_t::mode, and RA8_INTERNAL.

Referenced by internal_program_channel().

◆ internal_dmint_value()

uint8_t internal_dmint_value ( const ra8_dmac_config_t * cfg)
inlinestatic

Compose the DMINT register value.

Mirrors FSP's "if callback configured, enable DTIE; if irq_each and not repeat-block, also enable RPTIE | ESIE" rule (r_dmac.c lines 607-622). HUM 17.2.11 p 739.

Parameters
[in,out]cfgSee function signature.
Returns
Result code or value; see implementation.
Return values
0Success or default value.
Precondition
Module has been initialized.
Caller has validated arguments.
Postcondition
Side effects bounded to documented state.
State reflects operation result.
Note
Not thread-safe unless documented otherwise.
Since
0.1.0

Definition at line 291 of file ra8_dmac.c.

References ra8_dmac_config_t::enable_dtie, ra8_dmac_config_t::irq_each, k_ra8_dmac_mode_repeat_block, k_ra8_dmint_dtie_mask, k_ra8_dmint_esie_mask, k_ra8_dmint_rptie_mask, ra8_dmac_config_t::mode, priv_ra8_dmac_internal_dmint_extra_irq(), and RA8_INTERNAL.

Referenced by internal_program_channel().

◆ internal_dmtmd_value()

uint16_t internal_dmtmd_value ( const ra8_dmac_config_t * cfg)
inlinestatic

Compose the DMTMD register value.

DCTG is left at 00b (software request); ELC routing is the substrate's job via DELSR. SZ / MD / DTS are positioned per HUM.

Parameters
[in,out]cfgSee function signature.
Returns
Result code or value; see implementation.
Return values
0Success or default value.
Precondition
Module has been initialized.
Caller has validated arguments.
Postcondition
Side effects bounded to documented state.
State reflects operation result.
Note
Not thread-safe unless documented otherwise.
Since
0.1.0

Definition at line 264 of file ra8_dmac.c.

References internal_dts_code(), internal_md_code(), internal_sz_code(), k_ra8_dmtmd_dts_pos, k_ra8_dmtmd_md_pos, k_ra8_dmtmd_sz_pos, ra8_dmac_config_t::mode, RA8_INTERNAL, ra8_dmac_config_t::repeat_area, and ra8_dmac_config_t::width.

Referenced by internal_program_channel().

◆ internal_dts_code()

uint16_t internal_dts_code ( ra8_dmac_mode_t mode,
ra8_dmac_repeat_area_t area )
inlinestatic

Translate cfg->repeat_area -> DMTMD.DTS 2-bit code.

In normal and repeat-block mode the field is forced to "none" (HUM 17.2.10 p 738 – "In normal or repeat-block transfer mode, setting these bits is invalid").

Parameters
[in,out]areaSee function signature.
[in,out]modeSee function signature.
Returns
Result code or value; see implementation.
Return values
0Success or default value.
Precondition
Module has been initialized.
Caller has validated arguments.
Postcondition
Side effects bounded to documented state.
State reflects operation result.
Note
Not thread-safe unless documented otherwise.
Since
0.1.0

Definition at line 197 of file ra8_dmac.c.

References k_ra8_dmac_mode_normal, k_ra8_dmac_mode_repeat_block, k_ra8_dmac_repeat_area_dest, k_ra8_dmac_repeat_area_none, k_ra8_dmac_repeat_area_src, k_ra8_dmtmd_dts_dest_repeat, k_ra8_dmtmd_dts_none, k_ra8_dmtmd_dts_src_repeat, priv_ra8_dmac_internal_mode_disables_dts(), and RA8_INTERNAL.

Referenced by internal_dmtmd_value().

◆ internal_md_code()

uint16_t internal_md_code ( ra8_dmac_mode_t mode)
inlinestatic

Translate cfg->mode -> DMTMD.MD 2-bit code.

Maps the driver's ra8_dmac_mode_t enum onto the 2-bit MD field in DMTMD (HUM Ch 16.2.4, p 608). Defaults to normal mode when given an out-of-range value.

Parameters
[in]modeTransfer mode enum value.
Returns
DMTMD.MD field bits (already shifted into position 0).
Return values
k_ra8_dmtmd_md_normalNormal-transfer mode.
k_ra8_dmtmd_md_repeatRepeat-transfer mode.
k_ra8_dmtmd_md_blockBlock-transfer mode.
k_ra8_dmtmd_md_repeat_blockRepeat-block-transfer mode.
Precondition
mode is a valid ra8_dmac_mode_t value.
Caller is composing a fresh DMTMD value.
Postcondition
No state mutated.
Result fits in the DMTMD.MD field width.
Note
Pure function; thread-safe.
Since
0.1.0

Definition at line 162 of file ra8_dmac.c.

References k_ra8_dmac_mode_block, k_ra8_dmac_mode_normal, k_ra8_dmac_mode_repeat, k_ra8_dmac_mode_repeat_block, k_ra8_dmtmd_md_block, k_ra8_dmtmd_md_normal, k_ra8_dmtmd_md_repeat, k_ra8_dmtmd_md_repeat_block, and RA8_INTERNAL.

Referenced by internal_dmtmd_value().

◆ internal_program_channel()

void internal_program_channel ( volatile r_dmac_channel_regs_t * reg,
const ra8_dmac_config_t * cfg )
inlinestatic

Programme every per-channel register from cfg.

Steps 2-6 of the start sequence; the global activation gate and the channel-enable bit are flipped by the caller after this helper returns so the function-size budget stays under the NASA-Rule-4 / clang-tidy threshold.

Parameters
[in,out]cfgSee function signature.
[in,out]regSee function signature.
Precondition
Module has been initialized.
Caller has validated arguments.
Postcondition
Side effects bounded to documented state.
State reflects operation result.
Note
Not thread-safe unless documented otherwise.
Since
0.1.0

Definition at line 363 of file ra8_dmac.c.

References ra8_dmac_config_t::block_count, r_dmac_channel_regs_t::DMAMD, r_dmac_channel_regs_t::DMCNT, r_dmac_channel_regs_t::DMCRA, r_dmac_channel_regs_t::DMCRB, r_dmac_channel_regs_t::DMDAR, r_dmac_channel_regs_t::DMINT, r_dmac_channel_regs_t::DMOFR, r_dmac_channel_regs_t::DMSAR, r_dmac_channel_regs_t::DMTMD, ra8_dmac_config_t::dst, ra8_dmac_config_t::dst_inc, internal_dmamd_value(), internal_dmcra_value(), internal_dmint_value(), internal_dmtmd_value(), k_ra8_dmac_mode_normal, k_ra8_dmcra_high_pos, ra8_dmac_config_t::mode, RA8_INTERNAL, ra8_dmac_config_t::src, and ra8_dmac_config_t::src_inc.

Referenced by ra8_dmac_start().

◆ internal_start_with_mode()

ra8_err_t internal_start_with_mode ( uint8_t channel,
const ra8_dmac_config_t * cfg,
ra8_dmac_mode_t forced_mode )
static

◆ internal_sz_code()

uint16_t internal_sz_code ( ra8_dmac_width_t width)
inlinestatic

Translate cfg->width -> DMTMD.SZ 2-bit code.

Maps the driver's ra8_dmac_width_t enum onto the 2-bit SZ field in DMTMD (HUM Ch 16.2.4 "DMTMD : DMA Transfer Mode Register", p 608). Defaults to byte-width when given an out-of-range value.

Parameters
[in]widthTransfer width enum value.
Returns
DMTMD.SZ field bits (already shifted into position 0).
Return values
k_ra8_dmtmd_sz_byte8-bit transfers.
k_ra8_dmtmd_sz_half16-bit transfers.
k_ra8_dmtmd_sz_word32-bit transfers.
Precondition
width is a valid ra8_dmac_width_t value.
Caller is composing a fresh DMTMD value.
Postcondition
No state mutated.
Result fits in the DMTMD.SZ field width.
Note
Pure function; thread-safe.
Since
0.1.0

Definition at line 124 of file ra8_dmac.c.

References k_ra8_dmac_width_byte, k_ra8_dmac_width_half, k_ra8_dmac_width_word, k_ra8_dmtmd_sz_byte, k_ra8_dmtmd_sz_half, k_ra8_dmtmd_sz_word, and RA8_INTERNAL.

Referenced by internal_dmtmd_value().

◆ internal_validate_cfg()

ra8_err_t internal_validate_cfg ( const ra8_dmac_config_t * cfg)
inlinestatic

◆ priv_ra8_dmac_internal_dmint_extra_irq()

bool priv_ra8_dmac_internal_dmint_extra_irq ( bool irq_each,
uint32_t mode_repeat_block_val,
uint32_t mode )

Pure extra-IRQ predicate – see header for full contract.

Pure predicate for the DMINT "extra IRQ bits" decision.

Promoted helper so the line-246 AND can be driven under MC/DC.

Parameters
[in]irq_eachBoolean: per-block IRQ enable.
[in]mode_repeat_block_valNumeric value of k_ra8_dmac_mode_repeat_block.
[in]modeCandidate mode value.
Returns
Boolean predicate.
Return values
trueCaller must OR in RPTIE | ESIE.
falseLeave RPTIE / ESIE clear.
Precondition
None.
None.
Postcondition
No state mutated.
Return depends solely on inputs.
Note
Pure; thread-safe.
Since
0.1.0

Definition at line 87 of file ra8_dmac.c.

Referenced by internal_dmint_value().

◆ priv_ra8_dmac_internal_mode_disables_dts()

bool priv_ra8_dmac_internal_mode_disables_dts ( uint32_t mode_normal_val,
uint32_t mode_repeat_block_val,
uint32_t mode )

Pure DTS-disabled predicate – see header for full contract.

Pure predicate for the DMTMD-DTS "no repeat" decision.

Promoted helper so the line-151 OR can be driven under MC/DC.

Parameters
[in]mode_normal_valNumeric value of k_ra8_dmac_mode_normal.
[in]mode_repeat_block_valNumeric value of k_ra8_dmac_mode_repeat_block.
[in]modeCandidate mode value.
Returns
Boolean predicate.
Return values
trueMode disables DTS.
falseMode requires non-zero DTS code.
Precondition
None.
None.
Postcondition
No state mutated.
Return depends solely on inputs.
Note
Pure; thread-safe.
Since
0.1.0

Definition at line 64 of file ra8_dmac.c.

Referenced by internal_dts_code().

◆ ra8_dmac_attach_callback()

ra8_err_t ra8_dmac_attach_callback ( uint8_t channel,
ra8_dmac_callback_fn_t fn,
void * ctx )
nodiscard

Attach a transfer-end IRQ callback to a DMAC channel.

Registers a per-channel completion callback. The driver fires it whenever ra8_dmac_dispatch(channel) is called by the matching DMAC ISR (or, in host-test mode, by the test harness). Replaces any earlier global callback that the substrate may have used.

Parameters
[in]channelDMAC0 channel index 0..7.
[in]fnCallback function (NULL clears the slot).
[in]ctxOpaque pointer passed to fn.
Returns
ra8_err_t error code.
Return values
k_ra8_okSlot updated.
k_ra8_err_out_of_rangechannel >= 8.
Precondition
ra8_mstp_init() has been called.
Postcondition
ra8_dmac_dispatch(channel) invokes fn(ctx).
Note
Not thread-safe; pair with IRQ masking.
Since
0.1.0

Definition at line 524 of file ra8_dmac.c.

References k_ra8_dmac_channel_count, k_ra8_err_out_of_range, k_ra8_ok, and s_dmac_cb_slots.

◆ ra8_dmac_attach_half_complete_handler()

ra8_err_t ra8_dmac_attach_half_complete_handler ( uint8_t channel,
ra8_dmac_callback_fn_t fn,
void * ctx )
nodiscard

Attach a half-block IRQ callback to a DMAC channel.

Registers fn as the user-side handler invoked when DMINT.RPTIE fires (repeat-size end – HUM 17.2.11 p 739). The driver enables RPTIE in the DMAC ISR plumbing so the half-complete callback fires once per cfg->count transfers, independent of DTIE.

Parameters
[in]channelDMAC0 channel index 0..7.
[in]fnCallback function (NULL clears the slot).
[in]ctxOpaque pointer passed to fn.
Returns
ra8_err_t error code.
Return values
k_ra8_okSlot updated.
k_ra8_err_out_of_rangechannel >= 8.
Precondition
ra8_dmac_start_*() was called for channel.
Postcondition
ra8_dmac_dispatch_half(channel) invokes fn(ctx).
Note
Not thread-safe; pair with IRQ masking.
Since
0.1.0

Definition at line 514 of file ra8_dmac.c.

References k_ra8_dmac_channel_count, k_ra8_err_out_of_range, k_ra8_ok, and s_dmac_cb_slots.

◆ ra8_dmac_dispatch()

void ra8_dmac_dispatch ( uint8_t channel)

Fire the per-channel completion callback (DMINT.DTIE path).

Test / ISR helper; consumes the slot installed by ra8_dmac_attach_callback(). Silently returns if no callback is registered or the channel is out of range. Reads DMINT.DTIE (HUM Ch 16.2.7 "DMINT : DMA Interrupt Setting Register", p 612) to decide whether the transfer-end IRQ is enabled before invoking the callback.

Parameters
[in]channelDMAC0 channel index 0..7.
Precondition
ra8_mstp_init() and ra8_dmac_start(channel, ...) have been called.
Called from ISR context or unit-test driver.
Postcondition
Registered completion callback invoked at most once.
No state change if channel is out of range or no callback is set.
Note
Thread safety: ISR context only; not re-entrant per channel.
Since
0.1.0

Definition at line 535 of file ra8_dmac.c.

References k_ra8_dmac_channel_count, and s_dmac_cb_slots.

◆ ra8_dmac_dispatch_half()

void ra8_dmac_dispatch_half ( uint8_t channel)

Fire the per-channel half-complete callback (DMINT.RPTIE path).

ISR / test helper for the repeat-block half-complete event. Consumes the slot installed by ra8_dmac_attach_half_complete_handler() and silently returns if no callback is registered or the channel is out of range. Tied to DMINT.RPTIE (HUM Ch 16.2.7, p 612).

Parameters
[in]channelDMAC0 channel index 0..7.
Precondition
ra8_mstp_init() and ra8_dmac_start_repeat(channel, ...) have been called.
Called from ISR context or unit-test driver.
Postcondition
Registered half-complete callback invoked at most once.
No state change if channel is out of range or no callback is set.
Note
Thread safety: ISR context only; not re-entrant per channel.
Since
0.1.0

Definition at line 548 of file ra8_dmac.c.

References k_ra8_dmac_channel_count, and s_dmac_cb_slots.

◆ ra8_dmac_is_active()

ra8_err_t ra8_dmac_is_active ( uint8_t channel,
bool * out_active )
nodiscard

Query whether a DMAC0 channel is mid-transfer.

Reads DMSTS.ACT on channel (HUM Ch 17.2.16 "DMSTS : DMAC Status Register" p 745 – the ACT bit reads 1 while the controller is executing a transfer and clears to 0 once the request in flight has been satisfied). The status is returned through out_active rather than the return value so that a bad channel or a NULL pointer is still reportable as an error code (NASA P10 Rule 7).

Parameters
[in]channelDMAC0 channel index 0..7.
[out]out_activeSet true when DMSTS.ACT is 1, else false. Untouched on any error return.
Returns
ra8_err_t error code.
Return values
k_ra8_ok*out_active written.
k_ra8_err_null_ptrout_active is NULL.
k_ra8_err_out_of_rangechannel >= 8.
Precondition
ra8_dmac_start() (or a sibling) armed channel.
out_active points to writable storage.
Postcondition
On k_ra8_ok *out_active reflects DMSTS.ACT.
No channel register is modified.
Note
Reads a single volatile byte; safe with IRQs unmasked.
See also
ra8_dmac_wait_idle
ra8_dmac_software_trigger
Since
0.1.0

Definition at line 576 of file ra8_dmac.c.

References r_dmac_channel_regs_t::DMSTS, k_ra8_dmsts_act_mask, k_ra8_err_out_of_range, k_ra8_ok, RA8_CHECK_NULL_PTR, ra8_dmac(), and s_tag.

◆ ra8_dmac_set_address_mode()

ra8_err_t ra8_dmac_set_address_mode ( uint8_t channel,
ra8_dmac_addr_mode_t src_mode,
ra8_dmac_addr_mode_t dest_mode )
nodiscard

Override the DMAMD.SM / DMAMD.DM address-update modes.

Lets callers pick from the full 4-mode menu (fixed / offset / increment / decrement) per HUM 17.2.12 p 741. The base ra8_dmac_config_t only models fixed vs increment, so this entry point is required when offset-addition or decrement is needed (e.g. byte-reversed copy, ring-walk with stride).

Parameters
[in]channelDMAC0 channel index 0..7.
[in]src_modeNew DMAMD.SM value.
[in]dest_modeNew DMAMD.DM value.
Returns
ra8_err_t error code.
Return values
k_ra8_okDMAMD updated.
k_ra8_err_out_of_rangechannel >= 8.
k_ra8_err_invalid_argEither mode > k_ra8_dmac_addr_decrement.
Precondition
ra8_dmac_start() (or sibling) was called for channel.
Channel is currently disabled (DMCNT.DTE = 0) before reprogramming.
Postcondition
DMAMD.SM and DMAMD.DM reflect the requested codes.
All other DMAMD bits are preserved.
Note
Not thread-safe.
Since
0.1.0

Definition at line 492 of file ra8_dmac.c.

References r_dmac_channel_regs_t::DMAMD, k_ra8_dmac_addr_decrement, k_ra8_dmamd_dm_mask, k_ra8_dmamd_dm_pos, k_ra8_dmamd_sm_mask, k_ra8_dmamd_sm_pos, k_ra8_err_invalid_arg, k_ra8_err_out_of_range, k_ra8_ok, and ra8_dmac().

◆ ra8_dmac_software_trigger()

ra8_err_t ra8_dmac_software_trigger ( uint8_t channel)
nodiscard

Software-trigger one transfer request on a DMAC0 channel.

Writes DMREQ.SWREQ = 1 on channel to raise a software DMA transfer request (HUM Ch 17.2.15 "DMREQ : DMAC Software Start Register" p 744 – "When 1 is written to the SWREQ bit, a DMA transfer request is generated. After the DMA transfer is started [...] this bit is automatically cleared to 0"). The channel must already have been programmed and armed by ra8_dmac_start (or a sibling) with a software request source (DMTMD.DCTG = 00b, the driver default).

In block or repeat-block mode a single trigger moves a whole DMCRAH-sized block; in normal mode it moves one unit. Pair with ra8_dmac_wait_idle / ra8_dmac_is_active to observe completion. This is the HAL primitive that replaces reaching for ra8_dmac(channel)->DMREQ directly in application code.

Parameters
[in]channelDMAC0 channel index 0..7.
Returns
ra8_err_t error code.
Return values
k_ra8_okSoftware request raised.
k_ra8_err_out_of_rangechannel >= 8.
Precondition
ra8_dmac_start() (or a sibling) armed channel.
The channel's request source is software (DMTMD.DCTG = 00b).
Postcondition
DMREQ.SWREQ was written 1 for channel.
No other channel register is modified.
Note
Not thread-safe; pair with IRQ masking on a shared channel.
See also
ra8_dmac_wait_idle
ra8_dmac_is_active
ra8_dmac_start_block
Since
0.1.0

Definition at line 565 of file ra8_dmac.c.

References r_dmac_channel_regs_t::DMREQ, k_ra8_dmreq_swreq_mask, k_ra8_err_out_of_range, k_ra8_ok, and ra8_dmac().

Referenced by internal_run_copy().

◆ ra8_dmac_start()

ra8_err_t ra8_dmac_start ( uint8_t channel,
const ra8_dmac_config_t * cfg )
nodiscard

Programme and enable a DMAC0 channel.

Mirrors FSP's R_DMAC_Open for the steady-state programme path. Sequence (matches HUM 17.6 register-setting procedure):

  1. Bring DMAC0 out of MSTP (k_ra8_mstp_dmac0_dtc0).
  2. Disable channel (DMCNT.DTE = 0).
  3. Programme DMTMD (mode, repeat area, size, software request).
  4. Programme DMAMD (source/dest update mode).
  5. Programme DMSAR / DMDAR / DMCRA / DMCRB / DMOFR.
  6. Programme DMINT (DTIE / RPTIE / ESIE per cfg).
  7. Set the global DMA module activation gate (DMAST.DMST = 1).
  8. Enable channel (DMCNT.DTE = 1).
Parameters
[in]channelDMAC0 channel index 0..7.
[in]cfgTransfer descriptor.
Returns
ra8_err_t error code.
Return values
k_ra8_okChannel armed.
k_ra8_err_null_ptrcfg is NULL.
k_ra8_err_out_of_rangechannel >= 8.
k_ra8_err_invalid_argcfg->mode or cfg->width invalid.
Precondition
ra8_mstp_init() has been called.
IRQs masked or single-threaded init context.
Postcondition
On success the channel is enabled and waiting for its configured trigger (software or ELC event via DELSR).
See also
ra8_dmac_stop
Since
0.1.0

Definition at line 398 of file ra8_dmac.c.

References r_dma_shared_regs_t::DMAST, r_dmac_channel_regs_t::DMCNT, internal_program_channel(), internal_validate_cfg(), k_ra8_dmast_dmst_mask, k_ra8_dmcnt_dte_mask, k_ra8_err_out_of_range, k_ra8_mstp_dmac0_dtc0, k_ra8_ok, RA8_CHECK_NULL_PTR, ra8_dma_shared(), ra8_dmac(), ra8_log_info_val, ra8_mstp_enable(), RA8_RETURN_ON_ERROR, and s_tag.

Referenced by internal_start_rx_dma(), internal_start_tx_dma(), internal_start_with_mode(), ra8_ceu_dma_pump(), and ra8_dma_request().

◆ ra8_dmac_start_block()

ra8_err_t ra8_dmac_start_block ( uint8_t channel,
const ra8_dmac_config_t * cfg )
nodiscard

Programme a DMAC channel in block-transfer mode.

Convenience wrapper that forces cfg->mode = k_ra8_dmac_mode_block before delegating to ra8_dmac_start(). The controller transfers cfg->count elements per trigger and then rewinds the repeat side; cfg->block_count blocks are processed before the channel is automatically disabled. HUM 17.2.10 p 738 (DMTMD.MD = 10b) and HUM 17.2.9 (DMCRB block count).

Parameters
[in]channelDMAC0 channel index 0..7.
[in]cfgTransfer descriptor; mode is ignored.
Returns
ra8_err_t error code.
Return values
k_ra8_okChannel armed in block mode.
k_ra8_err_null_ptrcfg is NULL.
k_ra8_err_out_of_rangechannel >= 8.
k_ra8_err_invalid_argcfg->block_count is zero.
Precondition
ra8_mstp_init() has been called.
cfg->block_count is non-zero.
Postcondition
Channel is enabled and waiting for its trigger.
DMCRB carries cfg->block_count.
Note
Not thread-safe.
See also
ra8_dmac_start
ra8_dmac_start_repeat
Since
0.1.0

Definition at line 483 of file ra8_dmac.c.

References ra8_dmac_config_t::block_count, internal_start_with_mode(), k_ra8_dmac_mode_block, k_ra8_err_invalid_arg, RA8_CHECK_NULL_PTR, and s_tag.

Referenced by internal_run_copy().

◆ ra8_dmac_start_repeat()

ra8_err_t ra8_dmac_start_repeat ( uint8_t channel,
const ra8_dmac_config_t * cfg )
nodiscard

Programme a DMAC channel in repeat-area transfer mode.

Convenience wrapper that forces cfg->mode = k_ra8_dmac_mode_repeat before delegating to ra8_dmac_start(). In repeat mode the controller automatically rewinds either DMSAR or DMDAR (per cfg->repeat_area) every cfg->count transfers, so ring buffers and double-buffered framebuffers can be expressed without software intervention. HUM 17.2.10 p 738 (DMTMD.MD = 01b).

Parameters
[in]channelDMAC0 channel index 0..7.
[in]cfgTransfer descriptor; mode is ignored.
Returns
ra8_err_t error code.
Return values
k_ra8_okChannel armed in repeat mode.
k_ra8_err_null_ptrcfg is NULL.
k_ra8_err_out_of_rangechannel >= 8.
k_ra8_err_invalid_argcfg->width invalid.
Precondition
ra8_mstp_init() has been called.
cfg->repeat_area selects either source or destination side.
Postcondition
Channel is enabled and waiting for its trigger.
DMTMD.MD reads as 01b (repeat).
Note
Not thread-safe.
See also
ra8_dmac_start
ra8_dmac_start_block
Since
0.1.0

Definition at line 478 of file ra8_dmac.c.

References internal_start_with_mode(), and k_ra8_dmac_mode_repeat.

◆ ra8_dmac_stop()

ra8_err_t ra8_dmac_stop ( uint8_t channel)
nodiscard

Disable a DMAC0 channel and drop its MSTP reference.

Parameters
[in]channelDMAC0 channel index 0..7.
Returns
ra8_err_t error code.
Return values
k_ra8_okChannel disabled.
k_ra8_err_out_of_rangechannel >= 8.
Precondition
ra8_dmac_start() was called for channel.
Postcondition
DMCNT.DTE is 0 for channel.
One MSTP reference on k_ra8_mstp_dmac0_dtc0 is released.
Since
0.1.0

Definition at line 432 of file ra8_dmac.c.

References r_dmac_channel_regs_t::DMCNT, k_ra8_err_out_of_range, k_ra8_mstp_dmac0_dtc0, ra8_dmac(), and ra8_mstp_disable().

Referenced by internal_run_copy(), internal_unwind_tx_dma(), ra8_dma_deinit(), ra8_dma_release(), and ra8_ssie_detach_dma().

◆ ra8_dmac_wait_idle()

ra8_err_t ra8_dmac_wait_idle ( uint8_t channel,
uint32_t poll_limit )
nodiscard

Spin until a DMAC0 channel goes idle or a poll bound expires.

Polls DMSTS.ACT (HUM Ch 17.2.16 "DMSTS : DMAC Status Register" p 745) up to poll_limit times, returning as soon as the bit reads 0 (transfer complete). This is the synchronous completion gate the fire-and-wait DMA demos use after ra8_dmac_software_trigger: a block-mode copy holds ACT asserted for the duration of the block and clears it at completion.

The poll loop is statically bounded by poll_limit (NASA P10 Rule 2); a poll_limit of 0 performs no read and reports a timeout. Choose the bound for the expected transfer length at the current bus clock.

Parameters
[in]channelDMAC0 channel index 0..7.
[in]poll_limitMaximum number of DMSTS.ACT reads before giving up.
Returns
ra8_err_t error code.
Return values
k_ra8_okChannel reached idle (ACT = 0).
k_ra8_err_hw_timeoutpoll_limit exhausted, ACT still 1.
k_ra8_err_out_of_rangechannel >= 8.
Precondition
ra8_dmac_start() (or a sibling) armed channel.
A transfer has been requested (ra8_dmac_software_trigger or an ELC event) or the channel is already idle.
Postcondition
On k_ra8_ok the channel's DMSTS.ACT reads 0.
No channel register is modified.
Note
Busy-wait; not thread-safe.
See also
ra8_dmac_software_trigger
ra8_dmac_is_active
Since
0.1.0

Definition at line 588 of file ra8_dmac.c.

References r_dmac_channel_regs_t::DMSTS, k_ra8_dmsts_act_mask, k_ra8_err_hw_timeout, k_ra8_err_out_of_range, k_ra8_ok, and ra8_dmac().

Referenced by internal_run_copy().

Variable Documentation

◆ s_dmac_cb_slots

One slot per DMAC0 channel.

Definition at line 466 of file ra8_dmac.c.

Referenced by ra8_dmac_attach_callback(), ra8_dmac_attach_half_complete_handler(), ra8_dmac_dispatch(), and ra8_dmac_dispatch_half().

◆ s_tag

const char* s_tag = "DMAC"
static

Definition at line 94 of file ra8_dmac.c.