Lines Matching +full:avg +full:- +full:samples
1 // SPDX-License-Identifier: GPL-2.0-only
8 #include <linux/clk-provider.h>
15 #include <linux/nvmem-consumer.h>
20 #include <dt-bindings/thermal/mediatek,lvts-thermal.h>
83 #define LVTS_COEFF_A_MT8195 -250460
85 #define LVTS_COEFF_A_MT7988 -204650
213 lvts_td->dom_dentry = debugfs_create_dir(dev_name(dev), NULL); in lvts_debugfs_init()
214 if (IS_ERR(lvts_td->dom_dentry)) in lvts_debugfs_init()
217 for (i = 0; i < lvts_td->num_lvts_ctrl; i++) { in lvts_debugfs_init()
219 lvts_ctrl = &lvts_td->lvts_ctrl[i]; in lvts_debugfs_init()
222 dentry = debugfs_create_dir(name, lvts_td->dom_dentry); in lvts_debugfs_init()
230 regset->base = lvts_ctrl->base; in lvts_debugfs_init()
231 regset->regs = lvts_regs; in lvts_debugfs_init()
232 regset->nregs = ARRAY_SIZE(lvts_regs); in lvts_debugfs_init()
242 debugfs_remove_recursive(lvts_td->dom_dentry); in lvts_debugfs_exit()
269 u32 raw_temp = ((s64)(golden_temp_offset - temperature)) << 14; in lvts_temp_to_raw()
271 raw_temp = div_s64(raw_temp, -temp_factor); in lvts_temp_to_raw()
280 sensors[lvts_sensor->id]); in lvts_get_temp()
281 const struct lvts_data *lvts_data = lvts_ctrl->lvts_data; in lvts_get_temp()
282 void __iomem *msr = lvts_sensor->msr; in lvts_get_temp()
289 * LVTS_MSR[0-3] / LVTS_IMMD[0-3] in lvts_get_temp()
293 * 32-17: Unused in lvts_get_temp()
295 * 15-0 : Raw temperature in lvts_get_temp()
312 return -EAGAIN; in lvts_get_temp()
314 *temp = lvts_raw_to_temp(value & 0xFFFF, lvts_data->temp_factor); in lvts_get_temp()
330 value = readl(LVTS_MONINT(lvts_ctrl->base)); in lvts_update_irq_mask()
333 if (lvts_ctrl->sensors[i].high_thresh == lvts_ctrl->high_thresh in lvts_update_irq_mask()
334 && lvts_ctrl->sensors[i].low_thresh == lvts_ctrl->low_thresh) in lvts_update_irq_mask()
340 writel(value, LVTS_MONINT(lvts_ctrl->base)); in lvts_update_irq_mask()
347 if (high > lvts_ctrl->high_thresh) in lvts_should_update_thresh()
350 for (i = 0; i < lvts_ctrl->num_lvts_sensor; i++) in lvts_should_update_thresh()
351 if (lvts_ctrl->sensors[i].high_thresh == lvts_ctrl->high_thresh in lvts_should_update_thresh()
352 && lvts_ctrl->sensors[i].low_thresh == lvts_ctrl->low_thresh) in lvts_should_update_thresh()
362 sensors[lvts_sensor->id]); in lvts_set_trips()
363 const struct lvts_data *lvts_data = lvts_ctrl->lvts_data; in lvts_set_trips()
364 void __iomem *base = lvts_sensor->base; in lvts_set_trips()
365 u32 raw_low = lvts_temp_to_raw(low != -INT_MAX ? low : LVTS_MINIMUM_THRESHOLD, in lvts_set_trips()
366 lvts_data->temp_factor); in lvts_set_trips()
367 u32 raw_high = lvts_temp_to_raw(high, lvts_data->temp_factor); in lvts_set_trips()
370 lvts_sensor->low_thresh = low; in lvts_set_trips()
371 lvts_sensor->high_thresh = high; in lvts_set_trips()
375 lvts_ctrl->high_thresh = high; in lvts_set_trips()
376 lvts_ctrl->low_thresh = low; in lvts_set_trips()
390 * 14-0 : Raw temperature for threshold in lvts_set_trips()
403 * 14-0 : Raw temperature for threshold in lvts_set_trips()
486 value = readl(LVTS_MONINTSTS(lvts_ctrl->base)); in lvts_ctrl_irq_handler()
500 thermal_zone_device_update(lvts_ctrl->sensors[i].tz, in lvts_ctrl_irq_handler()
508 writel(value, LVTS_MONINTSTS(lvts_ctrl->base)); in lvts_ctrl_irq_handler()
533 for (i = 0; i < lvts_td->num_lvts_ctrl; i++) { in lvts_irq_handler()
535 aux = lvts_ctrl_irq_handler(&lvts_td->lvts_ctrl[i]); in lvts_irq_handler()
553 struct lvts_sensor *lvts_sensor = lvts_ctrl->sensors; in lvts_sensor_init()
555 LVTS_MSR0(lvts_ctrl->base), in lvts_sensor_init()
556 LVTS_MSR1(lvts_ctrl->base), in lvts_sensor_init()
557 LVTS_MSR2(lvts_ctrl->base), in lvts_sensor_init()
558 LVTS_MSR3(lvts_ctrl->base) in lvts_sensor_init()
562 LVTS_IMMD0(lvts_ctrl->base), in lvts_sensor_init()
563 LVTS_IMMD1(lvts_ctrl->base), in lvts_sensor_init()
564 LVTS_IMMD2(lvts_ctrl->base), in lvts_sensor_init()
565 LVTS_IMMD3(lvts_ctrl->base) in lvts_sensor_init()
570 for (i = 0; i < lvts_ctrl_data->num_lvts_sensor; i++) { in lvts_sensor_init()
572 int dt_id = lvts_ctrl_data->lvts_sensor[i].dt_id; in lvts_sensor_init()
598 lvts_sensor[i].base = lvts_ctrl->base; in lvts_sensor_init()
603 lvts_sensor[i].msr = lvts_ctrl_data->mode == LVTS_MSR_IMMEDIATE_MODE ? in lvts_sensor_init()
610 lvts_ctrl->num_lvts_sensor = lvts_ctrl_data->num_lvts_sensor; in lvts_sensor_init()
622 * <-----mcu-tc#0-----> <-----sensor#0-----> <-----sensor#1----->
625 * <-----sensor#2-----> <-----sensor#3----->
628 …* <-----sensor#4-----> <-----sensor#5-----> <-----sensor#6-----> <-----sensor…
633 * <-----sensor#0-----> <-----sensor#1----->
636 * <-----sensor#2-----> <-----sensor#3----->
639 * <-----sensor#4-----> <-----sensor#5----->
642 * <-----sensor#6-----> <-----sensor#7-----> <-----sensor#8----->
648 * <-----mcu-tc#0-----> <-----sensor#0-----> <-----sensor#1----->
651 * <-----mcu-tc#1-----> <-----sensor#2-----> <-----sensor#3----->
654 …* <-----mcu-tc#2-----> <-----sensor#4-----> <-----sensor#5-----> <-----sensor#6-----> <-----sensor…
659 * <-----ap--tc#0-----> <-----sensor#0-----> <-----sensor#1----->
662 * <-----ap--tc#1-----> <-----sensor#2-----> <-----sensor#3----->
665 * <-----ap--tc#2-----> <-----sensor#4-----> <-----sensor#5-----> <-----sensor#6----->
668 * <-----ap--tc#3-----> <-----sensor#7-----> <-----sensor#8----->
680 for (i = 0; i < lvts_ctrl_data->num_lvts_sensor; i++) in lvts_calibration_init()
681 memcpy(&lvts_ctrl->calibration[i], in lvts_calibration_init()
682 efuse_calibration + lvts_ctrl_data->cal_offset[i], 2); in lvts_calibration_init()
701 of_property_for_each_string(np, "nvmem-cell-names", prop, cell_name) { in lvts_calibration_read()
720 lvts_td->calib = devm_krealloc(dev, lvts_td->calib, in lvts_calibration_read()
721 lvts_td->calib_len + len, GFP_KERNEL); in lvts_calibration_read()
722 if (!lvts_td->calib) in lvts_calibration_read()
723 return -ENOMEM; in lvts_calibration_read()
725 memcpy(lvts_td->calib + lvts_td->calib_len, efuse, len); in lvts_calibration_read()
727 lvts_td->calib_len += len; in lvts_calibration_read()
752 size_t size = sizeof(*lvts_td->lvts_ctrl) * lvts_data->num_lvts_ctrl; in lvts_ctrl_init()
767 ret = lvts_golden_temp_init(dev, (u32 *)lvts_td->calib, lvts_data->temp_offset); in lvts_ctrl_init()
773 return -ENOMEM; in lvts_ctrl_init()
775 for (i = 0; i < lvts_data->num_lvts_ctrl; i++) { in lvts_ctrl_init()
777 lvts_ctrl[i].base = lvts_td->base + lvts_data->lvts_ctrl[i].offset; in lvts_ctrl_init()
781 &lvts_data->lvts_ctrl[i]); in lvts_ctrl_init()
786 &lvts_data->lvts_ctrl[i], in lvts_ctrl_init()
787 lvts_td->calib); in lvts_ctrl_init()
795 lvts_ctrl[i].mode = lvts_data->lvts_ctrl[i].mode; in lvts_ctrl_init()
802 lvts_temp_to_raw(lvts_data->lvts_ctrl[i].hw_tshut_temp, in lvts_ctrl_init()
803 lvts_data->temp_factor); in lvts_ctrl_init()
812 devm_kfree(dev, lvts_td->calib); in lvts_ctrl_init()
814 lvts_td->lvts_ctrl = lvts_ctrl; in lvts_ctrl_init()
815 lvts_td->num_lvts_ctrl = lvts_data->num_lvts_ctrl; in lvts_ctrl_init()
834 writel(cmds[i], LVTS_CONFIG(lvts_ctrl->base)); in lvts_write_config()
846 * 19-18 : Sensor to base the protection on in lvts_irq_init()
847 * 17-16 : Strategy: in lvts_irq_init()
850 * 10 : Selected sensor with bits 19-18 in lvts_irq_init()
853 writel(BIT(16), LVTS_PROTCTL(lvts_ctrl->base)); in lvts_irq_init()
862 * 14-0: Raw temperature threshold in lvts_irq_init()
864 * writel(0x0, LVTS_PROTTA(lvts_ctrl->base)); in lvts_irq_init()
865 * writel(0x0, LVTS_PROTTB(lvts_ctrl->base)); in lvts_irq_init()
867 writel(lvts_ctrl->hw_tshut_raw_temp, LVTS_PROTTC(lvts_ctrl->base)); in lvts_irq_init()
875 writel(LVTS_MONINT_CONF, LVTS_MONINT(lvts_ctrl->base)); in lvts_irq_init()
903 writel(enable, LVTS_CLKEN(lvts_ctrl->base)); in lvts_ctrl_set_enable()
919 * 0-5 : thermal controller id in lvts_ctrl_connect()
922 id = readl(LVTS_ID(lvts_ctrl->base)); in lvts_ctrl_connect()
924 return -EIO; in lvts_ctrl_connect()
950 LVTS_EDATA00(lvts_ctrl->base), in lvts_ctrl_calibrate()
951 LVTS_EDATA01(lvts_ctrl->base), in lvts_ctrl_calibrate()
952 LVTS_EDATA02(lvts_ctrl->base), in lvts_ctrl_calibrate()
953 LVTS_EDATA03(lvts_ctrl->base) in lvts_ctrl_calibrate()
961 * 20-0 : Efuse value for normalization data in lvts_ctrl_calibrate()
964 writel(lvts_ctrl->calibration[i], lvts_edata[i]); in lvts_ctrl_calibrate()
978 * 31-24: ADC Sense 3 in lvts_ctrl_configure()
979 * 23-16: ADC Sense 2 in lvts_ctrl_configure()
980 * 15-8 : ADC Sense 1 in lvts_ctrl_configure()
981 * 7-0 : ADC Sense 0 in lvts_ctrl_configure()
984 writel(value, LVTS_TSSEL(lvts_ctrl->base)); in lvts_ctrl_configure()
998 * 001 : Avg 2 samples in lvts_ctrl_configure()
999 * 010 : 4 samples, drop min and max, avg 2 samples in lvts_ctrl_configure()
1000 * 011 : 6 samples, drop min and max, avg 4 samples in lvts_ctrl_configure()
1001 * 100 : 10 samples, drop min and max, avg 8 samples in lvts_ctrl_configure()
1002 * 101 : 18 samples, drop min and max, avg 16 samples in lvts_ctrl_configure()
1006 * 0-2 : Sensor0 filter in lvts_ctrl_configure()
1007 * 3-5 : Sensor1 filter in lvts_ctrl_configure()
1008 * 6-8 : Sensor2 filter in lvts_ctrl_configure()
1009 * 9-11 : Sensor3 filter in lvts_ctrl_configure()
1013 writel(value, LVTS_MSRCTL0(lvts_ctrl->base)); in lvts_ctrl_configure()
1027 * - Filter interval delay is a delay between two samples of in lvts_ctrl_configure()
1030 * - Sensor interval delay is a delay between two samples of in lvts_ctrl_configure()
1033 * - Group interval delay is a delay between different rounds. in lvts_ctrl_configure()
1045 * <--> Filter interval delay in lvts_ctrl_configure()
1046 * <--> Sensor interval delay in lvts_ctrl_configure()
1047 * <--> Group interval delay in lvts_ctrl_configure()
1049 * 29 - 20 : Group interval in lvts_ctrl_configure()
1050 * 16 - 13 : Send a single interrupt when crossing the hot threshold (1) in lvts_ctrl_configure()
1052 * 9 - 0 : Period unit in lvts_ctrl_configure()
1056 writel(value, LVTS_MONCTL1(lvts_ctrl->base)); in lvts_ctrl_configure()
1063 * 25-16 : Interval unit in PERIOD_UNIT between sample on in lvts_ctrl_configure()
1065 * 9-0 : Interval unit in PERIOD_UNIT between each sensor in lvts_ctrl_configure()
1069 writel(value, LVTS_MONCTL2(lvts_ctrl->base)); in lvts_ctrl_configure()
1076 struct lvts_sensor *lvts_sensors = lvts_ctrl->sensors; in lvts_ctrl_start()
1087 u32 *sensor_bitmap = lvts_ctrl->mode == LVTS_MSR_IMMEDIATE_MODE ? in lvts_ctrl_start()
1090 for (i = 0; i < lvts_ctrl->num_lvts_sensor; i++) { in lvts_ctrl_start()
1102 if (PTR_ERR(tz) == -ENODEV) in lvts_ctrl_start()
1135 if (lvts_ctrl->mode == LVTS_MSR_IMMEDIATE_MODE) { in lvts_ctrl_start()
1149 writel(sensor_map, LVTS_MSRCTL1(lvts_ctrl->base)); in lvts_ctrl_start()
1154 * 0-3: Enable sensing point 0-3 in lvts_ctrl_start()
1156 writel(sensor_map | BIT(9), LVTS_MONCTL0(lvts_ctrl->base)); in lvts_ctrl_start()
1172 ret = lvts_domain_reset(dev, lvts_td->reset); in lvts_domain_init()
1178 for (i = 0; i < lvts_td->num_lvts_ctrl; i++) { in lvts_domain_init()
1180 lvts_ctrl = &lvts_td->lvts_ctrl[i]; in lvts_domain_init()
1185 * - Enable the clock in lvts_domain_init()
1186 * - Connect to the LVTS in lvts_domain_init()
1187 * - Initialize the LVTS in lvts_domain_init()
1188 * - Prepare the calibration data in lvts_domain_init()
1189 * - Select monitored sensors in lvts_domain_init()
1192 * - Start measurement in lvts_domain_init()
1238 struct device *dev = &pdev->dev; in lvts_probe()
1244 return -ENOMEM; in lvts_probe()
1248 lvts_td->clk = devm_clk_get_enabled(dev, NULL); in lvts_probe()
1249 if (IS_ERR(lvts_td->clk)) in lvts_probe()
1250 return dev_err_probe(dev, PTR_ERR(lvts_td->clk), "Failed to retrieve clock\n"); in lvts_probe()
1254 return dev_err_probe(dev, (-ENXIO), "No IO resource\n"); in lvts_probe()
1256 lvts_td->base = devm_platform_get_and_ioremap_resource(pdev, 0, &res); in lvts_probe()
1257 if (IS_ERR(lvts_td->base)) in lvts_probe()
1258 return dev_err_probe(dev, PTR_ERR(lvts_td->base), "Failed to map io resource\n"); in lvts_probe()
1260 lvts_td->reset = devm_reset_control_get_by_index(dev, 0); in lvts_probe()
1261 if (IS_ERR(lvts_td->reset)) in lvts_probe()
1262 return dev_err_probe(dev, PTR_ERR(lvts_td->reset), "Failed to get reset control\n"); in lvts_probe()
1268 golden_temp_offset = lvts_data->temp_offset; in lvts_probe()
1295 for (i = 0; i < lvts_td->num_lvts_ctrl; i++) in lvts_remove()
1296 lvts_ctrl_set_enable(&lvts_td->lvts_ctrl[i], false); in lvts_remove()
1335 for (i = 0; i < lvts_td->num_lvts_ctrl; i++) in lvts_suspend()
1336 lvts_ctrl_set_enable(&lvts_td->lvts_ctrl[i], false); in lvts_suspend()
1338 clk_disable_unprepare(lvts_td->clk); in lvts_suspend()
1350 ret = clk_prepare_enable(lvts_td->clk); in lvts_resume()
1354 for (i = 0; i < lvts_td->num_lvts_ctrl; i++) in lvts_resume()
1355 lvts_ctrl_set_enable(&lvts_td->lvts_ctrl[i], true); in lvts_resume()
1553 { .compatible = "mediatek,mt7988-lvts-ap", .data = &mt7988_lvts_ap_data },
1554 { .compatible = "mediatek,mt8192-lvts-mcu", .data = &mt8192_lvts_mcu_data },
1555 { .compatible = "mediatek,mt8192-lvts-ap", .data = &mt8192_lvts_ap_data },
1556 { .compatible = "mediatek,mt8195-lvts-mcu", .data = &mt8195_lvts_mcu_data },
1557 { .compatible = "mediatek,mt8195-lvts-ap", .data = &mt8195_lvts_ap_data },
1570 .name = "mtk-lvts-thermal",