root/drivers/thermal/power_allocator.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. mul_frac
  2. div_frac
  3. estimate_sustainable_power
  4. estimate_pid_constants
  5. pid_controller
  6. divvy_up_power
  7. allocate_power
  8. get_governor_trips
  9. reset_pid_controller
  10. allow_maximum_power
  11. power_allocator_bind
  12. power_allocator_unbind
  13. power_allocator_throttle

   1 /*
   2  * A power allocator to manage temperature
   3  *
   4  * Copyright (C) 2014 ARM Ltd.
   5  *
   6  * This program is free software; you can redistribute it and/or modify
   7  * it under the terms of the GNU General Public License version 2 as
   8  * published by the Free Software Foundation.
   9  *
  10  * This program is distributed "as is" WITHOUT ANY WARRANTY of any
  11  * kind, whether express or implied; without even the implied warranty
  12  * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13  * GNU General Public License for more details.
  14  */
  15 
  16 #define pr_fmt(fmt) "Power allocator: " fmt
  17 
  18 #include <linux/rculist.h>
  19 #include <linux/slab.h>
  20 #include <linux/thermal.h>
  21 
  22 #define CREATE_TRACE_POINTS
  23 #include <trace/events/thermal_power_allocator.h>
  24 
  25 #include "thermal_core.h"
  26 
  27 #define INVALID_TRIP -1
  28 
  29 #define FRAC_BITS 10
  30 #define int_to_frac(x) ((x) << FRAC_BITS)
  31 #define frac_to_int(x) ((x) >> FRAC_BITS)
  32 
  33 /**
  34  * mul_frac() - multiply two fixed-point numbers
  35  * @x:  first multiplicand
  36  * @y:  second multiplicand
  37  *
  38  * Return: the result of multiplying two fixed-point numbers.  The
  39  * result is also a fixed-point number.
  40  */
  41 static inline s64 mul_frac(s64 x, s64 y)
  42 {
  43         return (x * y) >> FRAC_BITS;
  44 }
  45 
  46 /**
  47  * div_frac() - divide two fixed-point numbers
  48  * @x:  the dividend
  49  * @y:  the divisor
  50  *
  51  * Return: the result of dividing two fixed-point numbers.  The
  52  * result is also a fixed-point number.
  53  */
  54 static inline s64 div_frac(s64 x, s64 y)
  55 {
  56         return div_s64(x << FRAC_BITS, y);
  57 }
  58 
  59 /**
  60  * struct power_allocator_params - parameters for the power allocator governor
  61  * @allocated_tzp:      whether we have allocated tzp for this thermal zone and
  62  *                      it needs to be freed on unbind
  63  * @err_integral:       accumulated error in the PID controller.
  64  * @prev_err:   error in the previous iteration of the PID controller.
  65  *              Used to calculate the derivative term.
  66  * @trip_switch_on:     first passive trip point of the thermal zone.  The
  67  *                      governor switches on when this trip point is crossed.
  68  *                      If the thermal zone only has one passive trip point,
  69  *                      @trip_switch_on should be INVALID_TRIP.
  70  * @trip_max_desired_temperature:       last passive trip point of the thermal
  71  *                                      zone.  The temperature we are
  72  *                                      controlling for.
  73  */
  74 struct power_allocator_params {
  75         bool allocated_tzp;
  76         s64 err_integral;
  77         s32 prev_err;
  78         int trip_switch_on;
  79         int trip_max_desired_temperature;
  80 };
  81 
  82 /**
  83  * estimate_sustainable_power() - Estimate the sustainable power of a thermal zone
  84  * @tz: thermal zone we are operating in
  85  *
  86  * For thermal zones that don't provide a sustainable_power in their
  87  * thermal_zone_params, estimate one.  Calculate it using the minimum
  88  * power of all the cooling devices as that gives a valid value that
  89  * can give some degree of functionality.  For optimal performance of
  90  * this governor, provide a sustainable_power in the thermal zone's
  91  * thermal_zone_params.
  92  */
  93 static u32 estimate_sustainable_power(struct thermal_zone_device *tz)
  94 {
  95         u32 sustainable_power = 0;
  96         struct thermal_instance *instance;
  97         struct power_allocator_params *params = tz->governor_data;
  98 
  99         list_for_each_entry(instance, &tz->thermal_instances, tz_node) {
 100                 struct thermal_cooling_device *cdev = instance->cdev;
 101                 u32 min_power;
 102 
 103                 if (instance->trip != params->trip_max_desired_temperature)
 104                         continue;
 105 
 106                 if (power_actor_get_min_power(cdev, tz, &min_power))
 107                         continue;
 108 
 109                 sustainable_power += min_power;
 110         }
 111 
 112         return sustainable_power;
 113 }
 114 
 115 /**
 116  * estimate_pid_constants() - Estimate the constants for the PID controller
 117  * @tz:         thermal zone for which to estimate the constants
 118  * @sustainable_power:  sustainable power for the thermal zone
 119  * @trip_switch_on:     trip point number for the switch on temperature
 120  * @control_temp:       target temperature for the power allocator governor
 121  * @force:      whether to force the update of the constants
 122  *
 123  * This function is used to update the estimation of the PID
 124  * controller constants in struct thermal_zone_parameters.
 125  * Sustainable power is provided in case it was estimated.  The
 126  * estimated sustainable_power should not be stored in the
 127  * thermal_zone_parameters so it has to be passed explicitly to this
 128  * function.
 129  *
 130  * If @force is not set, the values in the thermal zone's parameters
 131  * are preserved if they are not zero.  If @force is set, the values
 132  * in thermal zone's parameters are overwritten.
 133  */
 134 static void estimate_pid_constants(struct thermal_zone_device *tz,
 135                                    u32 sustainable_power, int trip_switch_on,
 136                                    int control_temp, bool force)
 137 {
 138         int ret;
 139         int switch_on_temp;
 140         u32 temperature_threshold;
 141 
 142         ret = tz->ops->get_trip_temp(tz, trip_switch_on, &switch_on_temp);
 143         if (ret)
 144                 switch_on_temp = 0;
 145 
 146         temperature_threshold = control_temp - switch_on_temp;
 147         /*
 148          * estimate_pid_constants() tries to find appropriate default
 149          * values for thermal zones that don't provide them. If a
 150          * system integrator has configured a thermal zone with two
 151          * passive trip points at the same temperature, that person
 152          * hasn't put any effort to set up the thermal zone properly
 153          * so just give up.
 154          */
 155         if (!temperature_threshold)
 156                 return;
 157 
 158         if (!tz->tzp->k_po || force)
 159                 tz->tzp->k_po = int_to_frac(sustainable_power) /
 160                         temperature_threshold;
 161 
 162         if (!tz->tzp->k_pu || force)
 163                 tz->tzp->k_pu = int_to_frac(2 * sustainable_power) /
 164                         temperature_threshold;
 165 
 166         if (!tz->tzp->k_i || force)
 167                 tz->tzp->k_i = int_to_frac(10) / 1000;
 168         /*
 169          * The default for k_d and integral_cutoff is 0, so we can
 170          * leave them as they are.
 171          */
 172 }
 173 
 174 /**
 175  * pid_controller() - PID controller
 176  * @tz: thermal zone we are operating in
 177  * @control_temp:       the target temperature in millicelsius
 178  * @max_allocatable_power:      maximum allocatable power for this thermal zone
 179  *
 180  * This PID controller increases the available power budget so that the
 181  * temperature of the thermal zone gets as close as possible to
 182  * @control_temp and limits the power if it exceeds it.  k_po is the
 183  * proportional term when we are overshooting, k_pu is the
 184  * proportional term when we are undershooting.  integral_cutoff is a
 185  * threshold below which we stop accumulating the error.  The
 186  * accumulated error is only valid if the requested power will make
 187  * the system warmer.  If the system is mostly idle, there's no point
 188  * in accumulating positive error.
 189  *
 190  * Return: The power budget for the next period.
 191  */
 192 static u32 pid_controller(struct thermal_zone_device *tz,
 193                           int control_temp,
 194                           u32 max_allocatable_power)
 195 {
 196         s64 p, i, d, power_range;
 197         s32 err, max_power_frac;
 198         u32 sustainable_power;
 199         struct power_allocator_params *params = tz->governor_data;
 200 
 201         max_power_frac = int_to_frac(max_allocatable_power);
 202 
 203         if (tz->tzp->sustainable_power) {
 204                 sustainable_power = tz->tzp->sustainable_power;
 205         } else {
 206                 sustainable_power = estimate_sustainable_power(tz);
 207                 estimate_pid_constants(tz, sustainable_power,
 208                                        params->trip_switch_on, control_temp,
 209                                        true);
 210         }
 211 
 212         err = control_temp - tz->temperature;
 213         err = int_to_frac(err);
 214 
 215         /* Calculate the proportional term */
 216         p = mul_frac(err < 0 ? tz->tzp->k_po : tz->tzp->k_pu, err);
 217 
 218         /*
 219          * Calculate the integral term
 220          *
 221          * if the error is less than cut off allow integration (but
 222          * the integral is limited to max power)
 223          */
 224         i = mul_frac(tz->tzp->k_i, params->err_integral);
 225 
 226         if (err < int_to_frac(tz->tzp->integral_cutoff)) {
 227                 s64 i_next = i + mul_frac(tz->tzp->k_i, err);
 228 
 229                 if (abs(i_next) < max_power_frac) {
 230                         i = i_next;
 231                         params->err_integral += err;
 232                 }
 233         }
 234 
 235         /*
 236          * Calculate the derivative term
 237          *
 238          * We do err - prev_err, so with a positive k_d, a decreasing
 239          * error (i.e. driving closer to the line) results in less
 240          * power being applied, slowing down the controller)
 241          */
 242         d = mul_frac(tz->tzp->k_d, err - params->prev_err);
 243         d = div_frac(d, tz->passive_delay);
 244         params->prev_err = err;
 245 
 246         power_range = p + i + d;
 247 
 248         /* feed-forward the known sustainable dissipatable power */
 249         power_range = sustainable_power + frac_to_int(power_range);
 250 
 251         power_range = clamp(power_range, (s64)0, (s64)max_allocatable_power);
 252 
 253         trace_thermal_power_allocator_pid(tz, frac_to_int(err),
 254                                           frac_to_int(params->err_integral),
 255                                           frac_to_int(p), frac_to_int(i),
 256                                           frac_to_int(d), power_range);
 257 
 258         return power_range;
 259 }
 260 
 261 /**
 262  * divvy_up_power() - divvy the allocated power between the actors
 263  * @req_power:  each actor's requested power
 264  * @max_power:  each actor's maximum available power
 265  * @num_actors: size of the @req_power, @max_power and @granted_power's array
 266  * @total_req_power: sum of @req_power
 267  * @power_range:        total allocated power
 268  * @granted_power:      output array: each actor's granted power
 269  * @extra_actor_power:  an appropriately sized array to be used in the
 270  *                      function as temporary storage of the extra power given
 271  *                      to the actors
 272  *
 273  * This function divides the total allocated power (@power_range)
 274  * fairly between the actors.  It first tries to give each actor a
 275  * share of the @power_range according to how much power it requested
 276  * compared to the rest of the actors.  For example, if only one actor
 277  * requests power, then it receives all the @power_range.  If
 278  * three actors each requests 1mW, each receives a third of the
 279  * @power_range.
 280  *
 281  * If any actor received more than their maximum power, then that
 282  * surplus is re-divvied among the actors based on how far they are
 283  * from their respective maximums.
 284  *
 285  * Granted power for each actor is written to @granted_power, which
 286  * should've been allocated by the calling function.
 287  */
 288 static void divvy_up_power(u32 *req_power, u32 *max_power, int num_actors,
 289                            u32 total_req_power, u32 power_range,
 290                            u32 *granted_power, u32 *extra_actor_power)
 291 {
 292         u32 extra_power, capped_extra_power;
 293         int i;
 294 
 295         /*
 296          * Prevent division by 0 if none of the actors request power.
 297          */
 298         if (!total_req_power)
 299                 total_req_power = 1;
 300 
 301         capped_extra_power = 0;
 302         extra_power = 0;
 303         for (i = 0; i < num_actors; i++) {
 304                 u64 req_range = (u64)req_power[i] * power_range;
 305 
 306                 granted_power[i] = DIV_ROUND_CLOSEST_ULL(req_range,
 307                                                          total_req_power);
 308 
 309                 if (granted_power[i] > max_power[i]) {
 310                         extra_power += granted_power[i] - max_power[i];
 311                         granted_power[i] = max_power[i];
 312                 }
 313 
 314                 extra_actor_power[i] = max_power[i] - granted_power[i];
 315                 capped_extra_power += extra_actor_power[i];
 316         }
 317 
 318         if (!extra_power)
 319                 return;
 320 
 321         /*
 322          * Re-divvy the reclaimed extra among actors based on
 323          * how far they are from the max
 324          */
 325         extra_power = min(extra_power, capped_extra_power);
 326         if (capped_extra_power > 0)
 327                 for (i = 0; i < num_actors; i++)
 328                         granted_power[i] += (extra_actor_power[i] *
 329                                         extra_power) / capped_extra_power;
 330 }
 331 
 332 static int allocate_power(struct thermal_zone_device *tz,
 333                           int control_temp)
 334 {
 335         struct thermal_instance *instance;
 336         struct power_allocator_params *params = tz->governor_data;
 337         u32 *req_power, *max_power, *granted_power, *extra_actor_power;
 338         u32 *weighted_req_power;
 339         u32 total_req_power, max_allocatable_power, total_weighted_req_power;
 340         u32 total_granted_power, power_range;
 341         int i, num_actors, total_weight, ret = 0;
 342         int trip_max_desired_temperature = params->trip_max_desired_temperature;
 343 
 344         mutex_lock(&tz->lock);
 345 
 346         num_actors = 0;
 347         total_weight = 0;
 348         list_for_each_entry(instance, &tz->thermal_instances, tz_node) {
 349                 if ((instance->trip == trip_max_desired_temperature) &&
 350                     cdev_is_power_actor(instance->cdev)) {
 351                         num_actors++;
 352                         total_weight += instance->weight;
 353                 }
 354         }
 355 
 356         if (!num_actors) {
 357                 ret = -ENODEV;
 358                 goto unlock;
 359         }
 360 
 361         /*
 362          * We need to allocate five arrays of the same size:
 363          * req_power, max_power, granted_power, extra_actor_power and
 364          * weighted_req_power.  They are going to be needed until this
 365          * function returns.  Allocate them all in one go to simplify
 366          * the allocation and deallocation logic.
 367          */
 368         BUILD_BUG_ON(sizeof(*req_power) != sizeof(*max_power));
 369         BUILD_BUG_ON(sizeof(*req_power) != sizeof(*granted_power));
 370         BUILD_BUG_ON(sizeof(*req_power) != sizeof(*extra_actor_power));
 371         BUILD_BUG_ON(sizeof(*req_power) != sizeof(*weighted_req_power));
 372         req_power = kcalloc(num_actors * 5, sizeof(*req_power), GFP_KERNEL);
 373         if (!req_power) {
 374                 ret = -ENOMEM;
 375                 goto unlock;
 376         }
 377 
 378         max_power = &req_power[num_actors];
 379         granted_power = &req_power[2 * num_actors];
 380         extra_actor_power = &req_power[3 * num_actors];
 381         weighted_req_power = &req_power[4 * num_actors];
 382 
 383         i = 0;
 384         total_weighted_req_power = 0;
 385         total_req_power = 0;
 386         max_allocatable_power = 0;
 387 
 388         list_for_each_entry(instance, &tz->thermal_instances, tz_node) {
 389                 int weight;
 390                 struct thermal_cooling_device *cdev = instance->cdev;
 391 
 392                 if (instance->trip != trip_max_desired_temperature)
 393                         continue;
 394 
 395                 if (!cdev_is_power_actor(cdev))
 396                         continue;
 397 
 398                 if (cdev->ops->get_requested_power(cdev, tz, &req_power[i]))
 399                         continue;
 400 
 401                 if (!total_weight)
 402                         weight = 1 << FRAC_BITS;
 403                 else
 404                         weight = instance->weight;
 405 
 406                 weighted_req_power[i] = frac_to_int(weight * req_power[i]);
 407 
 408                 if (power_actor_get_max_power(cdev, tz, &max_power[i]))
 409                         continue;
 410 
 411                 total_req_power += req_power[i];
 412                 max_allocatable_power += max_power[i];
 413                 total_weighted_req_power += weighted_req_power[i];
 414 
 415                 i++;
 416         }
 417 
 418         power_range = pid_controller(tz, control_temp, max_allocatable_power);
 419 
 420         divvy_up_power(weighted_req_power, max_power, num_actors,
 421                        total_weighted_req_power, power_range, granted_power,
 422                        extra_actor_power);
 423 
 424         total_granted_power = 0;
 425         i = 0;
 426         list_for_each_entry(instance, &tz->thermal_instances, tz_node) {
 427                 if (instance->trip != trip_max_desired_temperature)
 428                         continue;
 429 
 430                 if (!cdev_is_power_actor(instance->cdev))
 431                         continue;
 432 
 433                 power_actor_set_power(instance->cdev, instance,
 434                                       granted_power[i]);
 435                 total_granted_power += granted_power[i];
 436 
 437                 i++;
 438         }
 439 
 440         trace_thermal_power_allocator(tz, req_power, total_req_power,
 441                                       granted_power, total_granted_power,
 442                                       num_actors, power_range,
 443                                       max_allocatable_power, tz->temperature,
 444                                       control_temp - tz->temperature);
 445 
 446         kfree(req_power);
 447 unlock:
 448         mutex_unlock(&tz->lock);
 449 
 450         return ret;
 451 }
 452 
 453 /**
 454  * get_governor_trips() - get the number of the two trip points that are key for this governor
 455  * @tz: thermal zone to operate on
 456  * @params:     pointer to private data for this governor
 457  *
 458  * The power allocator governor works optimally with two trips points:
 459  * a "switch on" trip point and a "maximum desired temperature".  These
 460  * are defined as the first and last passive trip points.
 461  *
 462  * If there is only one trip point, then that's considered to be the
 463  * "maximum desired temperature" trip point and the governor is always
 464  * on.  If there are no passive or active trip points, then the
 465  * governor won't do anything.  In fact, its throttle function
 466  * won't be called at all.
 467  */
 468 static void get_governor_trips(struct thermal_zone_device *tz,
 469                                struct power_allocator_params *params)
 470 {
 471         int i, last_active, last_passive;
 472         bool found_first_passive;
 473 
 474         found_first_passive = false;
 475         last_active = INVALID_TRIP;
 476         last_passive = INVALID_TRIP;
 477 
 478         for (i = 0; i < tz->trips; i++) {
 479                 enum thermal_trip_type type;
 480                 int ret;
 481 
 482                 ret = tz->ops->get_trip_type(tz, i, &type);
 483                 if (ret) {
 484                         dev_warn(&tz->device,
 485                                  "Failed to get trip point %d type: %d\n", i,
 486                                  ret);
 487                         continue;
 488                 }
 489 
 490                 if (type == THERMAL_TRIP_PASSIVE) {
 491                         if (!found_first_passive) {
 492                                 params->trip_switch_on = i;
 493                                 found_first_passive = true;
 494                         } else  {
 495                                 last_passive = i;
 496                         }
 497                 } else if (type == THERMAL_TRIP_ACTIVE) {
 498                         last_active = i;
 499                 } else {
 500                         break;
 501                 }
 502         }
 503 
 504         if (last_passive != INVALID_TRIP) {
 505                 params->trip_max_desired_temperature = last_passive;
 506         } else if (found_first_passive) {
 507                 params->trip_max_desired_temperature = params->trip_switch_on;
 508                 params->trip_switch_on = INVALID_TRIP;
 509         } else {
 510                 params->trip_switch_on = INVALID_TRIP;
 511                 params->trip_max_desired_temperature = last_active;
 512         }
 513 }
 514 
 515 static void reset_pid_controller(struct power_allocator_params *params)
 516 {
 517         params->err_integral = 0;
 518         params->prev_err = 0;
 519 }
 520 
 521 static void allow_maximum_power(struct thermal_zone_device *tz)
 522 {
 523         struct thermal_instance *instance;
 524         struct power_allocator_params *params = tz->governor_data;
 525 
 526         mutex_lock(&tz->lock);
 527         list_for_each_entry(instance, &tz->thermal_instances, tz_node) {
 528                 if ((instance->trip != params->trip_max_desired_temperature) ||
 529                     (!cdev_is_power_actor(instance->cdev)))
 530                         continue;
 531 
 532                 instance->target = 0;
 533                 mutex_lock(&instance->cdev->lock);
 534                 instance->cdev->updated = false;
 535                 mutex_unlock(&instance->cdev->lock);
 536                 thermal_cdev_update(instance->cdev);
 537         }
 538         mutex_unlock(&tz->lock);
 539 }
 540 
 541 /**
 542  * power_allocator_bind() - bind the power_allocator governor to a thermal zone
 543  * @tz: thermal zone to bind it to
 544  *
 545  * Initialize the PID controller parameters and bind it to the thermal
 546  * zone.
 547  *
 548  * Return: 0 on success, or -ENOMEM if we ran out of memory.
 549  */
 550 static int power_allocator_bind(struct thermal_zone_device *tz)
 551 {
 552         int ret;
 553         struct power_allocator_params *params;
 554         int control_temp;
 555 
 556         params = kzalloc(sizeof(*params), GFP_KERNEL);
 557         if (!params)
 558                 return -ENOMEM;
 559 
 560         if (!tz->tzp) {
 561                 tz->tzp = kzalloc(sizeof(*tz->tzp), GFP_KERNEL);
 562                 if (!tz->tzp) {
 563                         ret = -ENOMEM;
 564                         goto free_params;
 565                 }
 566 
 567                 params->allocated_tzp = true;
 568         }
 569 
 570         if (!tz->tzp->sustainable_power)
 571                 dev_warn(&tz->device, "power_allocator: sustainable_power will be estimated\n");
 572 
 573         get_governor_trips(tz, params);
 574 
 575         if (tz->trips > 0) {
 576                 ret = tz->ops->get_trip_temp(tz,
 577                                         params->trip_max_desired_temperature,
 578                                         &control_temp);
 579                 if (!ret)
 580                         estimate_pid_constants(tz, tz->tzp->sustainable_power,
 581                                                params->trip_switch_on,
 582                                                control_temp, false);
 583         }
 584 
 585         reset_pid_controller(params);
 586 
 587         tz->governor_data = params;
 588 
 589         return 0;
 590 
 591 free_params:
 592         kfree(params);
 593 
 594         return ret;
 595 }
 596 
 597 static void power_allocator_unbind(struct thermal_zone_device *tz)
 598 {
 599         struct power_allocator_params *params = tz->governor_data;
 600 
 601         dev_dbg(&tz->device, "Unbinding from thermal zone %d\n", tz->id);
 602 
 603         if (params->allocated_tzp) {
 604                 kfree(tz->tzp);
 605                 tz->tzp = NULL;
 606         }
 607 
 608         kfree(tz->governor_data);
 609         tz->governor_data = NULL;
 610 }
 611 
 612 static int power_allocator_throttle(struct thermal_zone_device *tz, int trip)
 613 {
 614         int ret;
 615         int switch_on_temp, control_temp;
 616         struct power_allocator_params *params = tz->governor_data;
 617 
 618         /*
 619          * We get called for every trip point but we only need to do
 620          * our calculations once
 621          */
 622         if (trip != params->trip_max_desired_temperature)
 623                 return 0;
 624 
 625         ret = tz->ops->get_trip_temp(tz, params->trip_switch_on,
 626                                      &switch_on_temp);
 627         if (!ret && (tz->temperature < switch_on_temp)) {
 628                 tz->passive = 0;
 629                 reset_pid_controller(params);
 630                 allow_maximum_power(tz);
 631                 return 0;
 632         }
 633 
 634         tz->passive = 1;
 635 
 636         ret = tz->ops->get_trip_temp(tz, params->trip_max_desired_temperature,
 637                                 &control_temp);
 638         if (ret) {
 639                 dev_warn(&tz->device,
 640                          "Failed to get the maximum desired temperature: %d\n",
 641                          ret);
 642                 return ret;
 643         }
 644 
 645         return allocate_power(tz, control_temp);
 646 }
 647 
 648 static struct thermal_governor thermal_gov_power_allocator = {
 649         .name           = "power_allocator",
 650         .bind_to_tz     = power_allocator_bind,
 651         .unbind_from_tz = power_allocator_unbind,
 652         .throttle       = power_allocator_throttle,
 653 };
 654 THERMAL_GOVERNOR_DECLARE(thermal_gov_power_allocator);

/* [<][>][^][v][top][bottom][index][help] */