From 02ee68b95d814f85c2c55a874bef3f15f2f972e5 Mon Sep 17 00:00:00 2001 From: Ryder Lee Date: Sat, 17 Jul 2021 08:18:25 +0800 Subject: [PATCH] mt76: mt7915: add control knobs for thermal throttling With this patch, users can set the trigger/restore temperature for thermal service according to their use cases. Signed-off-by: Ryder Lee Signed-off-by: Felix Fietkau --- drivers/net/wireless/mediatek/mt76/mt7915/init.c | 40 ++++++++++++++++++++-- drivers/net/wireless/mediatek/mt76/mt7915/mcu.c | 17 +++------ drivers/net/wireless/mediatek/mt76/mt7915/mt7915.h | 1 + 3 files changed, 43 insertions(+), 15 deletions(-) diff --git a/drivers/net/wireless/mediatek/mt76/mt7915/init.c b/drivers/net/wireless/mediatek/mt76/mt7915/init.c index 906dacef5bdf..bfe13452af82 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7915/init.c +++ b/drivers/net/wireless/mediatek/mt76/mt7915/init.c @@ -42,13 +42,17 @@ static const struct ieee80211_iface_combination if_comb[] = { } }; -static ssize_t mt7915_thermal_show_temp(struct device *dev, +static ssize_t mt7915_thermal_temp_show(struct device *dev, struct device_attribute *attr, char *buf) { struct mt7915_phy *phy = dev_get_drvdata(dev); + int i = to_sensor_dev_attr(attr)->index; int temperature; + if (i) + return sprintf(buf, "%u\n", phy->throttle_temp[i - 1] * 1000); + temperature = mt7915_mcu_get_temperature(phy); if (temperature < 0) return temperature; @@ -57,11 +61,34 @@ static ssize_t mt7915_thermal_show_temp(struct device *dev, return sprintf(buf, "%u\n", temperature * 1000); } -static SENSOR_DEVICE_ATTR(temp1_input, 0444, mt7915_thermal_show_temp, - NULL, 0); +static ssize_t mt7915_thermal_temp_store(struct device *dev, + struct device_attribute *attr, + const char *buf, size_t count) +{ + struct mt7915_phy *phy = dev_get_drvdata(dev); + int ret, i = to_sensor_dev_attr(attr)->index; + long val; + + ret = kstrtol(buf, 10, &val); + if (ret < 0) + return ret; + + mutex_lock(&phy->dev->mt76.mutex); + val = clamp_val(DIV_ROUND_CLOSEST(val, 1000), 60, 130); + phy->throttle_temp[i - 1] = val; + mutex_unlock(&phy->dev->mt76.mutex); + + return count; +} + +static SENSOR_DEVICE_ATTR_RO(temp1_input, mt7915_thermal_temp, 0); +static SENSOR_DEVICE_ATTR_RW(temp1_crit, mt7915_thermal_temp, 1); +static SENSOR_DEVICE_ATTR_RW(temp1_max, mt7915_thermal_temp, 2); static struct attribute *mt7915_hwmon_attrs[] = { &sensor_dev_attr_temp1_input.dev_attr.attr, + &sensor_dev_attr_temp1_crit.dev_attr.attr, + &sensor_dev_attr_temp1_max.dev_attr.attr, NULL, }; ATTRIBUTE_GROUPS(mt7915_hwmon); @@ -96,6 +123,9 @@ mt7915_thermal_set_cur_throttle_state(struct thermal_cooling_device *cdev, if (state > MT7915_THERMAL_THROTTLE_MAX) return -EINVAL; + if (phy->throttle_temp[0] > phy->throttle_temp[1]) + return 0; + if (state == phy->throttle_state) return 0; @@ -150,6 +180,10 @@ static int mt7915_thermal_init(struct mt7915_phy *phy) if (IS_ERR(hwmon)) return PTR_ERR(hwmon); + /* initialize critical/maximum high temperature */ + phy->throttle_temp[0] = 110; + phy->throttle_temp[1] = 120; + return 0; } diff --git a/drivers/net/wireless/mediatek/mt76/mt7915/mcu.c b/drivers/net/wireless/mediatek/mt76/mt7915/mcu.c index 5ed123a644ab..813092ca2a81 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7915/mcu.c +++ b/drivers/net/wireless/mediatek/mt76/mt7915/mcu.c @@ -3544,10 +3544,6 @@ int mt7915_mcu_set_thermal_throttling(struct mt7915_phy *phy, u8 state) }; int level; -#define TRIGGER_TEMPERATURE 122 -#define RESTORE_TEMPERATURE 116 -#define SUSTAIN_PERIOD 10 - if (!state) { req.ctrl.ctrl_id = THERMAL_PROTECT_DISABLE; goto out; @@ -3560,7 +3556,7 @@ int mt7915_mcu_set_thermal_throttling(struct mt7915_phy *phy, u8 state) req.ctrl.ctrl_id = THERMAL_PROTECT_DUTY_CONFIG; req.ctrl.duty.duty_level = level; req.ctrl.duty.duty_cycle = state; - state = state * 4 / 5; + state /= 2; ret = mt76_mcu_send_msg(&dev->mt76, MCU_EXT_CMD(THERMAL_PROT), &req, sizeof(req.ctrl), false); @@ -3568,15 +3564,12 @@ int mt7915_mcu_set_thermal_throttling(struct mt7915_phy *phy, u8 state) return ret; } - /* currently use fixed values for throttling, and would be better - * to implement thermal zone for dynamic trip in the long run. - */ - /* set high-temperature trigger threshold */ req.ctrl.ctrl_id = THERMAL_PROTECT_ENABLE; - req.trigger_temp = cpu_to_le32(TRIGGER_TEMPERATURE); - req.restore_temp = cpu_to_le32(RESTORE_TEMPERATURE); - req.sustain_time = cpu_to_le16(SUSTAIN_PERIOD); + /* add a safety margin ~10 */ + req.restore_temp = cpu_to_le32(phy->throttle_temp[0] - 10); + req.trigger_temp = cpu_to_le32(phy->throttle_temp[1]); + req.sustain_time = cpu_to_le16(10); out: req.ctrl.type.protect_type = 1; diff --git a/drivers/net/wireless/mediatek/mt76/mt7915/mt7915.h b/drivers/net/wireless/mediatek/mt76/mt7915/mt7915.h index a6b5b300d415..d06b7536bba6 100644 --- a/drivers/net/wireless/mediatek/mt76/mt7915/mt7915.h +++ b/drivers/net/wireless/mediatek/mt76/mt7915/mt7915.h @@ -121,6 +121,7 @@ struct mt7915_phy { struct thermal_cooling_device *cdev; u8 throttle_state; + u32 throttle_temp[2]; /* 0: critical high, 1: maximum */ u32 rxfilter; u64 omac_mask; -- 2.11.0