xref: /OK3568_Linux_fs/kernel/drivers/hwmon/abx500.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0-only
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  * Copyright (C) ST-Ericsson 2010 - 2013
4*4882a593Smuzhiyun  * Author: Martin Persson <martin.persson@stericsson.com>
5*4882a593Smuzhiyun  *         Hongbo Zhang <hongbo.zhang@linaro.org>
6*4882a593Smuzhiyun  *
7*4882a593Smuzhiyun  * ABX500 does not provide auto ADC, so to monitor the required temperatures,
8*4882a593Smuzhiyun  * a periodic work is used. It is more important to not wake up the CPU than
9*4882a593Smuzhiyun  * to perform this job, hence the use of a deferred delay.
10*4882a593Smuzhiyun  *
11*4882a593Smuzhiyun  * A deferred delay for thermal monitor is considered safe because:
12*4882a593Smuzhiyun  * If the chip gets too hot during a sleep state it's most likely due to
13*4882a593Smuzhiyun  * external factors, such as the surrounding temperature. I.e. no SW decisions
14*4882a593Smuzhiyun  * will make any difference.
15*4882a593Smuzhiyun  */
16*4882a593Smuzhiyun 
17*4882a593Smuzhiyun #include <linux/err.h>
18*4882a593Smuzhiyun #include <linux/hwmon.h>
19*4882a593Smuzhiyun #include <linux/hwmon-sysfs.h>
20*4882a593Smuzhiyun #include <linux/interrupt.h>
21*4882a593Smuzhiyun #include <linux/jiffies.h>
22*4882a593Smuzhiyun #include <linux/module.h>
23*4882a593Smuzhiyun #include <linux/mutex.h>
24*4882a593Smuzhiyun #include <linux/of.h>
25*4882a593Smuzhiyun #include <linux/platform_device.h>
26*4882a593Smuzhiyun #include <linux/pm.h>
27*4882a593Smuzhiyun #include <linux/slab.h>
28*4882a593Smuzhiyun #include <linux/sysfs.h>
29*4882a593Smuzhiyun #include <linux/workqueue.h>
30*4882a593Smuzhiyun #include "abx500.h"
31*4882a593Smuzhiyun 
32*4882a593Smuzhiyun #define DEFAULT_MONITOR_DELAY	HZ
33*4882a593Smuzhiyun #define DEFAULT_MAX_TEMP	130
34*4882a593Smuzhiyun 
schedule_monitor(struct abx500_temp * data)35*4882a593Smuzhiyun static inline void schedule_monitor(struct abx500_temp *data)
36*4882a593Smuzhiyun {
37*4882a593Smuzhiyun 	data->work_active = true;
38*4882a593Smuzhiyun 	schedule_delayed_work(&data->work, DEFAULT_MONITOR_DELAY);
39*4882a593Smuzhiyun }
40*4882a593Smuzhiyun 
threshold_updated(struct abx500_temp * data)41*4882a593Smuzhiyun static void threshold_updated(struct abx500_temp *data)
42*4882a593Smuzhiyun {
43*4882a593Smuzhiyun 	int i;
44*4882a593Smuzhiyun 	for (i = 0; i < data->monitored_sensors; i++)
45*4882a593Smuzhiyun 		if (data->max[i] != 0 || data->min[i] != 0) {
46*4882a593Smuzhiyun 			schedule_monitor(data);
47*4882a593Smuzhiyun 			return;
48*4882a593Smuzhiyun 		}
49*4882a593Smuzhiyun 
50*4882a593Smuzhiyun 	dev_dbg(&data->pdev->dev, "No active thresholds.\n");
51*4882a593Smuzhiyun 	cancel_delayed_work_sync(&data->work);
52*4882a593Smuzhiyun 	data->work_active = false;
53*4882a593Smuzhiyun }
54*4882a593Smuzhiyun 
gpadc_monitor(struct work_struct * work)55*4882a593Smuzhiyun static void gpadc_monitor(struct work_struct *work)
56*4882a593Smuzhiyun {
57*4882a593Smuzhiyun 	int temp, i, ret;
58*4882a593Smuzhiyun 	char alarm_node[30];
59*4882a593Smuzhiyun 	bool updated_min_alarm, updated_max_alarm;
60*4882a593Smuzhiyun 	struct abx500_temp *data;
61*4882a593Smuzhiyun 
62*4882a593Smuzhiyun 	data = container_of(work, struct abx500_temp, work.work);
63*4882a593Smuzhiyun 	mutex_lock(&data->lock);
64*4882a593Smuzhiyun 
65*4882a593Smuzhiyun 	for (i = 0; i < data->monitored_sensors; i++) {
66*4882a593Smuzhiyun 		/* Thresholds are considered inactive if set to 0 */
67*4882a593Smuzhiyun 		if (data->max[i] == 0 && data->min[i] == 0)
68*4882a593Smuzhiyun 			continue;
69*4882a593Smuzhiyun 
70*4882a593Smuzhiyun 		if (data->max[i] < data->min[i])
71*4882a593Smuzhiyun 			continue;
72*4882a593Smuzhiyun 
73*4882a593Smuzhiyun 		ret = data->ops.read_sensor(data, data->gpadc_addr[i], &temp);
74*4882a593Smuzhiyun 		if (ret < 0) {
75*4882a593Smuzhiyun 			dev_err(&data->pdev->dev, "GPADC read failed\n");
76*4882a593Smuzhiyun 			continue;
77*4882a593Smuzhiyun 		}
78*4882a593Smuzhiyun 
79*4882a593Smuzhiyun 		updated_min_alarm = false;
80*4882a593Smuzhiyun 		updated_max_alarm = false;
81*4882a593Smuzhiyun 
82*4882a593Smuzhiyun 		if (data->min[i] != 0) {
83*4882a593Smuzhiyun 			if (temp < data->min[i]) {
84*4882a593Smuzhiyun 				if (data->min_alarm[i] == false) {
85*4882a593Smuzhiyun 					data->min_alarm[i] = true;
86*4882a593Smuzhiyun 					updated_min_alarm = true;
87*4882a593Smuzhiyun 				}
88*4882a593Smuzhiyun 			} else {
89*4882a593Smuzhiyun 				if (data->min_alarm[i] == true) {
90*4882a593Smuzhiyun 					data->min_alarm[i] = false;
91*4882a593Smuzhiyun 					updated_min_alarm = true;
92*4882a593Smuzhiyun 				}
93*4882a593Smuzhiyun 			}
94*4882a593Smuzhiyun 		}
95*4882a593Smuzhiyun 		if (data->max[i] != 0) {
96*4882a593Smuzhiyun 			if (temp > data->max[i]) {
97*4882a593Smuzhiyun 				if (data->max_alarm[i] == false) {
98*4882a593Smuzhiyun 					data->max_alarm[i] = true;
99*4882a593Smuzhiyun 					updated_max_alarm = true;
100*4882a593Smuzhiyun 				}
101*4882a593Smuzhiyun 			} else if (temp < data->max[i] - data->max_hyst[i]) {
102*4882a593Smuzhiyun 				if (data->max_alarm[i] == true) {
103*4882a593Smuzhiyun 					data->max_alarm[i] = false;
104*4882a593Smuzhiyun 					updated_max_alarm = true;
105*4882a593Smuzhiyun 				}
106*4882a593Smuzhiyun 			}
107*4882a593Smuzhiyun 		}
108*4882a593Smuzhiyun 
109*4882a593Smuzhiyun 		if (updated_min_alarm) {
110*4882a593Smuzhiyun 			ret = sprintf(alarm_node, "temp%d_min_alarm", i + 1);
111*4882a593Smuzhiyun 			sysfs_notify(&data->pdev->dev.kobj, NULL, alarm_node);
112*4882a593Smuzhiyun 		}
113*4882a593Smuzhiyun 		if (updated_max_alarm) {
114*4882a593Smuzhiyun 			ret = sprintf(alarm_node, "temp%d_max_alarm", i + 1);
115*4882a593Smuzhiyun 			sysfs_notify(&data->pdev->dev.kobj, NULL, alarm_node);
116*4882a593Smuzhiyun 		}
117*4882a593Smuzhiyun 	}
118*4882a593Smuzhiyun 
119*4882a593Smuzhiyun 	schedule_monitor(data);
120*4882a593Smuzhiyun 	mutex_unlock(&data->lock);
121*4882a593Smuzhiyun }
122*4882a593Smuzhiyun 
123*4882a593Smuzhiyun /* HWMON sysfs interfaces */
name_show(struct device * dev,struct device_attribute * devattr,char * buf)124*4882a593Smuzhiyun static ssize_t name_show(struct device *dev, struct device_attribute *devattr,
125*4882a593Smuzhiyun 			 char *buf)
126*4882a593Smuzhiyun {
127*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
128*4882a593Smuzhiyun 	/* Show chip name */
129*4882a593Smuzhiyun 	return data->ops.show_name(dev, devattr, buf);
130*4882a593Smuzhiyun }
131*4882a593Smuzhiyun 
label_show(struct device * dev,struct device_attribute * devattr,char * buf)132*4882a593Smuzhiyun static ssize_t label_show(struct device *dev,
133*4882a593Smuzhiyun 			  struct device_attribute *devattr, char *buf)
134*4882a593Smuzhiyun {
135*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
136*4882a593Smuzhiyun 	/* Show each sensor label */
137*4882a593Smuzhiyun 	return data->ops.show_label(dev, devattr, buf);
138*4882a593Smuzhiyun }
139*4882a593Smuzhiyun 
input_show(struct device * dev,struct device_attribute * devattr,char * buf)140*4882a593Smuzhiyun static ssize_t input_show(struct device *dev,
141*4882a593Smuzhiyun 			  struct device_attribute *devattr, char *buf)
142*4882a593Smuzhiyun {
143*4882a593Smuzhiyun 	int ret, temp;
144*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
145*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
146*4882a593Smuzhiyun 	u8 gpadc_addr = data->gpadc_addr[attr->index];
147*4882a593Smuzhiyun 
148*4882a593Smuzhiyun 	ret = data->ops.read_sensor(data, gpadc_addr, &temp);
149*4882a593Smuzhiyun 	if (ret < 0)
150*4882a593Smuzhiyun 		return ret;
151*4882a593Smuzhiyun 
152*4882a593Smuzhiyun 	return sprintf(buf, "%d\n", temp);
153*4882a593Smuzhiyun }
154*4882a593Smuzhiyun 
155*4882a593Smuzhiyun /* Set functions (RW nodes) */
min_store(struct device * dev,struct device_attribute * devattr,const char * buf,size_t count)156*4882a593Smuzhiyun static ssize_t min_store(struct device *dev, struct device_attribute *devattr,
157*4882a593Smuzhiyun 			 const char *buf, size_t count)
158*4882a593Smuzhiyun {
159*4882a593Smuzhiyun 	unsigned long val;
160*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
161*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
162*4882a593Smuzhiyun 	int res = kstrtol(buf, 10, &val);
163*4882a593Smuzhiyun 	if (res < 0)
164*4882a593Smuzhiyun 		return res;
165*4882a593Smuzhiyun 
166*4882a593Smuzhiyun 	val = clamp_val(val, 0, DEFAULT_MAX_TEMP);
167*4882a593Smuzhiyun 
168*4882a593Smuzhiyun 	mutex_lock(&data->lock);
169*4882a593Smuzhiyun 	data->min[attr->index] = val;
170*4882a593Smuzhiyun 	threshold_updated(data);
171*4882a593Smuzhiyun 	mutex_unlock(&data->lock);
172*4882a593Smuzhiyun 
173*4882a593Smuzhiyun 	return count;
174*4882a593Smuzhiyun }
175*4882a593Smuzhiyun 
max_store(struct device * dev,struct device_attribute * devattr,const char * buf,size_t count)176*4882a593Smuzhiyun static ssize_t max_store(struct device *dev, struct device_attribute *devattr,
177*4882a593Smuzhiyun 			 const char *buf, size_t count)
178*4882a593Smuzhiyun {
179*4882a593Smuzhiyun 	unsigned long val;
180*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
181*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
182*4882a593Smuzhiyun 	int res = kstrtol(buf, 10, &val);
183*4882a593Smuzhiyun 	if (res < 0)
184*4882a593Smuzhiyun 		return res;
185*4882a593Smuzhiyun 
186*4882a593Smuzhiyun 	val = clamp_val(val, 0, DEFAULT_MAX_TEMP);
187*4882a593Smuzhiyun 
188*4882a593Smuzhiyun 	mutex_lock(&data->lock);
189*4882a593Smuzhiyun 	data->max[attr->index] = val;
190*4882a593Smuzhiyun 	threshold_updated(data);
191*4882a593Smuzhiyun 	mutex_unlock(&data->lock);
192*4882a593Smuzhiyun 
193*4882a593Smuzhiyun 	return count;
194*4882a593Smuzhiyun }
195*4882a593Smuzhiyun 
max_hyst_store(struct device * dev,struct device_attribute * devattr,const char * buf,size_t count)196*4882a593Smuzhiyun static ssize_t max_hyst_store(struct device *dev,
197*4882a593Smuzhiyun 			      struct device_attribute *devattr,
198*4882a593Smuzhiyun 			      const char *buf, size_t count)
199*4882a593Smuzhiyun {
200*4882a593Smuzhiyun 	unsigned long val;
201*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
202*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
203*4882a593Smuzhiyun 	int res = kstrtoul(buf, 10, &val);
204*4882a593Smuzhiyun 	if (res < 0)
205*4882a593Smuzhiyun 		return res;
206*4882a593Smuzhiyun 
207*4882a593Smuzhiyun 	val = clamp_val(val, 0, DEFAULT_MAX_TEMP);
208*4882a593Smuzhiyun 
209*4882a593Smuzhiyun 	mutex_lock(&data->lock);
210*4882a593Smuzhiyun 	data->max_hyst[attr->index] = val;
211*4882a593Smuzhiyun 	threshold_updated(data);
212*4882a593Smuzhiyun 	mutex_unlock(&data->lock);
213*4882a593Smuzhiyun 
214*4882a593Smuzhiyun 	return count;
215*4882a593Smuzhiyun }
216*4882a593Smuzhiyun 
217*4882a593Smuzhiyun /* Show functions (RO nodes) */
min_show(struct device * dev,struct device_attribute * devattr,char * buf)218*4882a593Smuzhiyun static ssize_t min_show(struct device *dev, struct device_attribute *devattr,
219*4882a593Smuzhiyun 			char *buf)
220*4882a593Smuzhiyun {
221*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
222*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
223*4882a593Smuzhiyun 
224*4882a593Smuzhiyun 	return sprintf(buf, "%lu\n", data->min[attr->index]);
225*4882a593Smuzhiyun }
226*4882a593Smuzhiyun 
max_show(struct device * dev,struct device_attribute * devattr,char * buf)227*4882a593Smuzhiyun static ssize_t max_show(struct device *dev, struct device_attribute *devattr,
228*4882a593Smuzhiyun 			char *buf)
229*4882a593Smuzhiyun {
230*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
231*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
232*4882a593Smuzhiyun 
233*4882a593Smuzhiyun 	return sprintf(buf, "%lu\n", data->max[attr->index]);
234*4882a593Smuzhiyun }
235*4882a593Smuzhiyun 
max_hyst_show(struct device * dev,struct device_attribute * devattr,char * buf)236*4882a593Smuzhiyun static ssize_t max_hyst_show(struct device *dev,
237*4882a593Smuzhiyun 			     struct device_attribute *devattr, char *buf)
238*4882a593Smuzhiyun {
239*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
240*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
241*4882a593Smuzhiyun 
242*4882a593Smuzhiyun 	return sprintf(buf, "%lu\n", data->max_hyst[attr->index]);
243*4882a593Smuzhiyun }
244*4882a593Smuzhiyun 
min_alarm_show(struct device * dev,struct device_attribute * devattr,char * buf)245*4882a593Smuzhiyun static ssize_t min_alarm_show(struct device *dev,
246*4882a593Smuzhiyun 			      struct device_attribute *devattr, char *buf)
247*4882a593Smuzhiyun {
248*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
249*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
250*4882a593Smuzhiyun 
251*4882a593Smuzhiyun 	return sprintf(buf, "%d\n", data->min_alarm[attr->index]);
252*4882a593Smuzhiyun }
253*4882a593Smuzhiyun 
max_alarm_show(struct device * dev,struct device_attribute * devattr,char * buf)254*4882a593Smuzhiyun static ssize_t max_alarm_show(struct device *dev,
255*4882a593Smuzhiyun 			      struct device_attribute *devattr, char *buf)
256*4882a593Smuzhiyun {
257*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
258*4882a593Smuzhiyun 	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
259*4882a593Smuzhiyun 
260*4882a593Smuzhiyun 	return sprintf(buf, "%d\n", data->max_alarm[attr->index]);
261*4882a593Smuzhiyun }
262*4882a593Smuzhiyun 
abx500_attrs_visible(struct kobject * kobj,struct attribute * attr,int n)263*4882a593Smuzhiyun static umode_t abx500_attrs_visible(struct kobject *kobj,
264*4882a593Smuzhiyun 				   struct attribute *attr, int n)
265*4882a593Smuzhiyun {
266*4882a593Smuzhiyun 	struct device *dev = container_of(kobj, struct device, kobj);
267*4882a593Smuzhiyun 	struct abx500_temp *data = dev_get_drvdata(dev);
268*4882a593Smuzhiyun 
269*4882a593Smuzhiyun 	if (data->ops.is_visible)
270*4882a593Smuzhiyun 		return data->ops.is_visible(attr, n);
271*4882a593Smuzhiyun 
272*4882a593Smuzhiyun 	return attr->mode;
273*4882a593Smuzhiyun }
274*4882a593Smuzhiyun 
275*4882a593Smuzhiyun /* Chip name, required by hwmon */
276*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(name, name, 0);
277*4882a593Smuzhiyun 
278*4882a593Smuzhiyun /* GPADC - SENSOR1 */
279*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp1_label, label, 0);
280*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp1_input, input, 0);
281*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp1_min, min, 0);
282*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp1_max, max, 0);
283*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp1_max_hyst, max_hyst, 0);
284*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp1_min_alarm, min_alarm, 0);
285*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp1_max_alarm, max_alarm, 0);
286*4882a593Smuzhiyun 
287*4882a593Smuzhiyun /* GPADC - SENSOR2 */
288*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp2_label, label, 1);
289*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp2_input, input, 1);
290*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp2_min, min, 1);
291*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp2_max, max, 1);
292*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp2_max_hyst, max_hyst, 1);
293*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp2_min_alarm, min_alarm, 1);
294*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp2_max_alarm, max_alarm, 1);
295*4882a593Smuzhiyun 
296*4882a593Smuzhiyun /* GPADC - SENSOR3 */
297*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp3_label, label, 2);
298*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp3_input, input, 2);
299*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp3_min, min, 2);
300*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp3_max, max, 2);
301*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp3_max_hyst, max_hyst, 2);
302*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp3_min_alarm, min_alarm, 2);
303*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp3_max_alarm, max_alarm, 2);
304*4882a593Smuzhiyun 
305*4882a593Smuzhiyun /* GPADC - SENSOR4 */
306*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp4_label, label, 3);
307*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp4_input, input, 3);
308*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp4_min, min, 3);
309*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp4_max, max, 3);
310*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RW(temp4_max_hyst, max_hyst, 3);
311*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp4_min_alarm, min_alarm, 3);
312*4882a593Smuzhiyun static SENSOR_DEVICE_ATTR_RO(temp4_max_alarm, max_alarm, 3);
313*4882a593Smuzhiyun 
314*4882a593Smuzhiyun static struct attribute *abx500_temp_attributes[] = {
315*4882a593Smuzhiyun 	&sensor_dev_attr_name.dev_attr.attr,
316*4882a593Smuzhiyun 
317*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_label.dev_attr.attr,
318*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_input.dev_attr.attr,
319*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_min.dev_attr.attr,
320*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_max.dev_attr.attr,
321*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_max_hyst.dev_attr.attr,
322*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_min_alarm.dev_attr.attr,
323*4882a593Smuzhiyun 	&sensor_dev_attr_temp1_max_alarm.dev_attr.attr,
324*4882a593Smuzhiyun 
325*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_label.dev_attr.attr,
326*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_input.dev_attr.attr,
327*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_min.dev_attr.attr,
328*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_max.dev_attr.attr,
329*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_max_hyst.dev_attr.attr,
330*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_min_alarm.dev_attr.attr,
331*4882a593Smuzhiyun 	&sensor_dev_attr_temp2_max_alarm.dev_attr.attr,
332*4882a593Smuzhiyun 
333*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_label.dev_attr.attr,
334*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_input.dev_attr.attr,
335*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_min.dev_attr.attr,
336*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_max.dev_attr.attr,
337*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_max_hyst.dev_attr.attr,
338*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_min_alarm.dev_attr.attr,
339*4882a593Smuzhiyun 	&sensor_dev_attr_temp3_max_alarm.dev_attr.attr,
340*4882a593Smuzhiyun 
341*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_label.dev_attr.attr,
342*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_input.dev_attr.attr,
343*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_min.dev_attr.attr,
344*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_max.dev_attr.attr,
345*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_max_hyst.dev_attr.attr,
346*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_min_alarm.dev_attr.attr,
347*4882a593Smuzhiyun 	&sensor_dev_attr_temp4_max_alarm.dev_attr.attr,
348*4882a593Smuzhiyun 	NULL
349*4882a593Smuzhiyun };
350*4882a593Smuzhiyun 
351*4882a593Smuzhiyun static const struct attribute_group abx500_temp_group = {
352*4882a593Smuzhiyun 	.attrs = abx500_temp_attributes,
353*4882a593Smuzhiyun 	.is_visible = abx500_attrs_visible,
354*4882a593Smuzhiyun };
355*4882a593Smuzhiyun 
abx500_temp_irq_handler(int irq,void * irq_data)356*4882a593Smuzhiyun static irqreturn_t abx500_temp_irq_handler(int irq, void *irq_data)
357*4882a593Smuzhiyun {
358*4882a593Smuzhiyun 	struct platform_device *pdev = irq_data;
359*4882a593Smuzhiyun 	struct abx500_temp *data = platform_get_drvdata(pdev);
360*4882a593Smuzhiyun 
361*4882a593Smuzhiyun 	data->ops.irq_handler(irq, data);
362*4882a593Smuzhiyun 	return IRQ_HANDLED;
363*4882a593Smuzhiyun }
364*4882a593Smuzhiyun 
setup_irqs(struct platform_device * pdev)365*4882a593Smuzhiyun static int setup_irqs(struct platform_device *pdev)
366*4882a593Smuzhiyun {
367*4882a593Smuzhiyun 	int ret;
368*4882a593Smuzhiyun 	int irq = platform_get_irq_byname(pdev, "ABX500_TEMP_WARM");
369*4882a593Smuzhiyun 
370*4882a593Smuzhiyun 	if (irq < 0) {
371*4882a593Smuzhiyun 		dev_err(&pdev->dev, "Get irq by name failed\n");
372*4882a593Smuzhiyun 		return irq;
373*4882a593Smuzhiyun 	}
374*4882a593Smuzhiyun 
375*4882a593Smuzhiyun 	ret = devm_request_threaded_irq(&pdev->dev, irq, NULL,
376*4882a593Smuzhiyun 		abx500_temp_irq_handler, 0, "abx500-temp", pdev);
377*4882a593Smuzhiyun 	if (ret < 0)
378*4882a593Smuzhiyun 		dev_err(&pdev->dev, "Request threaded irq failed (%d)\n", ret);
379*4882a593Smuzhiyun 
380*4882a593Smuzhiyun 	return ret;
381*4882a593Smuzhiyun }
382*4882a593Smuzhiyun 
abx500_temp_probe(struct platform_device * pdev)383*4882a593Smuzhiyun static int abx500_temp_probe(struct platform_device *pdev)
384*4882a593Smuzhiyun {
385*4882a593Smuzhiyun 	struct abx500_temp *data;
386*4882a593Smuzhiyun 	int err;
387*4882a593Smuzhiyun 
388*4882a593Smuzhiyun 	data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
389*4882a593Smuzhiyun 	if (!data)
390*4882a593Smuzhiyun 		return -ENOMEM;
391*4882a593Smuzhiyun 
392*4882a593Smuzhiyun 	data->pdev = pdev;
393*4882a593Smuzhiyun 	mutex_init(&data->lock);
394*4882a593Smuzhiyun 
395*4882a593Smuzhiyun 	/* Chip specific initialization */
396*4882a593Smuzhiyun 	err = abx500_hwmon_init(data);
397*4882a593Smuzhiyun 	if (err	< 0 || !data->ops.read_sensor || !data->ops.show_name ||
398*4882a593Smuzhiyun 			!data->ops.show_label)
399*4882a593Smuzhiyun 		return err;
400*4882a593Smuzhiyun 
401*4882a593Smuzhiyun 	INIT_DEFERRABLE_WORK(&data->work, gpadc_monitor);
402*4882a593Smuzhiyun 
403*4882a593Smuzhiyun 	platform_set_drvdata(pdev, data);
404*4882a593Smuzhiyun 
405*4882a593Smuzhiyun 	err = sysfs_create_group(&pdev->dev.kobj, &abx500_temp_group);
406*4882a593Smuzhiyun 	if (err < 0) {
407*4882a593Smuzhiyun 		dev_err(&pdev->dev, "Create sysfs group failed (%d)\n", err);
408*4882a593Smuzhiyun 		return err;
409*4882a593Smuzhiyun 	}
410*4882a593Smuzhiyun 
411*4882a593Smuzhiyun 	data->hwmon_dev = hwmon_device_register(&pdev->dev);
412*4882a593Smuzhiyun 	if (IS_ERR(data->hwmon_dev)) {
413*4882a593Smuzhiyun 		err = PTR_ERR(data->hwmon_dev);
414*4882a593Smuzhiyun 		dev_err(&pdev->dev, "Class registration failed (%d)\n", err);
415*4882a593Smuzhiyun 		goto exit_sysfs_group;
416*4882a593Smuzhiyun 	}
417*4882a593Smuzhiyun 
418*4882a593Smuzhiyun 	if (data->ops.irq_handler) {
419*4882a593Smuzhiyun 		err = setup_irqs(pdev);
420*4882a593Smuzhiyun 		if (err < 0)
421*4882a593Smuzhiyun 			goto exit_hwmon_reg;
422*4882a593Smuzhiyun 	}
423*4882a593Smuzhiyun 	return 0;
424*4882a593Smuzhiyun 
425*4882a593Smuzhiyun exit_hwmon_reg:
426*4882a593Smuzhiyun 	hwmon_device_unregister(data->hwmon_dev);
427*4882a593Smuzhiyun exit_sysfs_group:
428*4882a593Smuzhiyun 	sysfs_remove_group(&pdev->dev.kobj, &abx500_temp_group);
429*4882a593Smuzhiyun 	return err;
430*4882a593Smuzhiyun }
431*4882a593Smuzhiyun 
abx500_temp_remove(struct platform_device * pdev)432*4882a593Smuzhiyun static int abx500_temp_remove(struct platform_device *pdev)
433*4882a593Smuzhiyun {
434*4882a593Smuzhiyun 	struct abx500_temp *data = platform_get_drvdata(pdev);
435*4882a593Smuzhiyun 
436*4882a593Smuzhiyun 	cancel_delayed_work_sync(&data->work);
437*4882a593Smuzhiyun 	hwmon_device_unregister(data->hwmon_dev);
438*4882a593Smuzhiyun 	sysfs_remove_group(&pdev->dev.kobj, &abx500_temp_group);
439*4882a593Smuzhiyun 
440*4882a593Smuzhiyun 	return 0;
441*4882a593Smuzhiyun }
442*4882a593Smuzhiyun 
abx500_temp_suspend(struct platform_device * pdev,pm_message_t state)443*4882a593Smuzhiyun static int abx500_temp_suspend(struct platform_device *pdev,
444*4882a593Smuzhiyun 			       pm_message_t state)
445*4882a593Smuzhiyun {
446*4882a593Smuzhiyun 	struct abx500_temp *data = platform_get_drvdata(pdev);
447*4882a593Smuzhiyun 
448*4882a593Smuzhiyun 	if (data->work_active)
449*4882a593Smuzhiyun 		cancel_delayed_work_sync(&data->work);
450*4882a593Smuzhiyun 
451*4882a593Smuzhiyun 	return 0;
452*4882a593Smuzhiyun }
453*4882a593Smuzhiyun 
abx500_temp_resume(struct platform_device * pdev)454*4882a593Smuzhiyun static int abx500_temp_resume(struct platform_device *pdev)
455*4882a593Smuzhiyun {
456*4882a593Smuzhiyun 	struct abx500_temp *data = platform_get_drvdata(pdev);
457*4882a593Smuzhiyun 
458*4882a593Smuzhiyun 	if (data->work_active)
459*4882a593Smuzhiyun 		schedule_monitor(data);
460*4882a593Smuzhiyun 
461*4882a593Smuzhiyun 	return 0;
462*4882a593Smuzhiyun }
463*4882a593Smuzhiyun 
464*4882a593Smuzhiyun #ifdef CONFIG_OF
465*4882a593Smuzhiyun static const struct of_device_id abx500_temp_match[] = {
466*4882a593Smuzhiyun 	{ .compatible = "stericsson,abx500-temp" },
467*4882a593Smuzhiyun 	{},
468*4882a593Smuzhiyun };
469*4882a593Smuzhiyun MODULE_DEVICE_TABLE(of, abx500_temp_match);
470*4882a593Smuzhiyun #endif
471*4882a593Smuzhiyun 
472*4882a593Smuzhiyun static struct platform_driver abx500_temp_driver = {
473*4882a593Smuzhiyun 	.driver = {
474*4882a593Smuzhiyun 		.name = "abx500-temp",
475*4882a593Smuzhiyun 		.of_match_table = of_match_ptr(abx500_temp_match),
476*4882a593Smuzhiyun 	},
477*4882a593Smuzhiyun 	.suspend = abx500_temp_suspend,
478*4882a593Smuzhiyun 	.resume = abx500_temp_resume,
479*4882a593Smuzhiyun 	.probe = abx500_temp_probe,
480*4882a593Smuzhiyun 	.remove = abx500_temp_remove,
481*4882a593Smuzhiyun };
482*4882a593Smuzhiyun 
483*4882a593Smuzhiyun module_platform_driver(abx500_temp_driver);
484*4882a593Smuzhiyun 
485*4882a593Smuzhiyun MODULE_AUTHOR("Martin Persson <martin.persson@stericsson.com>");
486*4882a593Smuzhiyun MODULE_DESCRIPTION("ABX500 temperature driver");
487*4882a593Smuzhiyun MODULE_LICENSE("GPL");
488