32 uint8_t cmp_index,
bool invert,
bool auto_board_init)
34 gptmr_(reinterpret_cast<GPTMR_Type*>(pwm)),
36 pwm_index_(pwm_index),
37 cmp_index_(cmp_index),
39 auto_board_init_(auto_board_init),
49 return ErrorCode::INIT_ERR;
56 else if (value > 1.0f)
61#if LIBXR_HPM_PWM_SUPPORTED
62 const float duty_percent = value * 100.0f;
63 if (pwm_update_duty_edge_aligned(pwm_, cmp_index_, duty_percent) != status_success)
65 return ErrorCode::FAILED;
67#elif LIBXR_HPM_GPTMR_PWM_FALLBACK
70 uint32_t cmp =
static_cast<uint32_t
>(
static_cast<float>(reload_) * value);
75 else if (cmp >= reload_)
79 gptmr_update_cmp(gptmr_, pwm_index_, cmp_index_, cmp);
82 return ErrorCode::NOT_SUPPORT;
92 return ErrorCode::ARG_ERR;
95 uint32_t clock_hz = 0u;
97#if LIBXR_HPM_GPTMR_PWM_FALLBACK && LIBXR_HPM_PWM_HAS_BOARD_HELPER
98 if (auto_board_init_ && gptmr_ !=
nullptr)
102 clock_hz = board_init_gptmr_clock(gptmr_);
103 board_init_gptmr_channel_pin(gptmr_, pwm_index_,
true);
109 clock_hz = clock_get_frequency(clock_);
114 return ErrorCode::INIT_ERR;
117 uint32_t reload = clock_hz / config.
frequency;
118 if (reload == 0u || reload > 0xFFFFFFu)
120 return ErrorCode::INIT_ERR;
124#if LIBXR_HPM_PWM_SUPPORTED
125 pwm_stop_counter(pwm_);
127 pwm_config_t pwm_config{};
128 pwm_cmp_config_t cmp_config{};
130 pwm_get_default_pwm_config(pwm_, &pwm_config);
131 pwm_get_default_cmp_config(pwm_, &cmp_config);
133 pwm_config.enable_output =
true;
134 pwm_config.invert_output = invert_;
135 pwm_config.dead_zone_in_half_cycle = 0;
137 pwm_set_reload(pwm_, 0, reload_);
138 pwm_set_start_count(pwm_, 0, 0);
140 cmp_config.mode = pwm_cmp_mode_output_compare;
141 cmp_config.cmp = reload_ + 1;
142 cmp_config.update_trigger = pwm_shadow_register_update_on_modify;
144 if (pwm_setup_waveform(pwm_, pwm_index_, &pwm_config, cmp_index_, &cmp_config, 1) !=
147 return ErrorCode::INIT_ERR;
150 pwm_issue_shadow_register_lock_event(pwm_);
151#elif LIBXR_HPM_GPTMR_PWM_FALLBACK
152 if (gptmr_ ==
nullptr)
154 return ErrorCode::ARG_ERR;
157 const uint8_t reload_cmp_index = ResolveGptmrReloadCmpIndex(cmp_index_);
158 if (reload_cmp_index == kInvalidCmpIndex)
160 return ErrorCode::ARG_ERR;
165 gptmr_stop_counter(gptmr_, pwm_index_);
167 gptmr_channel_config_t cfg;
168 gptmr_channel_get_default_config(gptmr_, &cfg);
169 cfg.mode = gptmr_work_mode_no_capture;
170 cfg.cmp_initial_polarity_high = invert_;
171 cfg.enable_cmp_output =
true;
172 cfg.reload = reload_;
173 cfg.cmp[cmp_index_] = reload_ / 2u;
174 cfg.cmp[reload_cmp_index] = reload_;
176 if (gptmr_channel_config(gptmr_, pwm_index_, &cfg,
false) != status_success)
178 return ErrorCode::INIT_ERR;
180 gptmr_channel_reset_count(gptmr_, pwm_index_);
182 return ErrorCode::NOT_SUPPORT;
186 return ErrorCode::OK;
HPMPWM(LibXRHpmPwmType *pwm, clock_name_t clock, uint8_t pwm_index, uint8_t cmp_index, bool invert=false, bool auto_board_init=true)
构造 HPM PWM 对象 / Construct an HPM PWM object.