Lines Matching +full:- +full:e
1 // SPDX-License-Identifier: GPL-2.0
21 * 1. U-Boot parse cpu/dmc opp table from kernel dtb, anyone of
22 * "rockchip,low-temp = <...>" and "rockchip,high-temp = <...>" present in
25 * 1.1. When temperature trigger "rockchip,low-temp", increase 50mv voltage
26 * as target voltage. If target voltage is over "rockchip,max-volt",
27 * just set "rockchip,max-volt" as target voltage and lower 2 level freq,
29 * 1.2. When temperature trigger "rockchip,high-temp", just apply opp table[0]
32 * 2. U-Boot parse cpu/dmc thermal zone "trip-point-0" temperature from kernel
43 * uboot-wide-temperature {
45 * compatible = "rockchip,uboot-wide-temperature";
47 * cpu,low-temp-repeat;
48 * cpu,high-temp-repeat;
49 * dmc,low-temp-repeat;
50 * dmc,high-temp-repeat;
57 "/thermal-zones/soc-thermal/trips/trip-point-0"
59 "/thermal-zones/soc-thermal/cooling-maps"
122 .supply_name = "cpu-supply",
129 .supply_name = "center-supply",
141 temp < 0 ? "-" : "", integer, decimal_point); in temp2string()
145 struct pm_element *e) in wtemp_get_lowlevel_rate() argument
150 opp = e->opp; in wtemp_get_lowlevel_rate()
151 count = e->opp_nr; in wtemp_get_lowlevel_rate()
155 idx = (i <= level) ? 0 : i - level; in wtemp_get_lowlevel_rate()
163 static ulong __wtemp_clk_get_rate(struct pm_element *e) in __wtemp_clk_get_rate() argument
166 if (e->id == PM_DMC) in __wtemp_clk_get_rate()
169 return clk_get_rate(&e->clk); in __wtemp_clk_get_rate()
172 static ulong __wtemp_clk_set_rate(struct pm_element *e, ulong rate) in __wtemp_clk_set_rate() argument
175 if (e->id == PM_DMC) { in __wtemp_clk_set_rate()
180 rate = clk_set_rate(&e->clk, rate); in __wtemp_clk_set_rate()
185 static int __wtemp_regulator_get_value(struct pm_element *e) in __wtemp_regulator_get_value() argument
187 return regulator_get_value(e->supply); in __wtemp_regulator_get_value()
190 static int __wtemp_regulator_set_value(struct pm_element *e, int value) in __wtemp_regulator_set_value() argument
192 return regulator_set_value(e->supply, value); in __wtemp_regulator_set_value()
202 static void wtemp_dvfs_low_temp_adjust(struct udevice *dev, struct pm_element *e) in wtemp_dvfs_low_temp_adjust() argument
208 org_rate = __wtemp_clk_get_rate(e); in wtemp_dvfs_low_temp_adjust()
209 org_volt = __wtemp_regulator_get_value(e); in wtemp_dvfs_low_temp_adjust()
210 tgt_volt = org_volt + e->volt_diff; in wtemp_dvfs_low_temp_adjust()
211 if ((e->lmt.max_volt != -ENODATA) && (tgt_volt > e->lmt.max_volt)) { in wtemp_dvfs_low_temp_adjust()
212 tgt_volt = e->lmt.max_volt; in wtemp_dvfs_low_temp_adjust()
213 __wtemp_regulator_set_value(e, tgt_volt); in wtemp_dvfs_low_temp_adjust()
215 RATE_LOWER_LEVEL_N, priv->cpu); in wtemp_dvfs_low_temp_adjust()
216 __wtemp_clk_set_rate(e, tgt_rate); in wtemp_dvfs_low_temp_adjust()
218 __wtemp_regulator_set_value(e, tgt_volt); in wtemp_dvfs_low_temp_adjust()
223 rb_rate = __wtemp_clk_get_rate(e); in wtemp_dvfs_low_temp_adjust()
224 rb_volt = __wtemp_regulator_get_value(e); in wtemp_dvfs_low_temp_adjust()
227 e->name, tgt_rate, rb_rate); in wtemp_dvfs_low_temp_adjust()
230 e->name, tgt_volt, rb_volt); in wtemp_dvfs_low_temp_adjust()
232 printf("DVFS: %s(low): %ld->%ld Hz, %d->%d uV\n", in wtemp_dvfs_low_temp_adjust()
233 e->name, org_rate, rb_rate, org_volt, rb_volt); in wtemp_dvfs_low_temp_adjust()
239 * Just set opp table[0] volt and rate, i.e. the lowest performance.
241 static void wtemp_dvfs_high_temp_adjust(struct udevice *dev, struct pm_element *e) in wtemp_dvfs_high_temp_adjust() argument
247 org_rate = __wtemp_clk_get_rate(e); in wtemp_dvfs_high_temp_adjust()
249 tgt_rate = e->opp[0].hz; in wtemp_dvfs_high_temp_adjust()
250 __wtemp_clk_set_rate(e, tgt_rate); in wtemp_dvfs_high_temp_adjust()
251 rb_rate = __wtemp_clk_get_rate(e); in wtemp_dvfs_high_temp_adjust()
254 e->name, tgt_rate, rb_rate); in wtemp_dvfs_high_temp_adjust()
258 org_volt = __wtemp_regulator_get_value(e); in wtemp_dvfs_high_temp_adjust()
259 tgt_volt = e->opp[0].uv; in wtemp_dvfs_high_temp_adjust()
260 __wtemp_regulator_set_value(e, tgt_volt); in wtemp_dvfs_high_temp_adjust()
262 rb_volt = __wtemp_regulator_get_value(e); in wtemp_dvfs_high_temp_adjust()
265 e->name, tgt_volt, rb_volt); in wtemp_dvfs_high_temp_adjust()
267 printf("DVFS: %s(high): %ld->%ld Hz, %d->%d uV\n", in wtemp_dvfs_high_temp_adjust()
268 e->name, org_rate, tgt_rate, org_volt, tgt_volt); in wtemp_dvfs_high_temp_adjust()
271 static bool wtemp_dvfs_is_effect(struct pm_element *e, in wtemp_dvfs_is_effect() argument
275 if (e->lmt.ltemp_limit && temp <= e->lmt.low_temp) in wtemp_dvfs_is_effect()
280 if (e->lmt.tztemp_limit && temp >= e->lmt.tz_temp) in wtemp_dvfs_is_effect()
282 else if (e->lmt.htemp_limit && temp >= e->lmt.high_temp) in wtemp_dvfs_is_effect()
289 static int __wtemp_dvfs_apply(struct udevice *dev, struct pm_element *e, in __wtemp_dvfs_apply() argument
296 if (e->lmt.ltemp_limit && temp <= e->lmt.low_temp) { in __wtemp_dvfs_apply()
298 wtemp_dvfs_low_temp_adjust(dev, e); in __wtemp_dvfs_apply()
304 if (e->lmt.tztemp_limit && temp >= e->lmt.tz_temp) { in __wtemp_dvfs_apply()
306 wtemp_dvfs_high_temp_adjust(dev, e); in __wtemp_dvfs_apply()
307 } else if (e->lmt.htemp_limit && temp >= e->lmt.high_temp) { in __wtemp_dvfs_apply()
309 wtemp_dvfs_high_temp_adjust(dev, e); in __wtemp_dvfs_apply()
316 static int __wtemp_common_ofdata_to_platdata(ofnode node, struct pm_element *e) in __wtemp_common_ofdata_to_platdata() argument
324 if (!ofnode_read_u32(node, e->supply_name, &phandle)) { in __wtemp_common_ofdata_to_platdata()
326 ret = regulator_get_by_devname(supply.np->name, &e->supply); in __wtemp_common_ofdata_to_platdata()
329 e->name, supply.np->full_name, ret); in __wtemp_common_ofdata_to_platdata()
332 debug("DVFS: supply: %s\n", supply.np->full_name); in __wtemp_common_ofdata_to_platdata()
336 e->clk.id = clock[1]; in __wtemp_common_ofdata_to_platdata()
337 ret = rockchip_get_clk(&e->clk.dev); in __wtemp_common_ofdata_to_platdata()
339 printf("DVFS: %s: Get clk failed, ret=%d\n", e->name, ret); in __wtemp_common_ofdata_to_platdata()
344 /* Get opp-table & limit param */ in __wtemp_common_ofdata_to_platdata()
345 if (!ofnode_read_u32(node, "operating-points-v2", &phandle)) { in __wtemp_common_ofdata_to_platdata()
347 e->lmt.low_temp = ofnode_read_s32_default(opp_node, in __wtemp_common_ofdata_to_platdata()
348 "rockchip,low-temp", -ENODATA); in __wtemp_common_ofdata_to_platdata()
349 e->lmt.high_temp = ofnode_read_s32_default(opp_node, in __wtemp_common_ofdata_to_platdata()
350 "rockchip,high-temp", -ENODATA); in __wtemp_common_ofdata_to_platdata()
351 e->lmt.max_volt = ofnode_read_u32_default(opp_node, in __wtemp_common_ofdata_to_platdata()
352 "rockchip,max-volt", -ENODATA); in __wtemp_common_ofdata_to_platdata()
354 debug("DVFS: %s: low-temp=%d, high-temp=%d, max-volt=%d\n", in __wtemp_common_ofdata_to_platdata()
355 e->name, e->lmt.low_temp, e->lmt.high_temp, in __wtemp_common_ofdata_to_platdata()
356 e->lmt.max_volt); in __wtemp_common_ofdata_to_platdata()
359 if (e->opp_nr >= OPP_TABLE_MAX) { in __wtemp_common_ofdata_to_platdata()
364 ofnode_read_u64(node, "opp-hz", &hz); in __wtemp_common_ofdata_to_platdata()
365 ofnode_read_u32_array(node, "opp-microvolt", &uv, 1); in __wtemp_common_ofdata_to_platdata()
366 e->opp[e->opp_nr].hz = hz; in __wtemp_common_ofdata_to_platdata()
367 e->opp[e->opp_nr].uv = uv; in __wtemp_common_ofdata_to_platdata()
368 e->opp_nr++; in __wtemp_common_ofdata_to_platdata()
370 e->name, e->opp_nr - 1, in __wtemp_common_ofdata_to_platdata()
374 if (!e->opp_nr) { in __wtemp_common_ofdata_to_platdata()
375 printf("DVFS: %s: Can't find opp table\n", e->name); in __wtemp_common_ofdata_to_platdata()
376 return -EINVAL; in __wtemp_common_ofdata_to_platdata()
379 if (e->lmt.max_volt == -ENODATA) in __wtemp_common_ofdata_to_platdata()
380 e->lmt.max_volt = e->opp[e->opp_nr - 1].uv; in __wtemp_common_ofdata_to_platdata()
381 if (e->lmt.low_temp != -ENODATA) in __wtemp_common_ofdata_to_platdata()
382 e->lmt.ltemp_limit = true; in __wtemp_common_ofdata_to_platdata()
383 if (e->lmt.high_temp != -ENODATA) in __wtemp_common_ofdata_to_platdata()
384 e->lmt.htemp_limit = true; in __wtemp_common_ofdata_to_platdata()
393 struct pm_element *e; in wtemp_dvfs_apply() local
397 ret = thermal_get_temp(priv->thermal, &temp); in wtemp_dvfs_apply()
408 e = list_entry(node, struct pm_element, node); in wtemp_dvfs_apply()
409 __wtemp_dvfs_apply(dev, e, temp, PM_EVT_BOTH); in wtemp_dvfs_apply()
419 struct pm_element *e; in wtemp_dvfs_repeat_apply() local
425 ret = thermal_get_temp(priv->thermal, &temp); in wtemp_dvfs_repeat_apply()
434 e = list_entry(node, struct pm_element, node); in wtemp_dvfs_repeat_apply()
435 if (e->lmt.ltemp_repeat) in wtemp_dvfs_repeat_apply()
436 applied |= __wtemp_dvfs_apply(dev, e, temp, PM_EVT_LOW); in wtemp_dvfs_repeat_apply()
437 if (e->lmt.htemp_repeat) in wtemp_dvfs_repeat_apply()
438 applied |= __wtemp_dvfs_apply(dev, e, temp, PM_EVT_HIGH); in wtemp_dvfs_repeat_apply()
448 e = list_entry(node, struct pm_element, node); in wtemp_dvfs_repeat_apply()
449 if (e->lmt.ltemp_repeat && in wtemp_dvfs_repeat_apply()
450 !wtemp_dvfs_is_effect(e, temp, PM_EVT_LOW)) in wtemp_dvfs_repeat_apply()
452 if (e->lmt.htemp_repeat && in wtemp_dvfs_repeat_apply()
453 !wtemp_dvfs_is_effect(e, temp, PM_EVT_HIGH)) in wtemp_dvfs_repeat_apply()
459 e = list_entry(node, struct pm_element, node); in wtemp_dvfs_repeat_apply()
461 printf("DVFS: %s %s'c, %ld Hz, %d uV\n", e->name, in wtemp_dvfs_repeat_apply()
462 s_temp, __wtemp_clk_get_rate(e), in wtemp_dvfs_repeat_apply()
463 __wtemp_regulator_get_value(e)); in wtemp_dvfs_repeat_apply()
471 struct pm_element *e; in print_e_state() local
478 e = list_entry(node, struct pm_element, node); in print_e_state()
479 if (!e->lmt.ltemp_limit && in print_e_state()
480 !e->lmt.htemp_limit && !e->lmt.tztemp_limit) in print_e_state()
483 temp2string(e->lmt.tz_temp, s_tz, TEMP_STRING_LEN); in print_e_state()
484 temp2string(e->lmt.low_temp, s_low, TEMP_STRING_LEN); in print_e_state()
485 temp2string(e->lmt.high_temp, s_high, TEMP_STRING_LEN); in print_e_state()
488 e->name, e->lmt.ltemp_limit ? s_low : NULL, in print_e_state()
489 e->lmt.htemp_limit ? s_high : NULL, in print_e_state()
490 e->lmt.max_volt, in print_e_state()
491 e->lmt.tztemp_limit ? s_tz : NULL, in print_e_state()
492 e->lmt.htemp_repeat, e->lmt.ltemp_repeat); in print_e_state()
508 priv->cpu = &pm_cpu; in wtemp_dvfs_ofdata_to_platdata()
520 ret = __wtemp_common_ofdata_to_platdata(cpu, priv->cpu); in wtemp_dvfs_ofdata_to_platdata()
527 priv->cpu->lmt.ltemp_repeat = in wtemp_dvfs_ofdata_to_platdata()
528 dev_read_bool(dev, "cpu,low-temp-repeat"); in wtemp_dvfs_ofdata_to_platdata()
529 priv->cpu->lmt.htemp_repeat = in wtemp_dvfs_ofdata_to_platdata()
530 dev_read_bool(dev, "cpu,high-temp-repeat"); in wtemp_dvfs_ofdata_to_platdata()
532 list_add_tail(&priv->cpu->node, &pm_e_head); in wtemp_dvfs_ofdata_to_platdata()
536 priv->dmc = &pm_dmc; in wtemp_dvfs_ofdata_to_platdata()
547 ret = __wtemp_common_ofdata_to_platdata(dmc, priv->dmc); in wtemp_dvfs_ofdata_to_platdata()
551 priv->dmc->lmt.ltemp_repeat = in wtemp_dvfs_ofdata_to_platdata()
552 dev_read_bool(dev, "dmc,low-temp-repeat"); in wtemp_dvfs_ofdata_to_platdata()
553 priv->dmc->lmt.htemp_repeat = in wtemp_dvfs_ofdata_to_platdata()
554 dev_read_bool(dev, "dmc,high-temp-repeat"); in wtemp_dvfs_ofdata_to_platdata()
556 list_add_tail(&priv->dmc->node, &pm_e_head); in wtemp_dvfs_ofdata_to_platdata()
566 tz_temp = ofnode_read_s32_default(tz_trip0, "temperature", -ENODATA); in wtemp_dvfs_ofdata_to_platdata()
567 if (tz_temp == -ENODATA) { in wtemp_dvfs_ofdata_to_platdata()
579 ofnode_read_u32_array(node, "cooling-device", &phandle, 1); in wtemp_dvfs_ofdata_to_platdata()
584 priv->cpu->lmt.tztemp_limit = true; in wtemp_dvfs_ofdata_to_platdata()
585 priv->cpu->lmt.tz_temp = tz_temp; in wtemp_dvfs_ofdata_to_platdata()
587 priv->dmc->lmt.tztemp_limit = true; in wtemp_dvfs_ofdata_to_platdata()
588 priv->dmc->lmt.tz_temp = tz_temp; in wtemp_dvfs_ofdata_to_platdata()
619 ret = uclass_get_device(UCLASS_THERMAL, 0, &priv->thermal); in wtemp_dvfs_probe()
629 { .compatible = "rockchip,uboot-wide-temperature", },