1c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/*
2c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * A hwmon driver for the Analog Devices ADT7462
3c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * Copyright (C) 2008 IBM
4c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
5c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * Author: Darrick J. Wong <djwong@us.ibm.com>
6c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
7c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * This program is free software; you can redistribute it and/or modify
8c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * it under the terms of the GNU General Public License as published by
9c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * the Free Software Foundation; either version 2 of the License, or
10c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * (at your option) any later version.
11c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
12c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * This program is distributed in the hope that it will be useful,
13c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * but WITHOUT ANY WARRANTY; without even the implied warranty of
14c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * GNU General Public License for more details.
16c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
17c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * You should have received a copy of the GNU General Public License
18c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * along with this program; if not, write to the Free Software
19c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong */
21c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
22c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/module.h>
23c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/jiffies.h>
24c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/i2c.h>
25c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/hwmon.h>
26c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/hwmon-sysfs.h>
27c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/err.h>
28c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/mutex.h>
29c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/delay.h>
30c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#include <linux/log2.h>
315a0e3ad6af8660be21ca98a971cd00f331318c05Tejun Heo#include <linux/slab.h>
32c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
33c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* Addresses to scan */
34c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic const unsigned short normal_i2c[] = { 0x58, 0x5C, I2C_CLIENT_END };
35c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
36c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* ADT7462 registers */
37c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_DEVICE			0x3D
38c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_VENDOR			0x3E
39c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_REVISION			0x3F
40c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
41c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_MIN_TEMP_BASE_ADDR		0x44
42c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_MIN_TEMP_MAX_ADDR		0x47
43c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_MAX_TEMP_BASE_ADDR		0x48
44c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_MAX_TEMP_MAX_ADDR		0x4B
45c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_TEMP_BASE_ADDR		0x88
46c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_TEMP_MAX_ADDR		0x8F
47c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
48c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN_BASE_ADDR		0x98
49c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN_MAX_ADDR		0x9F
50c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN2_BASE_ADDR		0xA2
51c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN2_MAX_ADDR		0xA9
52c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN_ENABLE			0x07
53c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN_MIN_BASE_ADDR		0x78
54c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN_MIN_MAX_ADDR		0x7F
55c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
56c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_CFG2			0x02
57c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_FSPD_MASK		0x20
58c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
59c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_BASE_ADDR		0xAA
60c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_MAX_ADDR		0xAD
61c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define	ADT7462_REG_PWM_MIN_BASE_ADDR		0x28
62c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_MIN_MAX_ADDR		0x2B
63c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_MAX			0x2C
64c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_TEMP_MIN_BASE_ADDR	0x5C
65c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_TEMP_MIN_MAX_ADDR	0x5F
66c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_TEMP_RANGE_BASE_ADDR	0x60
67c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_TEMP_RANGE_MAX_ADDR	0x63
68724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define	ADT7462_PWM_HYST_MASK			0x0F
69724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define	ADT7462_PWM_RANGE_MASK			0xF0
70c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PWM_RANGE_SHIFT		4
71c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_CFG_BASE_ADDR		0x21
72c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_CFG_MAX_ADDR		0x24
73c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PWM_CHANNEL_MASK	0xE0
74c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PWM_CHANNEL_SHIFT	5
75c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
76c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PIN_CFG_BASE_ADDR		0x10
77c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PIN_CFG_MAX_ADDR		0x13
78c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN7_INPUT		0x01	/* cfg0 */
79c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_DIODE3_INPUT		0x20
80c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_DIODE1_INPUT		0x40
81c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_VID_INPUT		0x80
82c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN22_INPUT		0x04	/* cfg1 */
83c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN21_INPUT		0x08
84c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN19_INPUT		0x10
85c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN15_INPUT		0x20
86c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN13_INPUT		0x40
87c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN8_INPUT		0x80
88724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define		ADT7462_PIN23_MASK		0x03
89c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN23_SHIFT		0
90c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN26_MASK		0x0C	/* cfg2 */
91c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN26_SHIFT		2
92c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN25_MASK		0x30
93c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN25_SHIFT		4
94c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN24_MASK		0xC0
95c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN24_SHIFT		6
96c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN26_VOLT_INPUT	0x08
97c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN25_VOLT_INPUT	0x20
98bb595c923bc51dff9cdd112de18deb57ac7945d2Roger Blofeld#define		ADT7462_PIN28_SHIFT		4	/* cfg3 */
99c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_PIN28_VOLT		0x5
100c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
101c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_ALARM1			0xB8
102724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define	ADT7462_LT_ALARM			0x02
103c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_R1T_ALARM		0x04
104c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_R2T_ALARM		0x08
105c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_R3T_ALARM		0x10
106c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_ALARM2			0xBB
107c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V0_ALARM		0x01
108c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V1_ALARM		0x02
109c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V2_ALARM		0x04
110c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V3_ALARM		0x08
111c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V4_ALARM		0x10
112c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V5_ALARM		0x20
113c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V6_ALARM		0x40
114c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V7_ALARM		0x80
115c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_ALARM3			0xBC
116c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V8_ALARM		0x08
117c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V9_ALARM		0x10
118c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V10_ALARM		0x20
119c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V11_ALARM		0x40
120c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_V12_ALARM		0x80
121c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_ALARM4			0xBD
122c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F0_ALARM		0x01
123c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F1_ALARM		0x02
124c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F2_ALARM		0x04
125c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F3_ALARM		0x08
126c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F4_ALARM		0x10
127c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F5_ALARM		0x20
128c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F6_ALARM		0x40
129c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define		ADT7462_F7_ALARM		0x80
130c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM1				0x0000
131c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM2				0x0100
132c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM3				0x0200
133c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM4				0x0300
134c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM_REG_SHIFT			8
135c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM_FLAG_MASK			0x0F
136c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
137c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_TEMP_COUNT		4
138724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define ADT7462_TEMP_REG(x)		(ADT7462_REG_TEMP_BASE_ADDR + ((x) * 2))
139724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define ADT7462_TEMP_MIN_REG(x)		(ADT7462_REG_MIN_TEMP_BASE_ADDR + (x))
140724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeck#define ADT7462_TEMP_MAX_REG(x)		(ADT7462_REG_MAX_TEMP_BASE_ADDR + (x))
141c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define TEMP_FRAC_OFFSET		6
142c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
143c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_FAN_COUNT		8
144c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_FAN_MIN(x)		(ADT7462_REG_FAN_MIN_BASE_ADDR + (x))
145c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
146c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_PWM_COUNT		4
147c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM(x)		(ADT7462_REG_PWM_BASE_ADDR + (x))
148c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_MIN(x)		(ADT7462_REG_PWM_MIN_BASE_ADDR + (x))
149c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_TMIN(x)		\
150c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	(ADT7462_REG_PWM_TEMP_MIN_BASE_ADDR + (x))
151c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_TRANGE(x)	\
152c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	(ADT7462_REG_PWM_TEMP_RANGE_BASE_ADDR + (x))
153c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
154c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_PIN_CFG_REG_COUNT	4
155c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PIN_CFG(x)		(ADT7462_REG_PIN_CFG_BASE_ADDR + (x))
156c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REG_PWM_CFG(x)		(ADT7462_REG_PWM_CFG_BASE_ADDR + (x))
157c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
158c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_ALARM_REG_COUNT		4
159c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
160c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/*
161c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * The chip can measure 13 different voltage sources:
162c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
163c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 1. +12V1 (pin 7)
164c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 2. Vccp1/+2.5V/+1.8V/+1.5V (pin 23)
165c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 3. +12V3 (pin 22)
166c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 4. +5V (pin 21)
167c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 5. +1.25V/+0.9V (pin 19)
168c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 6. +2.5V/+1.8V (pin 15)
169c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 7. +3.3v (pin 13)
170c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 8. +12V2 (pin 8)
171c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 9. Vbatt/FSB_Vtt (pin 26)
172c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * A. +3.3V/+1.2V1 (pin 25)
173c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * B. Vccp2/+2.5V/+1.8V/+1.5V (pin 24)
174c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * C. +1.5V ICH (only if BOTH pin 28/29 are set to +1.5V)
175c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * D. +1.5V 3GPIO (only if BOTH pin 28/29 are set to +1.5V)
176c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
177c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * Each of these 13 has a factor to convert raw to voltage.  Even better,
178c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * the pins can be connected to other sensors (tach/gpio/hot/etc), which
179c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * makes the bookkeeping tricky.
180c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong *
181c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * Some, but not all, of these voltages have low/high limits.
182c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong */
18385f8d3e5faea8bd36c3e5196f8334f7db45e19b2Ray Copeland#define ADT7462_VOLT_COUNT	13
184c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
185c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_VENDOR		0x41
186c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_DEVICE		0x62
187c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* datasheet only mentions a revision 4 */
188c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define ADT7462_REVISION	0x04
189c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
190c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* How often do we reread sensors values? (In jiffies) */
191c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define SENSOR_REFRESH_INTERVAL	(2 * HZ)
192c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
193c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* How often do we reread sensor limit values? (In jiffies) */
194c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define LIMIT_REFRESH_INTERVAL	(60 * HZ)
195c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
196c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* datasheet says to divide this number by the fan reading to get fan rpm */
197c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define FAN_PERIOD_TO_RPM(x)	((90000 * 60) / (x))
198c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define FAN_RPM_TO_PERIOD	FAN_PERIOD_TO_RPM
199c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define FAN_PERIOD_INVALID	65535
200c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define FAN_DATA_VALID(x)	((x) && (x) != FAN_PERIOD_INVALID)
201c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
202c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define MASK_AND_SHIFT(value, prefix)	\
203c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	(((value) & prefix##_MASK) >> prefix##_SHIFT)
204c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
205c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstruct adt7462_data {
206c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct device		*hwmon_dev;
207c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct attribute_group	attrs;
208c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct mutex		lock;
209c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	char			sensors_valid;
210c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	char			limits_valid;
211c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	unsigned long		sensors_last_updated;	/* In jiffies */
212c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	unsigned long		limits_last_updated;	/* In jiffies */
213c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
214c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			temp[ADT7462_TEMP_COUNT];
215c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				/* bits 6-7 are quarter pieces of temp */
216c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			temp_frac[ADT7462_TEMP_COUNT];
217c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			temp_min[ADT7462_TEMP_COUNT];
218c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			temp_max[ADT7462_TEMP_COUNT];
219c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u16			fan[ADT7462_FAN_COUNT];
220c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			fan_enabled;
221c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			fan_min[ADT7462_FAN_COUNT];
222c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			cfg2;
223c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pwm[ADT7462_PWM_COUNT];
224c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pin_cfg[ADT7462_PIN_CFG_REG_COUNT];
225c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			voltages[ADT7462_VOLT_COUNT];
226c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			volt_max[ADT7462_VOLT_COUNT];
227c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			volt_min[ADT7462_VOLT_COUNT];
228c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pwm_min[ADT7462_PWM_COUNT];
229c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pwm_tmin[ADT7462_PWM_COUNT];
230c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pwm_trange[ADT7462_PWM_COUNT];
231c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pwm_max;	/* only one per chip */
232c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			pwm_cfg[ADT7462_PWM_COUNT];
233c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8			alarms[ADT7462_ALARM_REG_COUNT];
234c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong};
235c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
236c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int adt7462_probe(struct i2c_client *client,
237c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			 const struct i2c_device_id *id);
238310ec79210d754afe51e2e4a983e846b60179abdJean Delvarestatic int adt7462_detect(struct i2c_client *client,
239c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  struct i2c_board_info *info);
240c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int adt7462_remove(struct i2c_client *client);
241c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
242c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic const struct i2c_device_id adt7462_id[] = {
2431f86df49ddfd0067cce941187d57b2fd2f749a9eJean Delvare	{ "adt7462", 0 },
244c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	{ }
245c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong};
246c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. WongMODULE_DEVICE_TABLE(i2c, adt7462_id);
247c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
248c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic struct i2c_driver adt7462_driver = {
249c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	.class		= I2C_CLASS_HWMON,
250c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	.driver = {
251c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		.name	= "adt7462",
252c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	},
253c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	.probe		= adt7462_probe,
254c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	.remove		= adt7462_remove,
255c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	.id_table	= adt7462_id,
256c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	.detect		= adt7462_detect,
257c3813d6af177fab19e322f3114b1f64fbcf08d71Jean Delvare	.address_list	= normal_i2c,
258c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong};
259c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
260c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/*
261c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * 16-bit registers on the ADT7462 are low-byte first.  The data sheet says
262c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong * that the low byte must be read before the high byte.
263c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong */
264c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic inline int adt7462_read_word_data(struct i2c_client *client, u8 reg)
265c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
266c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u16 foo;
267c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	foo = i2c_smbus_read_byte_data(client, reg);
268c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	foo |= ((u16)i2c_smbus_read_byte_data(client, reg + 1) << 8);
269c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return foo;
270c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
271c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
272c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* For some reason these registers are not contiguous. */
273c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int ADT7462_REG_FAN(int fan)
274c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
275c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (fan < 4)
276c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return ADT7462_REG_FAN_BASE_ADDR + (2 * fan);
277c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return ADT7462_REG_FAN2_BASE_ADDR + (2 * (fan - 4));
278c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
279c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
280c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* Voltage registers are scattered everywhere */
281c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int ADT7462_REG_VOLT_MAX(struct adt7462_data *data, int which)
282c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
283c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
284c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
285c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_PIN7_INPUT))
286c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x7C;
287c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
288c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
289c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 0x69;
290c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
291c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN22_INPUT))
292c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x7F;
293c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
294c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
295c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN21_INPUT))
296c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x7E;
297c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
298c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 4:
299c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE3_INPUT))
300c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x4B;
301c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
302c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 5:
303c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE1_INPUT))
304c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x49;
305c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
306c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 6:
307c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN13_INPUT))
308c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x68;
309c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
310c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 7:
311c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN8_INPUT))
312c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x7D;
313c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
314c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 8:
315c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[2] & ADT7462_PIN26_VOLT_INPUT))
316c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x6C;
317c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
318c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 9:
319c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[2] & ADT7462_PIN25_VOLT_INPUT))
320c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x6B;
321c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
322c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 10:
323c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 0x6A;
324c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 11:
325c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
326c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
327c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
328c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x50;
329c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
330c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 12:
331c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
332c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
333c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
334c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x4C;
335c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
336c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
337c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return -ENODEV;
338c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
339c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
340c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int ADT7462_REG_VOLT_MIN(struct adt7462_data *data, int which)
341c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
342c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
343c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
344c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_PIN7_INPUT))
345c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x6D;
346c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
347c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
348c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 0x72;
349c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
350c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN22_INPUT))
351c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x6F;
352c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
353c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
354c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN21_INPUT))
355c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x71;
356c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
357c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 4:
358c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE3_INPUT))
359c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x47;
360c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
361c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 5:
362c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE1_INPUT))
363c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x45;
364c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
365c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 6:
366c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN13_INPUT))
367c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x70;
368c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
369c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 7:
370c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN8_INPUT))
371c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x6E;
372c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
373c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 8:
374c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[2] & ADT7462_PIN26_VOLT_INPUT))
375c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x75;
376c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
377c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 9:
378c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[2] & ADT7462_PIN25_VOLT_INPUT))
379c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x74;
380c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
381c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 10:
382c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 0x73;
383c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 11:
384c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
385c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
386c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
387c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x76;
388c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
389c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 12:
390c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
391c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
392c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
393c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x77;
394c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
395c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
396c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return -ENODEV;
397c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
398c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
399c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int ADT7462_REG_VOLT(struct adt7462_data *data, int which)
400c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
401c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
402c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
403c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_PIN7_INPUT))
404c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0xA3;
405c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
406c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
407c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 0x90;
408c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
409c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN22_INPUT))
410c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0xA9;
411c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
412c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
413c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN21_INPUT))
414c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0xA7;
415c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
416c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 4:
417c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE3_INPUT))
418c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x8F;
419c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
420c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 5:
421c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE1_INPUT))
422c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x8B;
423c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
424c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 6:
425c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN13_INPUT))
426c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x96;
427c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
428c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 7:
429c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN8_INPUT))
430c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0xA5;
431c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
432c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 8:
433c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[2] & ADT7462_PIN26_VOLT_INPUT))
434c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x93;
435c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
436c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 9:
437c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[2] & ADT7462_PIN25_VOLT_INPUT))
438c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x92;
439c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
440c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 10:
441c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 0x91;
442c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 11:
443c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
444c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
445c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
446c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x94;
447c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
448c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 12:
449c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
450c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
451c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
452c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 0x95;
453c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
454c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
455c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return -ENODEV;
456c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
457c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
458c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* Provide labels for sysfs */
459c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic const char *voltage_label(struct adt7462_data *data, int which)
460c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
461c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
462c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
463c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_PIN7_INPUT))
464c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+12V1";
465c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
466c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
467c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[1], ADT7462_PIN23)) {
468c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
469c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "Vccp1";
470c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
471c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+2.5V";
472c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 2:
473c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.8V";
474c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 3:
475c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.5V";
476c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
477c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
478c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN22_INPUT))
479c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+12V3";
480c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
481c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
482c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN21_INPUT))
483c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+5V";
484c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
485c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 4:
486c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE3_INPUT)) {
487c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			if (data->pin_cfg[1] & ADT7462_PIN19_INPUT)
488c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				return "+0.9V";
489c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.25V";
490c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
491c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
492c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 5:
493c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE1_INPUT)) {
494c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			if (data->pin_cfg[1] & ADT7462_PIN19_INPUT)
495c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				return "+1.8V";
496c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+2.5V";
497c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
498c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
499c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 6:
500c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN13_INPUT))
501c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+3.3V";
502c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
503c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 7:
504c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN8_INPUT))
505c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+12V2";
506c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
507c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 8:
508c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[2], ADT7462_PIN26)) {
509c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
510c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "Vbatt";
511c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
512c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "FSB_Vtt";
513c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
514c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
515c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 9:
516c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[2], ADT7462_PIN25)) {
517c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
518c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+3.3V";
519c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
520c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.2V1";
521c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
522c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
523c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 10:
524c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[2], ADT7462_PIN24)) {
525c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
526c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "Vccp2";
527c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
528c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+2.5V";
529c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 2:
530c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.8V";
531c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 3:
532c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.5";
533c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
534c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 11:
535c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
536c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
537c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
538c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.5V ICH";
539c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
540c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 12:
541c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
542c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
543c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
544c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "+1.5V 3GPIO";
545c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
546c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
547c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return "N/A";
548c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
549c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
550c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* Multipliers are actually in uV, not mV. */
551c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int voltage_multiplier(struct adt7462_data *data, int which)
552c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
553c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
554c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
555c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_PIN7_INPUT))
556c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 62500;
557c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
558c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
559c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[1], ADT7462_PIN23)) {
560c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
561c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			if (data->pin_cfg[0] & ADT7462_VID_INPUT)
562c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				return 12500;
563c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 6250;
564c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
565c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 13000;
566c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 2:
567c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 9400;
568c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 3:
569c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 7800;
570c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
571c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
572c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN22_INPUT))
573c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 62500;
574c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
575c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
576c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN21_INPUT))
577c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 26000;
578c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
579c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 4:
580c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE3_INPUT)) {
581c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			if (data->pin_cfg[1] & ADT7462_PIN19_INPUT)
582c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				return 4690;
583c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 6500;
584c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
585c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
586c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 5:
587c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[0] & ADT7462_DIODE1_INPUT)) {
588c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			if (data->pin_cfg[1] & ADT7462_PIN15_INPUT)
589c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				return 9400;
590c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 13000;
591c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
592c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
593c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 6:
594c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN13_INPUT))
595c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 17200;
596c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
597c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 7:
598c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!(data->pin_cfg[1] & ADT7462_PIN8_INPUT))
599c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 62500;
600c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
601c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 8:
602c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[2], ADT7462_PIN26)) {
603c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
604c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 15600;
605c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
606c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 6250;
607c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
608c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
609c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 9:
610c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[2], ADT7462_PIN25)) {
611c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
612c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 17200;
613c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
614c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 6250;
615c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
616c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
617c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 10:
618c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		switch (MASK_AND_SHIFT(data->pin_cfg[2], ADT7462_PIN24)) {
619c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 0:
620c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 6250;
621c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 1:
622c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 13000;
623c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 2:
624c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 9400;
625c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		case 3:
626c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 7800;
627c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		}
628c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 11:
629c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 12:
630c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[3] >> ADT7462_PIN28_SHIFT ==
631c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_PIN28_VOLT &&
632c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    !(data->pin_cfg[0] & ADT7462_VID_INPUT))
633c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 7800;
634c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
635c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return 0;
636c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
637c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
638c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int temp_enabled(struct adt7462_data *data, int which)
639c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
640c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
641c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
642c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
643c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 1;
644c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
645c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[0] & ADT7462_DIODE1_INPUT)
646c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 1;
647c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
648c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
649c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[0] & ADT7462_DIODE3_INPUT)
650c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return 1;
651c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
652c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
653c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return 0;
654c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
655c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
656c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic const char *temp_label(struct adt7462_data *data, int which)
657c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
658c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (which) {
659c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0:
660c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return "local";
661c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
662c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[0] & ADT7462_DIODE1_INPUT)
663c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "remote1";
664c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
665c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
666c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return "remote2";
667c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
668c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (data->pin_cfg[0] & ADT7462_DIODE3_INPUT)
669c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return "remote3";
670c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		break;
671c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
672c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return "N/A";
673c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
674c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
675c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* Map Trange register values to mC */
676c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong#define NUM_TRANGE_VALUES	16
677c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic const int trange_values[NUM_TRANGE_VALUES] = {
678c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	2000,
679c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	2500,
680c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	3300,
681c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	4000,
682c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	5000,
683c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	6700,
684c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	8000,
685c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	10000,
686c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	13300,
687c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	16000,
688c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	20000,
689c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	26700,
690c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	32000,
691c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	40000,
692c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	53300,
693c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	80000
694c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong};
695c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
696c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int find_trange_value(int trange)
697c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
698c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int i;
699c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
700c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < NUM_TRANGE_VALUES; i++)
701c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (trange_values[i] == trange)
702c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			return i;
703c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
704c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return -ENODEV;
705c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
706c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
707c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic struct adt7462_data *adt7462_update_device(struct device *dev)
708c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
709c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
710c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
711c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	unsigned long local_jiffies = jiffies;
712c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int i;
713c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
714c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
715c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (time_before(local_jiffies, data->sensors_last_updated +
716c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		SENSOR_REFRESH_INTERVAL)
717c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		&& data->sensors_valid)
718c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		goto no_sensor_update;
719c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
720c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_TEMP_COUNT; i++) {
721c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		/*
722c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		 * Reading the fractional register locks the integral
723c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		 * register until both have been read.
724c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		 */
725c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->temp_frac[i] = i2c_smbus_read_byte_data(client,
726c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_TEMP_REG(i));
727c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->temp[i] = i2c_smbus_read_byte_data(client,
728c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_TEMP_REG(i) + 1);
729c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
730c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
731c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_FAN_COUNT; i++)
732c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->fan[i] = adt7462_read_word_data(client,
733c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_FAN(i));
734c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
735c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->fan_enabled = i2c_smbus_read_byte_data(client,
736c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong					ADT7462_REG_FAN_ENABLE);
737c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
738c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_PWM_COUNT; i++)
739c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->pwm[i] = i2c_smbus_read_byte_data(client,
740c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_PWM(i));
741c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
742c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_PIN_CFG_REG_COUNT; i++)
743c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->pin_cfg[i] = i2c_smbus_read_byte_data(client,
744c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				ADT7462_REG_PIN_CFG(i));
745c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
746c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_VOLT_COUNT; i++) {
747c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		int reg = ADT7462_REG_VOLT(data, i);
748c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		if (!reg)
749c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			data->voltages[i] = 0;
750c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		else
751c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			data->voltages[i] = i2c_smbus_read_byte_data(client,
752c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong								     reg);
753c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
754c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
755c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->alarms[0] = i2c_smbus_read_byte_data(client, ADT7462_REG_ALARM1);
756c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->alarms[1] = i2c_smbus_read_byte_data(client, ADT7462_REG_ALARM2);
757c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->alarms[2] = i2c_smbus_read_byte_data(client, ADT7462_REG_ALARM3);
758c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->alarms[3] = i2c_smbus_read_byte_data(client, ADT7462_REG_ALARM4);
759c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
760c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->sensors_last_updated = local_jiffies;
761c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->sensors_valid = 1;
762c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
763c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongno_sensor_update:
764c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (time_before(local_jiffies, data->limits_last_updated +
765c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		LIMIT_REFRESH_INTERVAL)
766c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		&& data->limits_valid)
767c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		goto out;
768c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
769c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_TEMP_COUNT; i++) {
770c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->temp_min[i] = i2c_smbus_read_byte_data(client,
771c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_TEMP_MIN_REG(i));
772c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->temp_max[i] = i2c_smbus_read_byte_data(client,
773c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_TEMP_MAX_REG(i));
774c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
775c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
776c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_FAN_COUNT; i++)
777c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->fan_min[i] = i2c_smbus_read_byte_data(client,
778c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_FAN_MIN(i));
779c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
780c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_VOLT_COUNT; i++) {
781c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		int reg = ADT7462_REG_VOLT_MAX(data, i);
782c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->volt_max[i] =
783c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			(reg ? i2c_smbus_read_byte_data(client, reg) : 0);
784c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
785c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		reg = ADT7462_REG_VOLT_MIN(data, i);
786c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->volt_min[i] =
787c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			(reg ? i2c_smbus_read_byte_data(client, reg) : 0);
788c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
789c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
790c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	for (i = 0; i < ADT7462_PWM_COUNT; i++) {
791c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->pwm_min[i] = i2c_smbus_read_byte_data(client,
792c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_PWM_MIN(i));
793c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->pwm_tmin[i] = i2c_smbus_read_byte_data(client,
794c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_PWM_TMIN(i));
795c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->pwm_trange[i] = i2c_smbus_read_byte_data(client,
796c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_PWM_TRANGE(i));
797c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		data->pwm_cfg[i] = i2c_smbus_read_byte_data(client,
798c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong						ADT7462_REG_PWM_CFG(i));
799c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
800c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
801c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_max = i2c_smbus_read_byte_data(client, ADT7462_REG_PWM_MAX);
802c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
803c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->cfg2 = i2c_smbus_read_byte_data(client, ADT7462_REG_CFG2);
804c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
805c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->limits_last_updated = local_jiffies;
806c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->limits_valid = 1;
807c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
808c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongout:
809c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
810c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return data;
811c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
812c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
813c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_temp_min(struct device *dev,
814c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
815c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
816c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
817c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
818c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
819c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
820c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!temp_enabled(data, attr->index))
821c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
822c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
823c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", 1000 * (data->temp_min[attr->index] - 64));
824c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
825c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
826c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_temp_min(struct device *dev,
827c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
828c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
829c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
830c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
831c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
832c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
833c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
834c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
835c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
836179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp) || !temp_enabled(data, attr->index))
837c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
838c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
8398f8c1fb0c829278b889588da211a5a557518b06cDarrick J. Wong	temp = DIV_ROUND_CLOSEST(temp, 1000) + 64;
840c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
841c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
842c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
843c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->temp_min[attr->index] = temp;
844c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_TEMP_MIN_REG(attr->index),
845c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
846c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
847c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
848c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
849c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
850c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
851c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_temp_max(struct device *dev,
852c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
853c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
854c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
855c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
856c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
857c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
858c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!temp_enabled(data, attr->index))
859c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
860c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
861c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", 1000 * (data->temp_max[attr->index] - 64));
862c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
863c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
864c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_temp_max(struct device *dev,
865c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
866c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
867c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
868c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
869c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
870c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
871c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
872c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
873c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
874179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp) || !temp_enabled(data, attr->index))
875c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
876c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
8778f8c1fb0c829278b889588da211a5a557518b06cDarrick J. Wong	temp = DIV_ROUND_CLOSEST(temp, 1000) + 64;
878c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
879c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
880c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
881c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->temp_max[attr->index] = temp;
882c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_TEMP_MAX_REG(attr->index),
883c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
884c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
885c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
886c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
887c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
888c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
889c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_temp(struct device *dev, struct device_attribute *devattr,
890c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			 char *buf)
891c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
892c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
893c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
894c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8 frac = data->temp_frac[attr->index] >> TEMP_FRAC_OFFSET;
895c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
896c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!temp_enabled(data, attr->index))
897c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
898c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
899c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", 1000 * (data->temp[attr->index] - 64) +
900c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				     250 * frac);
901c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
902c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
903c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_temp_label(struct device *dev,
904c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			       struct device_attribute *devattr,
905c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			       char *buf)
906c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
907c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
908c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
909c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
910c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%s\n", temp_label(data, attr->index));
911c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
912c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
913c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_volt_max(struct device *dev,
914c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
915c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
916c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
917c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
918c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
919c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int x = voltage_multiplier(data, attr->index);
920c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
921c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	x *= data->volt_max[attr->index];
922c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	x /= 1000; /* convert from uV to mV */
923c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
924c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", x);
925c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
926c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
927c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_volt_max(struct device *dev,
928c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
929c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
930c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
931c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
932c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
933c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
934c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
935c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int x = voltage_multiplier(data, attr->index);
936c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
937c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
938179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp) || !x)
939c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
940c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
941c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp *= 1000; /* convert mV to uV */
9428f8c1fb0c829278b889588da211a5a557518b06cDarrick J. Wong	temp = DIV_ROUND_CLOSEST(temp, x);
943c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
944c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
945c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
946c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->volt_max[attr->index] = temp;
947c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client,
948c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  ADT7462_REG_VOLT_MAX(data, attr->index),
949c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
950c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
951c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
952c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
953c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
954c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
955c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_volt_min(struct device *dev,
956c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
957c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
958c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
959c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
960c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
961c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int x = voltage_multiplier(data, attr->index);
962c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
963c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	x *= data->volt_min[attr->index];
964c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	x /= 1000; /* convert from uV to mV */
965c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
966c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", x);
967c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
968c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
969c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_volt_min(struct device *dev,
970c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
971c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
972c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
973c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
974c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
975c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
976c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
977c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int x = voltage_multiplier(data, attr->index);
978c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
979c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
980179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp) || !x)
981c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
982c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
983c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp *= 1000; /* convert mV to uV */
9848f8c1fb0c829278b889588da211a5a557518b06cDarrick J. Wong	temp = DIV_ROUND_CLOSEST(temp, x);
985c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
986c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
987c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
988c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->volt_min[attr->index] = temp;
989c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client,
990c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  ADT7462_REG_VOLT_MIN(data, attr->index),
991c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
992c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
993c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
994c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
995c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
996c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
997c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_voltage(struct device *dev,
998c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
999c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    char *buf)
1000c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1001c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1002c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1003c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int x = voltage_multiplier(data, attr->index);
1004c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1005c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	x *= data->voltages[attr->index];
1006c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	x /= 1000; /* convert from uV to mV */
1007c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1008c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", x);
1009c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1010c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1011c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_voltage_label(struct device *dev,
1012c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  struct device_attribute *devattr,
1013c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  char *buf)
1014c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1015c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1016c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1017c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1018c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%s\n", voltage_label(data, attr->index));
1019c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1020c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1021c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_alarm(struct device *dev,
1022c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  struct device_attribute *devattr,
1023c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  char *buf)
1024c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1025c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1026c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1027c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int reg = attr->index >> ADT7462_ALARM_REG_SHIFT;
1028c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int mask = attr->index & ADT7462_ALARM_FLAG_MASK;
1029c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1030c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (data->alarms[reg] & mask)
1031c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "1\n");
1032c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	else
1033c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
1034c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1035c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1036c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int fan_enabled(struct adt7462_data *data, int fan)
1037c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1038c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return data->fan_enabled & (1 << fan);
1039c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1040c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1041c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_fan_min(struct device *dev,
1042c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1043c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    char *buf)
1044c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1045c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1046c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1047c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u16 temp;
1048c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1049c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	/* Only the MSB of the min fan period is stored... */
1050c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = data->fan_min[attr->index];
1051c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp <<= 8;
1052c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1053c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!fan_enabled(data, attr->index) ||
1054c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	    !FAN_DATA_VALID(temp))
1055c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
1056c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1057c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", FAN_PERIOD_TO_RPM(temp));
1058c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1059c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1060c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_fan_min(struct device *dev,
1061c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   struct device_attribute *devattr,
1062c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   const char *buf, size_t count)
1063c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1064c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1065c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1066c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1067c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1068c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1069179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp) || !temp ||
1070c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	    !fan_enabled(data, attr->index))
1071c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1072c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1073c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = FAN_RPM_TO_PERIOD(temp);
1074c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp >>= 8;
1075c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 1, 255);
1076c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1077c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1078c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->fan_min[attr->index] = temp;
1079c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_FAN_MIN(attr->index),
1080c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
1081c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1082c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1083c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1084c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1085c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1086c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_fan(struct device *dev, struct device_attribute *devattr,
1087c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			char *buf)
1088c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1089c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1090c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1091c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1092c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!fan_enabled(data, attr->index) ||
1093c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	    !FAN_DATA_VALID(data->fan[attr->index]))
1094c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
1095c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1096c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n",
1097c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		       FAN_PERIOD_TO_RPM(data->fan[attr->index]));
1098c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1099c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1100c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_force_pwm_max(struct device *dev,
1101c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  struct device_attribute *devattr,
1102c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  char *buf)
1103c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1104c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1105c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", (data->cfg2 & ADT7462_FSPD_MASK ? 1 : 0));
1106c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1107c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1108c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_force_pwm_max(struct device *dev,
1109c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				 struct device_attribute *devattr,
1110c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				 const char *buf,
1111c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				 size_t count)
1112c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1113c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1114c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1115c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1116c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	u8 reg;
1117c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1118179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1119c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1120c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1121c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1122c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	reg = i2c_smbus_read_byte_data(client, ADT7462_REG_CFG2);
1123c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (temp)
1124c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		reg |= ADT7462_FSPD_MASK;
1125c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	else
1126c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		reg &= ~ADT7462_FSPD_MASK;
1127c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->cfg2 = reg;
1128c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_CFG2, reg);
1129c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1130c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1131c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1132c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1133c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1134c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm(struct device *dev, struct device_attribute *devattr,
1135c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			char *buf)
1136c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1137c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1138c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1139c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", data->pwm[attr->index]);
1140c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1141c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1142c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm(struct device *dev, struct device_attribute *devattr,
1143c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			const char *buf, size_t count)
1144c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1145c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1146c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1147c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1148c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1149c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1150179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1151c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1152c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1153c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
1154c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1155c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1156c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm[attr->index] = temp;
1157c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM(attr->index), temp);
1158c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1159c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1160c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1161c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1162c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1163c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_max(struct device *dev,
1164c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1165c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    char *buf)
1166c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1167c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1168c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", data->pwm_max);
1169c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1170c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1171c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_max(struct device *dev,
1172c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   struct device_attribute *devattr,
1173c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   const char *buf,
1174c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   size_t count)
1175c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1176c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1177c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1178c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1179c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1180179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1181c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1182c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1183c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
1184c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1185c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1186c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_max = temp;
1187c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM_MAX, temp);
1188c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1189c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1190c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1191c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1192c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1193c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_min(struct device *dev,
1194c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1195c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    char *buf)
1196c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1197c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1198c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1199c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", data->pwm_min[attr->index]);
1200c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1201c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1202c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_min(struct device *dev,
1203c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   struct device_attribute *devattr,
1204c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   const char *buf,
1205c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			   size_t count)
1206c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1207c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1208c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1209c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1210c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1211c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1212179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1213c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1214c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1215c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
1216c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1217c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1218c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_min[attr->index] = temp;
1219c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM_MIN(attr->index),
1220c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
1221c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1222c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1223c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1224c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1225c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1226c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_hyst(struct device *dev,
1227c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
1228c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
1229c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1230c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1231c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1232c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", 1000 *
1233c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		      (data->pwm_trange[attr->index] & ADT7462_PWM_HYST_MASK));
1234c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1235c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1236c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_hyst(struct device *dev,
1237c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1238c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
1239c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
1240c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1241c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1242c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1243c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1244c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1245c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1246179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1247c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1248c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
12498f8c1fb0c829278b889588da211a5a557518b06cDarrick J. Wong	temp = DIV_ROUND_CLOSEST(temp, 1000);
1250c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 15);
1251c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1252c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	/* package things up */
1253c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp &= ADT7462_PWM_HYST_MASK;
1254c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp |= data->pwm_trange[attr->index] & ADT7462_PWM_RANGE_MASK;
1255c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1256c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1257c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_trange[attr->index] = temp;
1258c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM_TRANGE(attr->index),
1259c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
1260c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1261c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1262c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1263c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1264c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1265c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_tmax(struct device *dev,
1266c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
1267c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
1268c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1269c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1270c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1271c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1272c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	/* tmax = tmin + trange */
1273c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int trange = trange_values[data->pwm_trange[attr->index] >>
1274c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				   ADT7462_PWM_RANGE_SHIFT];
1275c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int tmin = (data->pwm_tmin[attr->index] - 64) * 1000;
1276c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1277c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", tmin + trange);
1278c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1279c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1280c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_tmax(struct device *dev,
1281c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1282c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
1283c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
1284c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1285c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int temp;
1286c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1287c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1288c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1289c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int tmin, trange_value;
1290c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long trange;
1291c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1292179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &trange))
1293c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1294c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1295c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	/* trange = tmax - tmin */
1296c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	tmin = (data->pwm_tmin[attr->index] - 64) * 1000;
1297c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	trange_value = find_trange_value(trange - tmin);
1298c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1299c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (trange_value < 0)
1300c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1301c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1302c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = trange_value << ADT7462_PWM_RANGE_SHIFT;
1303c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp |= data->pwm_trange[attr->index] & ADT7462_PWM_HYST_MASK;
1304c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1305c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1306c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_trange[attr->index] = temp;
1307c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM_TRANGE(attr->index),
1308c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
1309c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1310c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1311c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1312c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1313c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1314c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_tmin(struct device *dev,
1315c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
1316c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
1317c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1318c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1319c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1320c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return sprintf(buf, "%d\n", 1000 * (data->pwm_tmin[attr->index] - 64));
1321c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1322c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1323c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_tmin(struct device *dev,
1324c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1325c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
1326c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
1327c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1328c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1329c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1330c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1331c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1332c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1333179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1334c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1335c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
13368f8c1fb0c829278b889588da211a5a557518b06cDarrick J. Wong	temp = DIV_ROUND_CLOSEST(temp, 1000) + 64;
1337c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = SENSORS_LIMIT(temp, 0, 255);
1338c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1339c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1340c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_tmin[attr->index] = temp;
1341c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM_TMIN(attr->index),
1342c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  temp);
1343c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1344c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1345c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1346c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1347c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1348c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_auto(struct device *dev,
1349c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     struct device_attribute *devattr,
1350c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			     char *buf)
1351c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1352c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1353c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1354c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int cfg = data->pwm_cfg[attr->index] >> ADT7462_PWM_CHANNEL_SHIFT;
1355c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1356c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (cfg) {
1357c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 4: /* off */
1358c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
1359c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 7: /* manual */
1360c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "1\n");
1361c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	default: /* automatic */
1362c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "2\n");
1363c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
1364c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1365c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1366c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic void set_pwm_channel(struct i2c_client *client,
1367c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct adt7462_data *data,
1368c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    int which,
1369c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    int value)
1370c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1371c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int temp = data->pwm_cfg[which] & ~ADT7462_PWM_CHANNEL_MASK;
1372c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp |= value << ADT7462_PWM_CHANNEL_SHIFT;
1373c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1374c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_lock(&data->lock);
1375c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->pwm_cfg[which] = temp;
1376c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_smbus_write_byte_data(client, ADT7462_REG_PWM_CFG(which), temp);
1377c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_unlock(&data->lock);
1378c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1379c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1380c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_auto(struct device *dev,
1381c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    struct device_attribute *devattr,
1382c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    const char *buf,
1383c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			    size_t count)
1384c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1385c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1386c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1387c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1388c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1389c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1390179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1391c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1392c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1393c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (temp) {
1394c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0: /* off */
1395c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		set_pwm_channel(client, data, attr->index, 4);
1396c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return count;
1397c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1: /* manual */
1398c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		set_pwm_channel(client, data, attr->index, 7);
1399c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return count;
1400c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	default:
1401c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1402c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
1403c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1404c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1405c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t show_pwm_auto_temp(struct device *dev,
1406c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  struct device_attribute *devattr,
1407c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				  char *buf)
1408c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1409c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1410c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = adt7462_update_device(dev);
1411c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int channel = data->pwm_cfg[attr->index] >> ADT7462_PWM_CHANNEL_SHIFT;
1412c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1413c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	switch (channel) {
1414c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 0: /* temp[1234] only */
1415c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 1:
1416c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 2:
1417c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 3:
1418c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "%d\n", (1 << channel));
1419c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 5: /* temp1 & temp4  */
1420c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "9\n");
1421c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	case 6:
1422c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "15\n");
1423c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	default:
1424c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return sprintf(buf, "0\n");
1425c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
1426c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1427c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1428c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int cvt_auto_temp(int input)
1429c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1430c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (input == 0xF)
1431c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 6;
1432c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (input == 0x9)
1433c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return 5;
1434c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (input < 1 || !is_power_of_2(input))
1435c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1436c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return ilog2(input);
1437c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1438c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1439c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic ssize_t set_pwm_auto_temp(struct device *dev,
1440c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				 struct device_attribute *devattr,
1441c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				 const char *buf,
1442c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong				 size_t count)
1443c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1444c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct sensor_device_attribute *attr = to_sensor_dev_attr(devattr);
1445c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_client *client = to_i2c_client(dev);
1446c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1447c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	long temp;
1448c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1449179c4fdb565dd2157e5dfe89318b74868e3b523dFrans Meulenbroeks	if (kstrtol(buf, 10, &temp))
1450c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -EINVAL;
1451c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1452c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	temp = cvt_auto_temp(temp);
1453c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (temp < 0)
1454c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return temp;
1455c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1456c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	set_pwm_channel(client, data, attr->index, temp);
1457c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1458c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return count;
1459c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1460c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1461c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_max, S_IWUSR | S_IRUGO, show_temp_max,
1462c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_max, 0);
1463c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_max, S_IWUSR | S_IRUGO, show_temp_max,
1464c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_max, 1);
1465c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_max, S_IWUSR | S_IRUGO, show_temp_max,
1466c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_max, 2);
1467c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_max, S_IWUSR | S_IRUGO, show_temp_max,
1468c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_max, 3);
1469c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1470c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_min, S_IWUSR | S_IRUGO, show_temp_min,
1471c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_min, 0);
1472c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_min, S_IWUSR | S_IRUGO, show_temp_min,
1473c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_min, 1);
1474c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_min, S_IWUSR | S_IRUGO, show_temp_min,
1475c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_min, 2);
1476c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_min, S_IWUSR | S_IRUGO, show_temp_min,
1477c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_temp_min, 3);
1478c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1479c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_input, S_IRUGO, show_temp, NULL, 0);
1480c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_input, S_IRUGO, show_temp, NULL, 1);
1481c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_input, S_IRUGO, show_temp, NULL, 2);
1482c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_input, S_IRUGO, show_temp, NULL, 3);
1483c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1484c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_label, S_IRUGO, show_temp_label, NULL, 0);
1485c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_label, S_IRUGO, show_temp_label, NULL, 1);
1486c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_label, S_IRUGO, show_temp_label, NULL, 2);
1487c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_label, S_IRUGO, show_temp_label, NULL, 3);
1488c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1489c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_alarm, S_IRUGO, show_alarm, NULL,
1490c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM1 | ADT7462_LT_ALARM);
1491c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_alarm, S_IRUGO, show_alarm, NULL,
1492c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM1 | ADT7462_R1T_ALARM);
1493c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_alarm, S_IRUGO, show_alarm, NULL,
1494c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM1 | ADT7462_R2T_ALARM);
1495c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_alarm, S_IRUGO, show_alarm, NULL,
1496c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM1 | ADT7462_R3T_ALARM);
1497c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1498c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in1_max, S_IWUSR | S_IRUGO, show_volt_max,
1499c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 0);
1500c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in2_max, S_IWUSR | S_IRUGO, show_volt_max,
1501c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 1);
1502c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in3_max, S_IWUSR | S_IRUGO, show_volt_max,
1503c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 2);
1504c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in4_max, S_IWUSR | S_IRUGO, show_volt_max,
1505c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 3);
1506c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in5_max, S_IWUSR | S_IRUGO, show_volt_max,
1507c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 4);
1508c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in6_max, S_IWUSR | S_IRUGO, show_volt_max,
1509c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 5);
1510c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in7_max, S_IWUSR | S_IRUGO, show_volt_max,
1511c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 6);
1512c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in8_max, S_IWUSR | S_IRUGO, show_volt_max,
1513c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 7);
1514c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in9_max, S_IWUSR | S_IRUGO, show_volt_max,
1515c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 8);
1516c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in10_max, S_IWUSR | S_IRUGO, show_volt_max,
1517c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 9);
1518c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in11_max, S_IWUSR | S_IRUGO, show_volt_max,
1519c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 10);
1520c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in12_max, S_IWUSR | S_IRUGO, show_volt_max,
1521c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 11);
1522c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in13_max, S_IWUSR | S_IRUGO, show_volt_max,
1523c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_max, 12);
1524c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1525c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in1_min, S_IWUSR | S_IRUGO, show_volt_min,
1526c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 0);
1527c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in2_min, S_IWUSR | S_IRUGO, show_volt_min,
1528c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 1);
1529c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in3_min, S_IWUSR | S_IRUGO, show_volt_min,
1530c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 2);
1531c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in4_min, S_IWUSR | S_IRUGO, show_volt_min,
1532c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 3);
1533c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in5_min, S_IWUSR | S_IRUGO, show_volt_min,
1534c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 4);
1535c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in6_min, S_IWUSR | S_IRUGO, show_volt_min,
1536c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 5);
1537c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in7_min, S_IWUSR | S_IRUGO, show_volt_min,
1538c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 6);
1539c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in8_min, S_IWUSR | S_IRUGO, show_volt_min,
1540c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 7);
1541c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in9_min, S_IWUSR | S_IRUGO, show_volt_min,
1542c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 8);
1543c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in10_min, S_IWUSR | S_IRUGO, show_volt_min,
1544c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 9);
1545c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in11_min, S_IWUSR | S_IRUGO, show_volt_min,
1546c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 10);
1547c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in12_min, S_IWUSR | S_IRUGO, show_volt_min,
1548c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 11);
1549c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in13_min, S_IWUSR | S_IRUGO, show_volt_min,
1550c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_volt_min, 12);
1551c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1552c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in1_input, S_IRUGO, show_voltage, NULL, 0);
1553c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in2_input, S_IRUGO, show_voltage, NULL, 1);
1554c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in3_input, S_IRUGO, show_voltage, NULL, 2);
1555c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in4_input, S_IRUGO, show_voltage, NULL, 3);
1556c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in5_input, S_IRUGO, show_voltage, NULL, 4);
1557c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in6_input, S_IRUGO, show_voltage, NULL, 5);
1558c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in7_input, S_IRUGO, show_voltage, NULL, 6);
1559c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in8_input, S_IRUGO, show_voltage, NULL, 7);
1560c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in9_input, S_IRUGO, show_voltage, NULL, 8);
1561c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in10_input, S_IRUGO, show_voltage, NULL, 9);
1562c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in11_input, S_IRUGO, show_voltage, NULL, 10);
1563c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in12_input, S_IRUGO, show_voltage, NULL, 11);
1564c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in13_input, S_IRUGO, show_voltage, NULL, 12);
1565c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1566c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in1_label, S_IRUGO, show_voltage_label, NULL, 0);
1567c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in2_label, S_IRUGO, show_voltage_label, NULL, 1);
1568c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in3_label, S_IRUGO, show_voltage_label, NULL, 2);
1569c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in4_label, S_IRUGO, show_voltage_label, NULL, 3);
1570c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in5_label, S_IRUGO, show_voltage_label, NULL, 4);
1571c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in6_label, S_IRUGO, show_voltage_label, NULL, 5);
1572c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in7_label, S_IRUGO, show_voltage_label, NULL, 6);
1573c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in8_label, S_IRUGO, show_voltage_label, NULL, 7);
1574c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in9_label, S_IRUGO, show_voltage_label, NULL, 8);
1575c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in10_label, S_IRUGO, show_voltage_label, NULL, 9);
1576c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in11_label, S_IRUGO, show_voltage_label, NULL, 10);
1577c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in12_label, S_IRUGO, show_voltage_label, NULL, 11);
1578c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in13_label, S_IRUGO, show_voltage_label, NULL, 12);
1579c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1580c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in1_alarm, S_IRUGO, show_alarm, NULL,
1581c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V0_ALARM);
1582c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in2_alarm, S_IRUGO, show_alarm, NULL,
1583c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V7_ALARM);
1584c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in3_alarm, S_IRUGO, show_alarm, NULL,
1585c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V2_ALARM);
1586c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in4_alarm, S_IRUGO, show_alarm, NULL,
1587c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V6_ALARM);
1588c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in5_alarm, S_IRUGO, show_alarm, NULL,
1589c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V5_ALARM);
1590c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in6_alarm, S_IRUGO, show_alarm, NULL,
1591c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V4_ALARM);
1592c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in7_alarm, S_IRUGO, show_alarm, NULL,
1593c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V3_ALARM);
1594c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in8_alarm, S_IRUGO, show_alarm, NULL,
1595c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM2 | ADT7462_V1_ALARM);
1596c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in9_alarm, S_IRUGO, show_alarm, NULL,
1597c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM3 | ADT7462_V10_ALARM);
1598c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in10_alarm, S_IRUGO, show_alarm, NULL,
1599c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM3 | ADT7462_V9_ALARM);
1600c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in11_alarm, S_IRUGO, show_alarm, NULL,
1601c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM3 | ADT7462_V8_ALARM);
1602c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in12_alarm, S_IRUGO, show_alarm, NULL,
1603c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM3 | ADT7462_V11_ALARM);
1604c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(in13_alarm, S_IRUGO, show_alarm, NULL,
1605c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM3 | ADT7462_V12_ALARM);
1606c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1607c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan1_min, S_IWUSR | S_IRUGO, show_fan_min,
1608c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 0);
1609c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan2_min, S_IWUSR | S_IRUGO, show_fan_min,
1610c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 1);
1611c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan3_min, S_IWUSR | S_IRUGO, show_fan_min,
1612c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 2);
1613c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan4_min, S_IWUSR | S_IRUGO, show_fan_min,
1614c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 3);
1615c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan5_min, S_IWUSR | S_IRUGO, show_fan_min,
1616c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 4);
1617c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan6_min, S_IWUSR | S_IRUGO, show_fan_min,
1618c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 5);
1619c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan7_min, S_IWUSR | S_IRUGO, show_fan_min,
1620c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 6);
1621c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan8_min, S_IWUSR | S_IRUGO, show_fan_min,
1622c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_fan_min, 7);
1623c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1624c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan1_input, S_IRUGO, show_fan, NULL, 0);
1625c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan2_input, S_IRUGO, show_fan, NULL, 1);
1626c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan3_input, S_IRUGO, show_fan, NULL, 2);
1627c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan4_input, S_IRUGO, show_fan, NULL, 3);
1628c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan5_input, S_IRUGO, show_fan, NULL, 4);
1629c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan6_input, S_IRUGO, show_fan, NULL, 5);
1630c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan7_input, S_IRUGO, show_fan, NULL, 6);
1631c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan8_input, S_IRUGO, show_fan, NULL, 7);
1632c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1633c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan1_alarm, S_IRUGO, show_alarm, NULL,
1634c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F0_ALARM);
1635c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan2_alarm, S_IRUGO, show_alarm, NULL,
1636c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F1_ALARM);
1637c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan3_alarm, S_IRUGO, show_alarm, NULL,
1638c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F2_ALARM);
1639c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan4_alarm, S_IRUGO, show_alarm, NULL,
1640c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F3_ALARM);
1641c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan5_alarm, S_IRUGO, show_alarm, NULL,
1642c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F4_ALARM);
1643c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan6_alarm, S_IRUGO, show_alarm, NULL,
1644c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F5_ALARM);
1645c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan7_alarm, S_IRUGO, show_alarm, NULL,
1646c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F6_ALARM);
1647c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(fan8_alarm, S_IRUGO, show_alarm, NULL,
1648c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  ADT7462_ALARM4 | ADT7462_F7_ALARM);
1649c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1650c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(force_pwm_max, S_IWUSR | S_IRUGO,
1651c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_force_pwm_max, set_force_pwm_max, 0);
1652c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1653c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm1, S_IWUSR | S_IRUGO, show_pwm, set_pwm, 0);
1654c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm2, S_IWUSR | S_IRUGO, show_pwm, set_pwm, 1);
1655c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm3, S_IWUSR | S_IRUGO, show_pwm, set_pwm, 2);
1656c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm4, S_IWUSR | S_IRUGO, show_pwm, set_pwm, 3);
1657c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1658c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm1_auto_point1_pwm, S_IWUSR | S_IRUGO,
1659c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_min, set_pwm_min, 0);
1660c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm2_auto_point1_pwm, S_IWUSR | S_IRUGO,
1661c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_min, set_pwm_min, 1);
1662c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm3_auto_point1_pwm, S_IWUSR | S_IRUGO,
1663c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_min, set_pwm_min, 2);
1664c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm4_auto_point1_pwm, S_IWUSR | S_IRUGO,
1665c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_min, set_pwm_min, 3);
1666c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1667c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm1_auto_point2_pwm, S_IWUSR | S_IRUGO,
1668c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_max, set_pwm_max, 0);
1669c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm2_auto_point2_pwm, S_IWUSR | S_IRUGO,
1670c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_max, set_pwm_max, 1);
1671c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm3_auto_point2_pwm, S_IWUSR | S_IRUGO,
1672c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_max, set_pwm_max, 2);
1673c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm4_auto_point2_pwm, S_IWUSR | S_IRUGO,
1674c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_max, set_pwm_max, 3);
1675c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1676c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_auto_point1_hyst, S_IWUSR | S_IRUGO,
1677c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 0);
1678c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_auto_point1_hyst, S_IWUSR | S_IRUGO,
1679c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 1);
1680c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_auto_point1_hyst, S_IWUSR | S_IRUGO,
1681c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 2);
1682c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_auto_point1_hyst, S_IWUSR | S_IRUGO,
1683c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 3);
1684c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1685c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_auto_point2_hyst, S_IWUSR | S_IRUGO,
1686c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 0);
1687c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_auto_point2_hyst, S_IWUSR | S_IRUGO,
1688c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 1);
1689c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_auto_point2_hyst, S_IWUSR | S_IRUGO,
1690c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 2);
1691c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_auto_point2_hyst, S_IWUSR | S_IRUGO,
1692c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_hyst, set_pwm_hyst, 3);
1693c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1694c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_auto_point1_temp, S_IWUSR | S_IRUGO,
1695c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmin, set_pwm_tmin, 0);
1696c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_auto_point1_temp, S_IWUSR | S_IRUGO,
1697c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmin, set_pwm_tmin, 1);
1698c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_auto_point1_temp, S_IWUSR | S_IRUGO,
1699c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmin, set_pwm_tmin, 2);
1700c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_auto_point1_temp, S_IWUSR | S_IRUGO,
1701c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmin, set_pwm_tmin, 3);
1702c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1703c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp1_auto_point2_temp, S_IWUSR | S_IRUGO,
1704c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmax, set_pwm_tmax, 0);
1705c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp2_auto_point2_temp, S_IWUSR | S_IRUGO,
1706c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmax, set_pwm_tmax, 1);
1707c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp3_auto_point2_temp, S_IWUSR | S_IRUGO,
1708c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmax, set_pwm_tmax, 2);
1709c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(temp4_auto_point2_temp, S_IWUSR | S_IRUGO,
1710c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_tmax, set_pwm_tmax, 3);
1711c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1712c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm1_enable, S_IWUSR | S_IRUGO, show_pwm_auto,
1713c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_pwm_auto, 0);
1714c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm2_enable, S_IWUSR | S_IRUGO, show_pwm_auto,
1715c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_pwm_auto, 1);
1716c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm3_enable, S_IWUSR | S_IRUGO, show_pwm_auto,
1717c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_pwm_auto, 2);
1718c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm4_enable, S_IWUSR | S_IRUGO, show_pwm_auto,
1719c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    set_pwm_auto, 3);
1720c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1721c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm1_auto_channels_temp, S_IWUSR | S_IRUGO,
1722c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_auto_temp, set_pwm_auto_temp, 0);
1723c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm2_auto_channels_temp, S_IWUSR | S_IRUGO,
1724c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_auto_temp, set_pwm_auto_temp, 1);
1725c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm3_auto_channels_temp, S_IWUSR | S_IRUGO,
1726c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_auto_temp, set_pwm_auto_temp, 2);
1727c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic SENSOR_DEVICE_ATTR(pwm4_auto_channels_temp, S_IWUSR | S_IRUGO,
1728c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		    show_pwm_auto_temp, set_pwm_auto_temp, 3);
1729c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1730724cc3316e6e1060f727958b4c327001c0bbd62cGuenter Roeckstatic struct attribute *adt7462_attr[] = {
1731c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_max.dev_attr.attr,
1732c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_max.dev_attr.attr,
1733c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_max.dev_attr.attr,
1734c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_max.dev_attr.attr,
1735c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1736c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_min.dev_attr.attr,
1737c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_min.dev_attr.attr,
1738c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_min.dev_attr.attr,
1739c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_min.dev_attr.attr,
1740c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1741c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_input.dev_attr.attr,
1742c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_input.dev_attr.attr,
1743c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_input.dev_attr.attr,
1744c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_input.dev_attr.attr,
1745c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1746c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_label.dev_attr.attr,
1747c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_label.dev_attr.attr,
1748c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_label.dev_attr.attr,
1749c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_label.dev_attr.attr,
1750c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1751c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_alarm.dev_attr.attr,
1752c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_alarm.dev_attr.attr,
1753c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_alarm.dev_attr.attr,
1754c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_alarm.dev_attr.attr,
1755c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1756c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in1_max.dev_attr.attr,
1757c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in2_max.dev_attr.attr,
1758c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in3_max.dev_attr.attr,
1759c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in4_max.dev_attr.attr,
1760c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in5_max.dev_attr.attr,
1761c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in6_max.dev_attr.attr,
1762c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in7_max.dev_attr.attr,
1763c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in8_max.dev_attr.attr,
1764c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in9_max.dev_attr.attr,
1765c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in10_max.dev_attr.attr,
1766c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in11_max.dev_attr.attr,
1767c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in12_max.dev_attr.attr,
1768c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in13_max.dev_attr.attr,
1769c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1770c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in1_min.dev_attr.attr,
1771c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in2_min.dev_attr.attr,
1772c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in3_min.dev_attr.attr,
1773c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in4_min.dev_attr.attr,
1774c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in5_min.dev_attr.attr,
1775c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in6_min.dev_attr.attr,
1776c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in7_min.dev_attr.attr,
1777c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in8_min.dev_attr.attr,
1778c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in9_min.dev_attr.attr,
1779c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in10_min.dev_attr.attr,
1780c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in11_min.dev_attr.attr,
1781c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in12_min.dev_attr.attr,
1782c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in13_min.dev_attr.attr,
1783c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1784c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in1_input.dev_attr.attr,
1785c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in2_input.dev_attr.attr,
1786c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in3_input.dev_attr.attr,
1787c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in4_input.dev_attr.attr,
1788c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in5_input.dev_attr.attr,
1789c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in6_input.dev_attr.attr,
1790c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in7_input.dev_attr.attr,
1791c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in8_input.dev_attr.attr,
1792c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in9_input.dev_attr.attr,
1793c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in10_input.dev_attr.attr,
1794c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in11_input.dev_attr.attr,
1795c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in12_input.dev_attr.attr,
1796c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in13_input.dev_attr.attr,
1797c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1798c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in1_label.dev_attr.attr,
1799c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in2_label.dev_attr.attr,
1800c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in3_label.dev_attr.attr,
1801c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in4_label.dev_attr.attr,
1802c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in5_label.dev_attr.attr,
1803c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in6_label.dev_attr.attr,
1804c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in7_label.dev_attr.attr,
1805c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in8_label.dev_attr.attr,
1806c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in9_label.dev_attr.attr,
1807c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in10_label.dev_attr.attr,
1808c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in11_label.dev_attr.attr,
1809c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in12_label.dev_attr.attr,
1810c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in13_label.dev_attr.attr,
1811c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1812c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in1_alarm.dev_attr.attr,
1813c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in2_alarm.dev_attr.attr,
1814c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in3_alarm.dev_attr.attr,
1815c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in4_alarm.dev_attr.attr,
1816c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in5_alarm.dev_attr.attr,
1817c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in6_alarm.dev_attr.attr,
1818c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in7_alarm.dev_attr.attr,
1819c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in8_alarm.dev_attr.attr,
1820c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in9_alarm.dev_attr.attr,
1821c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in10_alarm.dev_attr.attr,
1822c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in11_alarm.dev_attr.attr,
1823c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in12_alarm.dev_attr.attr,
1824c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_in13_alarm.dev_attr.attr,
1825c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1826c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan1_min.dev_attr.attr,
1827c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan2_min.dev_attr.attr,
1828c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan3_min.dev_attr.attr,
1829c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan4_min.dev_attr.attr,
1830c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan5_min.dev_attr.attr,
1831c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan6_min.dev_attr.attr,
1832c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan7_min.dev_attr.attr,
1833c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan8_min.dev_attr.attr,
1834c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1835c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan1_input.dev_attr.attr,
1836c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan2_input.dev_attr.attr,
1837c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan3_input.dev_attr.attr,
1838c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan4_input.dev_attr.attr,
1839c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan5_input.dev_attr.attr,
1840c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan6_input.dev_attr.attr,
1841c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan7_input.dev_attr.attr,
1842c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan8_input.dev_attr.attr,
1843c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1844c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan1_alarm.dev_attr.attr,
1845c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan2_alarm.dev_attr.attr,
1846c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan3_alarm.dev_attr.attr,
1847c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan4_alarm.dev_attr.attr,
1848c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan5_alarm.dev_attr.attr,
1849c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan6_alarm.dev_attr.attr,
1850c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan7_alarm.dev_attr.attr,
1851c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_fan8_alarm.dev_attr.attr,
1852c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1853c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_force_pwm_max.dev_attr.attr,
1854c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm1.dev_attr.attr,
1855c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm2.dev_attr.attr,
1856c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm3.dev_attr.attr,
1857c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm4.dev_attr.attr,
1858c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1859c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm1_auto_point1_pwm.dev_attr.attr,
1860c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm2_auto_point1_pwm.dev_attr.attr,
1861c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm3_auto_point1_pwm.dev_attr.attr,
1862c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm4_auto_point1_pwm.dev_attr.attr,
1863c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1864c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm1_auto_point2_pwm.dev_attr.attr,
1865c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm2_auto_point2_pwm.dev_attr.attr,
1866c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm3_auto_point2_pwm.dev_attr.attr,
1867c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm4_auto_point2_pwm.dev_attr.attr,
1868c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1869c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_auto_point1_hyst.dev_attr.attr,
1870c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_auto_point1_hyst.dev_attr.attr,
1871c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_auto_point1_hyst.dev_attr.attr,
1872c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_auto_point1_hyst.dev_attr.attr,
1873c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1874c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_auto_point2_hyst.dev_attr.attr,
1875c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_auto_point2_hyst.dev_attr.attr,
1876c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_auto_point2_hyst.dev_attr.attr,
1877c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_auto_point2_hyst.dev_attr.attr,
1878c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1879c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_auto_point1_temp.dev_attr.attr,
1880c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_auto_point1_temp.dev_attr.attr,
1881c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_auto_point1_temp.dev_attr.attr,
1882c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_auto_point1_temp.dev_attr.attr,
1883c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1884c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp1_auto_point2_temp.dev_attr.attr,
1885c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp2_auto_point2_temp.dev_attr.attr,
1886c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp3_auto_point2_temp.dev_attr.attr,
1887c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_temp4_auto_point2_temp.dev_attr.attr,
1888c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1889c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm1_enable.dev_attr.attr,
1890c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm2_enable.dev_attr.attr,
1891c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm3_enable.dev_attr.attr,
1892c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm4_enable.dev_attr.attr,
1893c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1894c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm1_auto_channels_temp.dev_attr.attr,
1895c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm2_auto_channels_temp.dev_attr.attr,
1896c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm3_auto_channels_temp.dev_attr.attr,
1897c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	&sensor_dev_attr_pwm4_auto_channels_temp.dev_attr.attr,
1898c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	NULL
1899c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong};
1900c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1901c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong/* Return 0 if detection is successful, -ENODEV otherwise */
1902310ec79210d754afe51e2e4a983e846b60179abdJean Delvarestatic int adt7462_detect(struct i2c_client *client,
1903c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			  struct i2c_board_info *info)
1904c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1905c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct i2c_adapter *adapter = client->adapter;
190652df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	int vendor, device, revision;
1907c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1908c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA))
1909c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		return -ENODEV;
1910c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
191152df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	vendor = i2c_smbus_read_byte_data(client, ADT7462_REG_VENDOR);
191252df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	if (vendor != ADT7462_VENDOR)
191352df6440a29123eed912183fe785bbe174ef14b9Jean Delvare		return -ENODEV;
1914c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
191552df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	device = i2c_smbus_read_byte_data(client, ADT7462_REG_DEVICE);
191652df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	if (device != ADT7462_DEVICE)
191752df6440a29123eed912183fe785bbe174ef14b9Jean Delvare		return -ENODEV;
1918c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
191952df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	revision = i2c_smbus_read_byte_data(client, ADT7462_REG_REVISION);
192052df6440a29123eed912183fe785bbe174ef14b9Jean Delvare	if (revision != ADT7462_REVISION)
192152df6440a29123eed912183fe785bbe174ef14b9Jean Delvare		return -ENODEV;
1922c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1923c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	strlcpy(info->type, "adt7462", I2C_NAME_SIZE);
1924c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1925c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return 0;
1926c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1927c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1928c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int adt7462_probe(struct i2c_client *client,
1929c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong			 const struct i2c_device_id *id)
1930c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1931c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data;
1932c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	int err;
1933c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1934c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data = kzalloc(sizeof(struct adt7462_data), GFP_KERNEL);
1935c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (!data) {
1936c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		err = -ENOMEM;
1937c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		goto exit;
1938c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
1939c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1940c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	i2c_set_clientdata(client, data);
1941c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	mutex_init(&data->lock);
1942c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1943c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	dev_info(&client->dev, "%s chip found\n", client->name);
1944c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1945c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	/* Register sysfs hooks */
1946c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->attrs.attrs = adt7462_attr;
1947c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	err = sysfs_create_group(&client->dev.kobj, &data->attrs);
1948c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (err)
1949c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		goto exit_free;
1950c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1951c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	data->hwmon_dev = hwmon_device_register(&client->dev);
1952c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	if (IS_ERR(data->hwmon_dev)) {
1953c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		err = PTR_ERR(data->hwmon_dev);
1954c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong		goto exit_remove;
1955c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	}
1956c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1957c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return 0;
1958c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1959c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongexit_remove:
1960c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	sysfs_remove_group(&client->dev.kobj, &data->attrs);
1961c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongexit_free:
1962c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	kfree(data);
1963c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongexit:
1964c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return err;
1965c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1966c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1967c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wongstatic int adt7462_remove(struct i2c_client *client)
1968c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong{
1969c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	struct adt7462_data *data = i2c_get_clientdata(client);
1970c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1971c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	hwmon_device_unregister(data->hwmon_dev);
1972c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	sysfs_remove_group(&client->dev.kobj, &data->attrs);
1973c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	kfree(data);
1974c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong	return 0;
1975c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong}
1976c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1977f0967eea80ec2a19a4fe1ad27e3ff1b22c79a3c7Axel Linmodule_i2c_driver(adt7462_driver);
1978c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. Wong
1979c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. WongMODULE_AUTHOR("Darrick J. Wong <djwong@us.ibm.com>");
1980c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. WongMODULE_DESCRIPTION("ADT7462 driver");
1981c0b4e3ab0c769913438aeb078535ff117eeba5fbDarrick J. WongMODULE_LICENSE("GPL");
1982