Files
tinygo/src/machine/machine_esp32s3_pwm.go
T
Dima 47282be619 esp3s3 & esp32c3 PWM implements (#5215)
* esp3s3 pwm

* esp32s3-pwm: added spi alias for esp32s3 for tests

* esp32s3-pwm: fix linters

* esp32s3-pwm: fix rename

* esp32s3-pwm: replace if to switch

* esp32s3-pwm: chip specific registry

* esp32s3-pwm: fix linters
2026-04-05 14:15:40 +02:00

227 lines
7.4 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
//go:build esp32s3
package machine
import "device/esp"
// LEDC PWM for ESP32-S3: 4 timers (PWM0PWM3), 8 channels per timer; each timer has its own frequency.
// Range: frequency from a few Hz up to ~40 MHz (at 1-bit resolution); duty resolution 115 bits
// (higher frequency gives lower resolution). Clock source: APB 80 MHz. Low-speed mode only.
// Duty must not equal 2^resolution (overflow risk). See ESP-IDF LEDC driver, TRM LED PWM Controller.
// GPIO matrix output signal indices for LEDC (soc/gpio_sig_map.h)
const (
LEDC_LS_SIG_OUT0_IDX = 73
)
const ledcChannelsS3 = 8
var (
PWM0 = &LEDCPWM{SigOutBase: LEDC_LS_SIG_OUT0_IDX, NumChannels: ledcChannelsS3, timerNum: 0}
PWM1 = &LEDCPWM{SigOutBase: LEDC_LS_SIG_OUT0_IDX, NumChannels: ledcChannelsS3, timerNum: 1}
PWM2 = &LEDCPWM{SigOutBase: LEDC_LS_SIG_OUT0_IDX, NumChannels: ledcChannelsS3, timerNum: 2}
PWM3 = &LEDCPWM{SigOutBase: LEDC_LS_SIG_OUT0_IDX, NumChannels: ledcChannelsS3, timerNum: 3}
)
// chanOp implements LEDC low-speed channel ops for ESP32-S3 (channels 07).
func (pwm *LEDCPWM) chanOp(ch uint8, op ledcChanOp, duty uint32, inverting bool) {
invVal := uint32(0)
if inverting {
invVal = 1
}
switch ch {
case 0:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH0_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH0_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH0_CONF0_IDLE_LV(0)
esp.LEDC.SetCH0_HPOINT_HPOINT(0)
esp.LEDC.SetCH0_DUTY_DUTY(0)
esp.LEDC.SetCH0_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH0_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH0_CONF1_DUTY_INC(1)
esp.LEDC.SetCH0_CONF1_DUTY_START(1)
esp.LEDC.SetCH0_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH0_DUTY_DUTY(duty)
esp.LEDC.SetCH0_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH0_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH0_CONF1_DUTY_INC(1)
esp.LEDC.SetCH0_CONF1_DUTY_START(1)
esp.LEDC.SetCH0_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH0_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH0_CONF0_IDLE_LV(invVal)
}
case 1:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH1_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH1_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH1_CONF0_IDLE_LV(0)
esp.LEDC.SetCH1_HPOINT_HPOINT(0)
esp.LEDC.SetCH1_DUTY_DUTY(0)
esp.LEDC.SetCH1_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH1_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH1_CONF1_DUTY_INC(1)
esp.LEDC.SetCH1_CONF1_DUTY_START(1)
esp.LEDC.SetCH1_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH1_DUTY_DUTY(duty)
esp.LEDC.SetCH1_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH1_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH1_CONF1_DUTY_INC(1)
esp.LEDC.SetCH1_CONF1_DUTY_START(1)
esp.LEDC.SetCH1_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH1_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH1_CONF0_IDLE_LV(invVal)
}
case 2:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH2_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH2_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH2_CONF0_IDLE_LV(0)
esp.LEDC.SetCH2_HPOINT_HPOINT(0)
esp.LEDC.SetCH2_DUTY_DUTY(0)
esp.LEDC.SetCH2_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH2_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH2_CONF1_DUTY_INC(1)
esp.LEDC.SetCH2_CONF1_DUTY_START(1)
esp.LEDC.SetCH2_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH2_DUTY_DUTY(duty)
esp.LEDC.SetCH2_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH2_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH2_CONF1_DUTY_INC(1)
esp.LEDC.SetCH2_CONF1_DUTY_START(1)
esp.LEDC.SetCH2_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH2_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH2_CONF0_IDLE_LV(invVal)
}
case 3:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH3_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH3_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH3_CONF0_IDLE_LV(0)
esp.LEDC.SetCH3_HPOINT_HPOINT(0)
esp.LEDC.SetCH3_DUTY_DUTY(0)
esp.LEDC.SetCH3_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH3_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH3_CONF1_DUTY_INC(1)
esp.LEDC.SetCH3_CONF1_DUTY_START(1)
esp.LEDC.SetCH3_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH3_DUTY_DUTY(duty)
esp.LEDC.SetCH3_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH3_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH3_CONF1_DUTY_INC(1)
esp.LEDC.SetCH3_CONF1_DUTY_START(1)
esp.LEDC.SetCH3_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH3_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH3_CONF0_IDLE_LV(invVal)
}
case 4:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH4_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH4_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH4_CONF0_IDLE_LV(0)
esp.LEDC.SetCH4_HPOINT_HPOINT(0)
esp.LEDC.SetCH4_DUTY_DUTY(0)
esp.LEDC.SetCH4_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH4_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH4_CONF1_DUTY_INC(1)
esp.LEDC.SetCH4_CONF1_DUTY_START(1)
esp.LEDC.SetCH4_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH4_DUTY_DUTY(duty)
esp.LEDC.SetCH4_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH4_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH4_CONF1_DUTY_INC(1)
esp.LEDC.SetCH4_CONF1_DUTY_START(1)
esp.LEDC.SetCH4_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH4_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH4_CONF0_IDLE_LV(invVal)
}
case 5:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH5_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH5_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH5_CONF0_IDLE_LV(0)
esp.LEDC.SetCH5_HPOINT_HPOINT(0)
esp.LEDC.SetCH5_DUTY_DUTY(0)
esp.LEDC.SetCH5_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH5_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH5_CONF1_DUTY_INC(1)
esp.LEDC.SetCH5_CONF1_DUTY_START(1)
esp.LEDC.SetCH5_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH5_DUTY_DUTY(duty)
esp.LEDC.SetCH5_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH5_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH5_CONF1_DUTY_INC(1)
esp.LEDC.SetCH5_CONF1_DUTY_START(1)
esp.LEDC.SetCH5_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH5_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH5_CONF0_IDLE_LV(invVal)
}
case 6:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH6_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH6_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH6_CONF0_IDLE_LV(0)
esp.LEDC.SetCH6_HPOINT_HPOINT(0)
esp.LEDC.SetCH6_DUTY_DUTY(0)
esp.LEDC.SetCH6_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH6_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH6_CONF1_DUTY_INC(1)
esp.LEDC.SetCH6_CONF1_DUTY_START(1)
esp.LEDC.SetCH6_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH6_DUTY_DUTY(duty)
esp.LEDC.SetCH6_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH6_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH6_CONF1_DUTY_INC(1)
esp.LEDC.SetCH6_CONF1_DUTY_START(1)
esp.LEDC.SetCH6_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH6_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH6_CONF0_IDLE_LV(invVal)
}
case 7:
switch op {
case ledcChanOpInit:
esp.LEDC.SetCH7_CONF0_TIMER_SEL(uint32(pwm.timerNum))
esp.LEDC.SetCH7_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH7_CONF0_IDLE_LV(0)
esp.LEDC.SetCH7_HPOINT_HPOINT(0)
esp.LEDC.SetCH7_DUTY_DUTY(0)
esp.LEDC.SetCH7_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH7_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH7_CONF1_DUTY_INC(1)
esp.LEDC.SetCH7_CONF1_DUTY_START(1)
esp.LEDC.SetCH7_CONF0_PARA_UP(1)
case ledcChanOpSetDuty:
esp.LEDC.SetCH7_DUTY_DUTY(duty)
esp.LEDC.SetCH7_CONF1_DUTY_CYCLE(1)
esp.LEDC.SetCH7_CONF1_DUTY_NUM(1)
esp.LEDC.SetCH7_CONF1_DUTY_INC(1)
esp.LEDC.SetCH7_CONF1_DUTY_START(1)
esp.LEDC.SetCH7_CONF0_SIG_OUT_EN(1)
esp.LEDC.SetCH7_CONF0_PARA_UP(1)
case ledcChanOpSetInvert:
esp.LEDC.SetCH7_CONF0_IDLE_LV(invVal)
}
}
}