Messages in this thread | | | From | Amit Kucheria <> | Date | Wed, 20 May 2020 10:08:35 +0530 | Subject | Re: [RFC][PATCH 4/5] thermal: Add support for setting polling interval |
| |
On Mon, May 4, 2020 at 11:47 PM Srinivas Pandruvada <srinivas.pandruvada@linux.intel.com> wrote: > > Add new attribute in the thermal syfs for setting temperature sampling > interval when CONFIG_THERMAL_USER_EVENT_INTERFACE is defined. The default > value is 0, which means no polling. > > At this interval user space will get an event THERMAL_TEMP_SAMPLE with > temperature sample. This reuses existing polling mecahnism when polling > or passive delay is specified during zone registry. To avoid interference > with passive and polling delay, this new polling attribute can't be used > for those zones.
Why should the kernel periodically emit events for userspace when the userspace is perfectly capable of deciding how frequently it wants to poll a file for changes?
> > Signed-off-by: Srinivas Pandruvada <srinivas.pandruvada@linux.intel.com> > --- > drivers/thermal/thermal_core.c | 7 +++++++ > drivers/thermal/thermal_sysfs.c | 36 +++++++++++++++++++++++++++++++-- > include/linux/thermal.h | 1 + > 3 files changed, 42 insertions(+), 2 deletions(-) > > diff --git a/drivers/thermal/thermal_core.c b/drivers/thermal/thermal_core.c > index 14770d882d42..17cd799b0073 100644 > --- a/drivers/thermal/thermal_core.c > +++ b/drivers/thermal/thermal_core.c > @@ -313,6 +313,8 @@ static void monitor_thermal_zone(struct thermal_zone_device *tz) > thermal_zone_device_set_polling(tz, tz->passive_delay); > else if (tz->polling_delay) > thermal_zone_device_set_polling(tz, tz->polling_delay); > + else if (tz->temp_polling_delay) > + thermal_zone_device_set_polling(tz, tz->temp_polling_delay); > else > thermal_zone_device_set_polling(tz, 0); > > @@ -446,6 +448,11 @@ static void update_temperature(struct thermal_zone_device *tz) > tz->temperature = temp; > mutex_unlock(&tz->lock); > > + if (tz->temp_polling_delay) { > + thermal_dev_send_event(tz->id, THERMAL_TEMP_SAMPLE, temp); > + monitor_thermal_zone(tz); > + } > + > trace_thermal_temperature(tz); > if (tz->last_temperature == THERMAL_TEMP_INVALID) > dev_dbg(&tz->device, "last_temperature N/A, current_temperature=%d\n", > diff --git a/drivers/thermal/thermal_sysfs.c b/drivers/thermal/thermal_sysfs.c > index aa85424c3ac4..0df7997993fe 100644 > --- a/drivers/thermal/thermal_sysfs.c > +++ b/drivers/thermal/thermal_sysfs.c > @@ -248,6 +248,36 @@ create_thres_attr(temp_thres_low); > create_thres_attr(temp_thres_high); > create_thres_attr(temp_thres_hyst); > > +static ssize_t > +temp_polling_delay_store(struct device *dev, struct device_attribute *attr, > + const char *buf, size_t count) > +{ > + struct thermal_zone_device *tz = to_thermal_zone(dev); > + int val; > + > + if (kstrtoint(buf, 10, &val)) > + return -EINVAL; > + > + if (val && val < 1000) > + return -EINVAL; > + > + tz->temp_polling_delay = val; > + thermal_zone_device_update(tz, THERMAL_EVENT_UNSPECIFIED); > + > + return count; > +} > + > +static ssize_t > +temp_polling_delay_show(struct device *dev, struct device_attribute *attr, > + char *buf) > +{ > + struct thermal_zone_device *tz = to_thermal_zone(dev); > + > + return sprintf(buf, "%d\n", tz->temp_polling_delay); > +} > + > +static DEVICE_ATTR_RW(temp_polling_delay); > + > static int create_user_events_attrs(struct thermal_zone_device *tz) > { > struct attribute **attrs; > @@ -260,8 +290,8 @@ static int create_user_events_attrs(struct thermal_zone_device *tz) > if (tz->ops->get_temp_thres_high) > ++index; > > - /* One additional space for NULL */ > - attrs = kcalloc(index + 1, sizeof(*attrs), GFP_KERNEL); > + /* One additional space for NULL and temp_pollling_delay */ > + attrs = kcalloc(index + 2, sizeof(*attrs), GFP_KERNEL); > if (!attrs) > return -ENOMEM; > > @@ -312,6 +342,8 @@ static int create_user_events_attrs(struct thermal_zone_device *tz) > attrs[index] = &tz->threshold_attrs[index].attr.attr; > ++index; > } > + if (!tz->polling_delay && !tz->passive_delay) > + attrs[index++] = &dev_attr_temp_polling_delay.attr; > attrs[index] = NULL; > tz->threshold_attribute_group.attrs = attrs; > > diff --git a/include/linux/thermal.h b/include/linux/thermal.h > index ee9d79ace7ce..0ec4bd8c9c5c 100644 > --- a/include/linux/thermal.h > +++ b/include/linux/thermal.h > @@ -216,6 +216,7 @@ struct thermal_zone_device { > enum thermal_notify_event notify_event; > struct attribute_group threshold_attribute_group; > struct thermal_attr *threshold_attrs; > + int temp_polling_delay; > }; > > /** > -- > 2.25.4 >
| |