mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/next/linux-next.git
synced 2025-01-01 10:42:11 +00:00
pwm: core: export pwm_get_state_hw()
Export the pwm_get_state_hw() function. This is useful in cases where we want to know what the hardware is actually doing, rather than what what we requested it should do. Locking had to be rearranged to ensure that the chip is still operational before trying to access ops now that this can be called from outside the pwm core. Signed-off-by: David Lechner <dlechner@baylibre.com> Link: https://lore.kernel.org/r/20241029-pwm-export-pwm_get_state_hw-v2-1-03ba063a3230@baylibre.com [ukleinek: Add dummy for !CONFIG_PWM] Signed-off-by: Uwe Kleine-König <ukleinek@kernel.org>
This commit is contained in:
parent
fdb62922ae
commit
2ea25aab93
@ -718,40 +718,54 @@ int pwm_apply_atomic(struct pwm_device *pwm, const struct pwm_state *state)
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(pwm_apply_atomic);
|
||||
|
||||
static int pwm_get_state_hw(struct pwm_device *pwm, struct pwm_state *state)
|
||||
/**
|
||||
* pwm_get_state_hw() - get the current PWM state from hardware
|
||||
* @pwm: PWM device
|
||||
* @state: state to fill with the current PWM state
|
||||
*
|
||||
* Similar to pwm_get_state() but reads the current PWM state from hardware
|
||||
* instead of the requested state.
|
||||
*
|
||||
* Returns: 0 on success or a negative error code on failure.
|
||||
* Context: May sleep.
|
||||
*/
|
||||
int pwm_get_state_hw(struct pwm_device *pwm, struct pwm_state *state)
|
||||
{
|
||||
struct pwm_chip *chip = pwm->chip;
|
||||
const struct pwm_ops *ops = chip->ops;
|
||||
int ret = -EOPNOTSUPP;
|
||||
|
||||
might_sleep();
|
||||
|
||||
guard(pwmchip)(chip);
|
||||
|
||||
if (!chip->operational)
|
||||
return -ENODEV;
|
||||
|
||||
if (ops->read_waveform) {
|
||||
char wfhw[WFHWSIZE];
|
||||
struct pwm_waveform wf;
|
||||
|
||||
BUG_ON(WFHWSIZE < ops->sizeof_wfhw);
|
||||
|
||||
scoped_guard(pwmchip, chip) {
|
||||
ret = __pwm_read_waveform(chip, pwm, &wfhw);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = __pwm_read_waveform(chip, pwm, &wfhw);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
ret = __pwm_round_waveform_fromhw(chip, pwm, &wfhw, &wf);
|
||||
if (ret)
|
||||
return ret;
|
||||
}
|
||||
ret = __pwm_round_waveform_fromhw(chip, pwm, &wfhw, &wf);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
pwm_wf2state(&wf, state);
|
||||
|
||||
} else if (ops->get_state) {
|
||||
scoped_guard(pwmchip, chip)
|
||||
ret = ops->get_state(chip, pwm, state);
|
||||
|
||||
ret = ops->get_state(chip, pwm, state);
|
||||
trace_pwm_get(pwm, state, ret);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL_GPL(pwm_get_state_hw);
|
||||
|
||||
/**
|
||||
* pwm_adjust_config() - adjust the current PWM config to the PWM arguments
|
||||
|
@ -370,6 +370,7 @@ int pwm_get_waveform_might_sleep(struct pwm_device *pwm, struct pwm_waveform *wf
|
||||
int pwm_set_waveform_might_sleep(struct pwm_device *pwm, const struct pwm_waveform *wf, bool exact);
|
||||
int pwm_apply_might_sleep(struct pwm_device *pwm, const struct pwm_state *state);
|
||||
int pwm_apply_atomic(struct pwm_device *pwm, const struct pwm_state *state);
|
||||
int pwm_get_state_hw(struct pwm_device *pwm, struct pwm_state *state);
|
||||
int pwm_adjust_config(struct pwm_device *pwm);
|
||||
|
||||
/**
|
||||
@ -494,6 +495,11 @@ static inline int pwm_apply_atomic(struct pwm_device *pwm,
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
static inline int pwm_get_state_hw(struct pwm_device *pwm, struct pwm_state *state)
|
||||
{
|
||||
return -EOPNOTSUPP;
|
||||
}
|
||||
|
||||
static inline int pwm_adjust_config(struct pwm_device *pwm)
|
||||
{
|
||||
return -EOPNOTSUPP;
|
||||
|
Loading…
Reference in New Issue
Block a user