lkml.org 
[lkml]   [2010]   [May]   [10]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    From
    Subject[110/117] cpuidle: Fix incorrect optimization
    2.6.33-stable review patch.  If anyone has any objections, please let us know.

    ------------------

    From: Arjan van de Ven <arjan@linux.intel.com>

    commit 1c6fe0364fa7bf28248488753ee0afb6b759cd04 upstream.

    commit 672917dcc78 ("cpuidle: menu governor: reduce latency on exit")
    added an optimization, where the analysis on the past idle period moved
    from the end of idle, to the beginning of the new idle.

    Unfortunately, this optimization had a bug where it zeroed one key
    variable for new use, that is needed for the analysis. The fix is
    simple, zero the variable after doing the work from the previous idle.

    During the audit of the code that found this issue, another issue was
    also found; the ->measured_us data structure member is never set, a
    local variable is always used instead.

    Signed-off-by: Arjan van de Ven <arjan@linux.intel.com>
    Cc: Corrado Zoccolo <czoccolo@gmail.com>
    Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
    Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>

    ---
    drivers/cpuidle/governors/menu.c | 9 ++++-----
    1 file changed, 4 insertions(+), 5 deletions(-)

    --- a/drivers/cpuidle/governors/menu.c
    +++ b/drivers/cpuidle/governors/menu.c
    @@ -101,7 +101,6 @@ struct menu_device {

    unsigned int expected_us;
    u64 predicted_us;
    - unsigned int measured_us;
    unsigned int exit_us;
    unsigned int bucket;
    u64 correction_factor[BUCKETS];
    @@ -187,14 +186,14 @@ static int menu_select(struct cpuidle_de
    int i;
    int multiplier;

    - data->last_state_idx = 0;
    - data->exit_us = 0;
    -
    if (data->needs_update) {
    menu_update(dev);
    data->needs_update = 0;
    }

    + data->last_state_idx = 0;
    + data->exit_us = 0;
    +
    /* Special case when user has set very strict latency requirement */
    if (unlikely(latency_req == 0))
    return 0;
    @@ -294,7 +293,7 @@ static void menu_update(struct cpuidle_d
    new_factor = data->correction_factor[data->bucket]
    * (DECAY - 1) / DECAY;

    - if (data->expected_us > 0 && data->measured_us < MAX_INTERESTING)
    + if (data->expected_us > 0 && measured_us < MAX_INTERESTING)
    new_factor += RESOLUTION * measured_us / data->expected_us;
    else
    /*



    \
     
     \ /
      Last update: 2010-05-12 10:15    [W:0.020 / U:213.952 seconds]
    ©2003-2016 Jasper Spaans. hosted at Digital OceanAdvertise on this site