1 | // SPDX-License-Identifier: GPL-2.0+ |
2 | /* |
3 | * Hardware monitoring driver for MAX127. |
4 | * |
5 | * Copyright (c) 2020 Facebook Inc. |
6 | */ |
7 | |
8 | #include <linux/err.h> |
9 | #include <linux/hwmon.h> |
10 | #include <linux/i2c.h> |
11 | #include <linux/init.h> |
12 | #include <linux/module.h> |
13 | |
14 | /* |
15 | * MAX127 Control Byte. Refer to MAX127 datasheet, Table 1 "Control-Byte |
16 | * Format" for details. |
17 | */ |
18 | #define MAX127_CTRL_START BIT(7) |
19 | #define MAX127_CTRL_SEL_SHIFT 4 |
20 | #define MAX127_CTRL_RNG BIT(3) |
21 | #define MAX127_CTRL_BIP BIT(2) |
22 | #define MAX127_CTRL_PD1 BIT(1) |
23 | #define MAX127_CTRL_PD0 BIT(0) |
24 | |
25 | #define MAX127_NUM_CHANNELS 8 |
26 | #define MAX127_SET_CHANNEL(ch) (((ch) & 7) << MAX127_CTRL_SEL_SHIFT) |
27 | |
28 | /* |
29 | * MAX127 channel input ranges. Refer to MAX127 datasheet, Table 3 "Range |
30 | * and Polarity Selection" for details. |
31 | */ |
32 | #define MAX127_FULL_RANGE 10000 /* 10V */ |
33 | #define MAX127_HALF_RANGE 5000 /* 5V */ |
34 | |
35 | /* |
36 | * MAX127 returns 2 bytes at read: |
37 | * - the first byte contains data[11:4]. |
38 | * - the second byte contains data[3:0] (MSB) and 4 dummy 0s (LSB). |
39 | * Refer to MAX127 datasheet, "Read a Conversion (Read Cycle)" section |
40 | * for details. |
41 | */ |
42 | #define MAX127_DATA_LEN 2 |
43 | #define MAX127_DATA_SHIFT 4 |
44 | |
45 | #define MAX127_SIGN_BIT BIT(11) |
46 | |
47 | struct max127_data { |
48 | struct mutex lock; |
49 | struct i2c_client *client; |
50 | u8 ctrl_byte[MAX127_NUM_CHANNELS]; |
51 | }; |
52 | |
53 | static int max127_select_channel(struct i2c_client *client, u8 ctrl_byte) |
54 | { |
55 | int status; |
56 | struct i2c_msg msg = { |
57 | .addr = client->addr, |
58 | .flags = 0, |
59 | .len = sizeof(ctrl_byte), |
60 | .buf = &ctrl_byte, |
61 | }; |
62 | |
63 | status = i2c_transfer(adap: client->adapter, msgs: &msg, num: 1); |
64 | if (status < 0) |
65 | return status; |
66 | if (status != 1) |
67 | return -EIO; |
68 | |
69 | return 0; |
70 | } |
71 | |
72 | static int max127_read_channel(struct i2c_client *client, long *val) |
73 | { |
74 | int status; |
75 | u8 i2c_data[MAX127_DATA_LEN]; |
76 | struct i2c_msg msg = { |
77 | .addr = client->addr, |
78 | .flags = I2C_M_RD, |
79 | .len = sizeof(i2c_data), |
80 | .buf = i2c_data, |
81 | }; |
82 | |
83 | status = i2c_transfer(adap: client->adapter, msgs: &msg, num: 1); |
84 | if (status < 0) |
85 | return status; |
86 | if (status != 1) |
87 | return -EIO; |
88 | |
89 | *val = (i2c_data[1] >> MAX127_DATA_SHIFT) | |
90 | ((u16)i2c_data[0] << MAX127_DATA_SHIFT); |
91 | return 0; |
92 | } |
93 | |
94 | static long max127_process_raw(u8 ctrl_byte, long raw) |
95 | { |
96 | long scale, weight; |
97 | |
98 | /* |
99 | * MAX127's data coding is binary in unipolar mode with 1 LSB = |
100 | * (Full-Scale/4096) and two’s complement binary in bipolar mode |
101 | * with 1 LSB = [(2 x |FS|)/4096]. |
102 | * Refer to MAX127 datasheet, "Transfer Function" section for |
103 | * details. |
104 | */ |
105 | scale = (ctrl_byte & MAX127_CTRL_RNG) ? MAX127_FULL_RANGE : |
106 | MAX127_HALF_RANGE; |
107 | if (ctrl_byte & MAX127_CTRL_BIP) { |
108 | weight = (raw & MAX127_SIGN_BIT); |
109 | raw &= ~MAX127_SIGN_BIT; |
110 | raw -= weight; |
111 | raw *= 2; |
112 | } |
113 | |
114 | return raw * scale / 4096; |
115 | } |
116 | |
117 | static int max127_read_input(struct max127_data *data, int channel, long *val) |
118 | { |
119 | long raw; |
120 | int status; |
121 | struct i2c_client *client = data->client; |
122 | u8 ctrl_byte = data->ctrl_byte[channel]; |
123 | |
124 | mutex_lock(&data->lock); |
125 | |
126 | status = max127_select_channel(client, ctrl_byte); |
127 | if (status) |
128 | goto exit; |
129 | |
130 | status = max127_read_channel(client, val: &raw); |
131 | if (status) |
132 | goto exit; |
133 | |
134 | *val = max127_process_raw(ctrl_byte, raw); |
135 | |
136 | exit: |
137 | mutex_unlock(lock: &data->lock); |
138 | return status; |
139 | } |
140 | |
141 | static int max127_read_min(struct max127_data *data, int channel, long *val) |
142 | { |
143 | u8 rng_bip = (data->ctrl_byte[channel] >> 2) & 3; |
144 | static const int min_input_map[4] = { |
145 | 0, /* RNG=0, BIP=0 */ |
146 | -MAX127_HALF_RANGE, /* RNG=0, BIP=1 */ |
147 | 0, /* RNG=1, BIP=0 */ |
148 | -MAX127_FULL_RANGE, /* RNG=1, BIP=1 */ |
149 | }; |
150 | |
151 | *val = min_input_map[rng_bip]; |
152 | return 0; |
153 | } |
154 | |
155 | static int max127_read_max(struct max127_data *data, int channel, long *val) |
156 | { |
157 | u8 rng_bip = (data->ctrl_byte[channel] >> 2) & 3; |
158 | static const int max_input_map[4] = { |
159 | MAX127_HALF_RANGE, /* RNG=0, BIP=0 */ |
160 | MAX127_HALF_RANGE, /* RNG=0, BIP=1 */ |
161 | MAX127_FULL_RANGE, /* RNG=1, BIP=0 */ |
162 | MAX127_FULL_RANGE, /* RNG=1, BIP=1 */ |
163 | }; |
164 | |
165 | *val = max_input_map[rng_bip]; |
166 | return 0; |
167 | } |
168 | |
169 | static int max127_write_min(struct max127_data *data, int channel, long val) |
170 | { |
171 | u8 ctrl; |
172 | |
173 | mutex_lock(&data->lock); |
174 | |
175 | ctrl = data->ctrl_byte[channel]; |
176 | if (val <= -MAX127_FULL_RANGE) { |
177 | ctrl |= (MAX127_CTRL_RNG | MAX127_CTRL_BIP); |
178 | } else if (val < 0) { |
179 | ctrl |= MAX127_CTRL_BIP; |
180 | ctrl &= ~MAX127_CTRL_RNG; |
181 | } else { |
182 | ctrl &= ~MAX127_CTRL_BIP; |
183 | } |
184 | data->ctrl_byte[channel] = ctrl; |
185 | |
186 | mutex_unlock(lock: &data->lock); |
187 | |
188 | return 0; |
189 | } |
190 | |
191 | static int max127_write_max(struct max127_data *data, int channel, long val) |
192 | { |
193 | mutex_lock(&data->lock); |
194 | |
195 | if (val >= MAX127_FULL_RANGE) |
196 | data->ctrl_byte[channel] |= MAX127_CTRL_RNG; |
197 | else |
198 | data->ctrl_byte[channel] &= ~MAX127_CTRL_RNG; |
199 | |
200 | mutex_unlock(lock: &data->lock); |
201 | |
202 | return 0; |
203 | } |
204 | |
205 | static umode_t max127_is_visible(const void *_data, |
206 | enum hwmon_sensor_types type, |
207 | u32 attr, int channel) |
208 | { |
209 | if (type == hwmon_in) { |
210 | switch (attr) { |
211 | case hwmon_in_input: |
212 | return 0444; |
213 | |
214 | case hwmon_in_min: |
215 | case hwmon_in_max: |
216 | return 0644; |
217 | |
218 | default: |
219 | break; |
220 | } |
221 | } |
222 | |
223 | return 0; |
224 | } |
225 | |
226 | static int max127_read(struct device *dev, enum hwmon_sensor_types type, |
227 | u32 attr, int channel, long *val) |
228 | { |
229 | int status; |
230 | struct max127_data *data = dev_get_drvdata(dev); |
231 | |
232 | if (type != hwmon_in) |
233 | return -EOPNOTSUPP; |
234 | |
235 | switch (attr) { |
236 | case hwmon_in_input: |
237 | status = max127_read_input(data, channel, val); |
238 | break; |
239 | |
240 | case hwmon_in_min: |
241 | status = max127_read_min(data, channel, val); |
242 | break; |
243 | |
244 | case hwmon_in_max: |
245 | status = max127_read_max(data, channel, val); |
246 | break; |
247 | |
248 | default: |
249 | status = -EOPNOTSUPP; |
250 | break; |
251 | } |
252 | |
253 | return status; |
254 | } |
255 | |
256 | static int max127_write(struct device *dev, enum hwmon_sensor_types type, |
257 | u32 attr, int channel, long val) |
258 | { |
259 | int status; |
260 | struct max127_data *data = dev_get_drvdata(dev); |
261 | |
262 | if (type != hwmon_in) |
263 | return -EOPNOTSUPP; |
264 | |
265 | switch (attr) { |
266 | case hwmon_in_min: |
267 | status = max127_write_min(data, channel, val); |
268 | break; |
269 | |
270 | case hwmon_in_max: |
271 | status = max127_write_max(data, channel, val); |
272 | break; |
273 | |
274 | default: |
275 | status = -EOPNOTSUPP; |
276 | break; |
277 | } |
278 | |
279 | return status; |
280 | } |
281 | |
282 | static const struct hwmon_ops max127_hwmon_ops = { |
283 | .is_visible = max127_is_visible, |
284 | .read = max127_read, |
285 | .write = max127_write, |
286 | }; |
287 | |
288 | static const struct hwmon_channel_info * const max127_info[] = { |
289 | HWMON_CHANNEL_INFO(in, |
290 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
291 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
292 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
293 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
294 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
295 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
296 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX, |
297 | HWMON_I_INPUT | HWMON_I_MIN | HWMON_I_MAX), |
298 | NULL, |
299 | }; |
300 | |
301 | static const struct hwmon_chip_info max127_chip_info = { |
302 | .ops = &max127_hwmon_ops, |
303 | .info = max127_info, |
304 | }; |
305 | |
306 | static int max127_probe(struct i2c_client *client) |
307 | { |
308 | int i; |
309 | struct device *hwmon_dev; |
310 | struct max127_data *data; |
311 | struct device *dev = &client->dev; |
312 | |
313 | data = devm_kzalloc(dev, size: sizeof(*data), GFP_KERNEL); |
314 | if (!data) |
315 | return -ENOMEM; |
316 | |
317 | data->client = client; |
318 | mutex_init(&data->lock); |
319 | for (i = 0; i < ARRAY_SIZE(data->ctrl_byte); i++) |
320 | data->ctrl_byte[i] = (MAX127_CTRL_START | |
321 | MAX127_SET_CHANNEL(i)); |
322 | |
323 | hwmon_dev = devm_hwmon_device_register_with_info(dev, name: client->name, |
324 | drvdata: data, |
325 | info: &max127_chip_info, |
326 | NULL); |
327 | |
328 | return PTR_ERR_OR_ZERO(ptr: hwmon_dev); |
329 | } |
330 | |
331 | static const struct i2c_device_id max127_id[] = { |
332 | { "max127" , 0 }, |
333 | { } |
334 | }; |
335 | MODULE_DEVICE_TABLE(i2c, max127_id); |
336 | |
337 | static struct i2c_driver max127_driver = { |
338 | .driver = { |
339 | .name = "max127" , |
340 | }, |
341 | .probe = max127_probe, |
342 | .id_table = max127_id, |
343 | }; |
344 | |
345 | module_i2c_driver(max127_driver); |
346 | |
347 | MODULE_LICENSE("GPL" ); |
348 | MODULE_AUTHOR("Mike Choi <mikechoi@fb.com>" ); |
349 | MODULE_AUTHOR("Tao Ren <rentao.bupt@gmail.com>" ); |
350 | MODULE_DESCRIPTION("MAX127 Hardware Monitoring driver" ); |
351 | |