• Viresh Kumar's avatar
    cpufreq: add support for intermediate (stable) frequencies · 1c03a2d0
    Viresh Kumar authored
    Douglas Anderson, recently pointed out an interesting problem due to which
    udelay() was expiring earlier than it should.
    
    While transitioning between frequencies few platforms may temporarily switch to
    a stable frequency, waiting for the main PLL to stabilize.
    
    For example: When we transition between very low frequencies on exynos, like
    between 200MHz and 300MHz, we may temporarily switch to a PLL running at 800MHz.
    No CPUFREQ notification is sent for that. That means there's a period of time
    when we're running at 800MHz but loops_per_jiffy is calibrated at between 200MHz
    and 300MHz. And so udelay behaves badly.
    
    To get this fixed in a generic way, introduce another set of callbacks
    get_intermediate() and target_intermediate(), only for drivers with
    target_index() and CPUFREQ_ASYNC_NOTIFICATION unset.
    
    get_intermediate() should return a stable intermediate frequency platform wants
    to switch to, and target_intermediate() should set CPU to that frequency,
    before jumping to the frequency corresponding to 'index'. Core will take care of
    sending notifications and driver doesn't have to handle them in
    target_intermediate() or target_index().
    
    NOTE: ->target_index() should restore to policy->restore_freq in case of
    failures as core would send notifications for that.
    Tested-by: default avatarStephen Warren <swarren@nvidia.com>
    Signed-off-by: default avatarViresh Kumar <viresh.kumar@linaro.org>
    Reviewed-by: default avatarDoug Anderson <dianders@chromium.org>
    Signed-off-by: default avatarRafael J. Wysocki <rafael.j.wysocki@intel.com>
    1c03a2d0
cpufreq.c 64.5 KB