Open noelleclement opened 4 years ago
^^ @wentongwu @nashif @ceolin @pabigot clock control API enhancement proposal in context of power management
^^ @wentongwu @nashif @ceolin @pabigot clock control API enhancement proposal in context of power management
@erwango I will give a +1 to this enhancement. I am in need of implementing stop mode on the STM32F411 which does not have LPTIM. I am able to get it into stop mode using LL libraries, and am able to configure an alarm which wakes the device up, but since the system clock does not resume it does not properly resume operation.
In a slack conversation I outlined what I think is a general solution, assuming the problem is that the system comes back up after a sleep where context (memory and instruction pointer) has not been lost, but the system clock has reset to zero.
That is to add API so that the uint64_t curr_tick
in kernel/timeout.c
that is the basis of all measures of system time can be asynchronously advanced by a given amount (corresponding to the duration of the suspenction) or set to a specific value (e.g. the duration in ticks since an epoch, when the time since epoch in seconds can be obtained from an RTC). A POSIX time_t
* TICKS_PER_SEC for example. The latter, if done every time the system comes up, would even ensure a monotonic non-decreasing system clock over sleeps where all context is lost (ignoring skew between the system clock and the external time source, which can be measured and compensated for using #28977).
This should "just work", even if there were pending timeouts when the system went to sleep. They'll fire, but late if they were scheduled during suspension. Anything that tries to track k_cycle_get_32()
values would be discontinuous, as that counter would restart from zero, but nothing's supposed to be using that for long durations anyway.
The wakeup process would have to be controlled so curr_ticks
can be advanced during wakeup before anything else touches time.
@pabigot Thanks for this analysis! Do you plan to work on such API ?
Plan; no. Desire; yes. It's not directly relevant to the folks who fund my Zephyr work, but I might get to it anyway in hopes it'll push #28977 along in its path to merge (coming up on two months, no reviews, sigh).
Absent other prioritization it won't be until the end of the month, if then: I have to get the new work queue stuff ready and make progress on device power management.
Thanks for the additional comment @pabigot! However, I'd like to point out that I believe this issue would still be relevant even if such an API would be implemented, as this issue has more to do with the SoC's clock reconfiguration required after wake up from a low-power mode. In my case the STM32L1x SoC defaults to the MSI clock source after wake up from 'stop mode', while I require the HSI, thus the additional step in the 'power state exit' is required.
Yes, I agree, part of this involves being able to re-initialize a driver at a point other than system startup. That's also desirable to completely solve #19448.
Yes that is exactly where I am stuck right now on the F4 -- I am able to enter stop mode, and wake up, but nothing further until clocks are reinitialized. I hadn't thought about those other issues you mentioned with regards to advancing the kernel clock after sleep, but that makes sense. That seems to be a more general requirement for low power mode on any device, I would think.
Either way I look forward to any progress on this, and would be happy to contribute/test where I can to help move this forward.
I've thought about this point and maybe one idea to make current topic progress might be for now to extend stm32 clock API with the missing function. Limiting the work to stm32 might allow to progress faster and it doesn't prevent to be integrated in the common API. An example of vendor specific API extension can be found here: https://github.com/zephyrproject-rtos/zephyr/pull/29810.
Something I think is important if this is going to be considered for a larger (power management) infrastructural change:
During my current debugging I've observed that reconfiguring the SoC system clock during the power management subsystem's exit function (_pm_power_state_exit_post_ops()
) might be too late in the post wake-up interrupt sequence. Just as a bit of a dummy example: a lot of garbage characters (most probably printk's that I put in for testing) are printed in my serial console upon wake-up, suggesting that clock reconfiguration hasn't been completed yet, when the kernel is already continuing its work. At some point it continues as usual, so the clock reconfiguration itself works fine, it's just the timing of it that seems to create this problem.
I can imagine that these kind of actions should be performed at (newly implemented) location that is closer to the wake-up interrupt time. This might tie nicely into this comment in #30590 where it's suggested that maybe another infrastructure is required for a 'scheduled wake-up' timeout.
Hi @nordic-krch,
This issue, marked as an Enhancement, was opened a while ago and did not get any traction. It was just assigned to you based on the labels. If you don't consider yourself the right person to address this issue, please re-assing it to the right person.
Please take a moment to review if the issue is still relevant to the project. If it is, please provide feedback and direction on how to move forward. If it is not, has already been addressed, is a duplicate, or is no longer relevant, please close it with a short comment explaining the reason.
@noelleclement you are also encouraged to help moving this issue forward by providing additional information and confirming this request/issue is still relevant to you.
Thanks!
Is your enhancement proposal related to a problem? Please describe. As described here clock reconfiguration is required after waking up from stop mode (STM32 SoCs). With the current STM32 clock_control implementation in
clock_stm32_ll_common.c
, the concerning function (static int stm32_clock_control_init(struct device *dev)
) is static and thus not callable outside of the scope. This can create problems when the function needs to be called after wake up, for example in the power management functions (such as SoC specificvoid _sys_pm_power_state_exit_post_ops(enum power_states state)
).Describe the solution you'd like A change to the concerning file (clock_stm32_ll_common.c) that would allow reconfiguration of the clock outside of the file's scope.
Describe alternatives you've considered My current (short-term) solution (as recommended by @erwango) has been to create a separate non-static initialization function, which is called by the initialization function called by the kernel:
static int stm32_clock_control_init(struct device *dev) { return stm32_clock_control_real_init(dev); }
However, this is clearly not a long-term solution, since it creates a vulnerability.
Another alternative is to add the function to the API. However, it currently is not part of the clock_control_driver_api struct, which would mean that this should be adapted too. This again would create the concern of vulnerabilities, so advice on a specific solution is highly appreciated.
Additional context This specific issue is important for the application I'm developing myself (custom board, STM32L1x SoC, power management priorities), but is also of importance for other (STM32) SoCs that require clock reconfiguration after exiting a low-power mode. Thus, there is overlap with the power management roadmap.