arch/arm/rtl8721dx: add shared Ameba PWM driver

Add a shared NuttX PWM lower-half for the Realtek Ameba PWM timer in
arch/arm/src/common/ameba, driven through the SDK fwlib.  TIM8 provides a
single time base feeding eight compare channels (CCR0..CCR7) that share one
frequency while each carries its own duty, so a single /dev/pwm0 exposes the
multichannel output via CONFIG_PWM_NCHANNELS.  The fwlib PWM routines are
split ROM/RAM: the time-base calls resolve from on-chip ROM, while the
capture/compare calls live in fwlib ram_common/ameba_tim.c, which the build
pulls into AMEBA_FWLIB_SRCS when CONFIG_AMEBA_PWM is set.

Per-chip wiring (timer index, channel count, register base, input clock,
IRQ, clock masks and the crossbar pad-mux code table) lives in
arch/arm/src/rtl8721dx/ameba_pwm_chip.h so a port to another Ameba chip only
supplies a same-named header; the pad-mux codes are a per-channel table
(AMEBA_PWM_PINMUX_FIDS) rather than a computed base, so chips with a single
shared code or codes grouped per timer are expressed by the header alone.

The timer registers as /dev/pwm0 from pke8721daf bring-up through the stock
PWM character driver; a dedicated `pwm` defconfig drives examples/pwm for
validation.

Signed-off-by: dechao_gong <dechao_gong@realsil.com.cn>
Assisted-by: Claude <noreply@anthropic.com>
This commit is contained in:
dechao_gong
2026-08-17 09:34:22 -03:00
committed by Alan C. Assis
parent 0790b52e64
commit 6f2e17c113
15 changed files with 981 additions and 1 deletions
@@ -41,6 +41,8 @@ Supported in this NuttX port:
on the SDK fwlib register layer
* SPI master buses exposed as ``/dev/spiN`` character devices, driven directly
on the SDK fwlib register layer
* PWM output exposed as a ``/dev/pwm0`` character device, driven directly on
the SDK fwlib timer register layer
Buttons and LEDs
================
@@ -134,6 +136,23 @@ tool::
nsh> spi exch -b 1 -x 4 deadbeef # full-duplex transfer on /dev/spi1
pwm
---
Minimal NSH with the PWM driver and the ``pwm`` example
(``examples/pwm``) enabled (no Wi-Fi). The board registers one timer at
``/dev/pwm0`` (see ``boards/arm/rtl8721dx/pke8721daf/src/rtl8721dx_pwm.c``):
TIM8 drives up to eight compare channels off one shared time base, so every
channel shares one frequency and each carries its own duty cycle. The example
table routes channel 1 to PB18 and channel 2 to PB19; edit it -- one pad per
channel, ``AMEBA_PWM_PIN_NC`` for the unused ones -- to match a board's
wiring. The pads use the same ``AMEBA_PA()`` / ``AMEBA_PB()`` encoding as the
GPIO table and are muxed to the PWM function through the crossbar. Set
``CONFIG_PWM_NCHANNELS`` to the number of channels used. Exercise it with the
example::
nsh> pwm -d 25 -f 1000 # 1 kHz, 25% duty on /dev/pwm0
Wi-Fi
=====